c# - 在字段定义或类构造函数中初始化类字段

标签 c# constructor initialization field

我有一个类,其中有一个字段需要在初始化对象时进行初始化,例如需要在添加/删除对象之前创建的列表。

public class MyClass1
{
    private List<MyOtherClass> _otherClassList;

    public MyClass1()
    {
        this._otherClasslist = new List<MyOtherClass>();
    }
}


public class MyClass2
{
    private List<MyOtherClass> = new List<MyOtherClass>();

    public MyClass2()
    {
    }
}

这两个类之间有什么区别,为什么您会选择一种方法而不是另一种方法?

我通常在构造函数中设置字段,就像在 MyClass1 中一样,因为我发现更容易在一个地方查看对象被实例化时发生的所有事情,但是在任何情况下像在 MyClass2 中那样直接初始化一个字段更好吗?

最佳答案

C# 编译器 (VS2008 sp1) 发出的 IL 在这两种情况下几乎相同(即使在调试和发布版本中)。

但是,如果您需要添加带参数的构造函数 List<MyOtherClass> 作为参数,它会有所不同(尤其是当您将使用此类构造函数创建大量对象时)。

请参阅以下示例以查看差异(您可以复制并粘贴到 VS 并构建它以查看带有 ReflectorILDASM 的 IL)。

using System;
using System.Collections.Generic;

namespace Ctors
{
    //Tested with VS2008 SP1
    class A
    {
        //This will be executed before entering any constructor bodies...
        private List<string> myList = new List<string>();

        public A() { }

        //This will create an unused temp List<string> object 
        //in both Debug and Release build
        public A(List<string> list)
        {
            myList = list;
        }
    }

    class B
    {
        private List<string> myList;

        //ILs emitted by C# compiler are identicial to 
        //those of public A() in both Debug and Release build 
        public B()
        {
            myList = new List<string>();
        }

        //No garbage here
        public B(List<string> list)
        {
            myList = list;
        }
    }

    class C
    {

        private List<string> myList = null;
        //In Release build, this is identical to B(), 
        //In Debug build, ILs to initialize myList to null is inserted. 
        //So more ILs than B() in Debug build.  
        public C()
        {
            myList = new List<string>();
        }

        //This is identical to B(List<string> list) 
        //in both Debug and Release build. 
        public C(List<string> list)
        {
            myList = list;
        }
    }

    class D
    {
        //This will be executed before entering a try/catch block
        //in the default constructor
        private E myE = new E();
        public D()
        {
            try
            { }
            catch (NotImplementedException e)
            {
                //Cannot catch NotImplementedException thrown by E(). 
                Console.WriteLine("Can I catch here???");
            }
        }
    }

    public class E
    {
        public E()
        {
            throw new NotImplementedException();
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            //This will result in an unhandled exception. 
            //You may want to use try/catch block when constructing D objects.
            D myD = new D();
        }
    }
}

注意:切换到发布版本时我没有更改任何优化标志。

关于c# - 在字段定义或类构造函数中初始化类字段,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1157201/

相关文章:

c# - 在 C# 中获取重叠的正则表达式匹配

c++ - 是否可以在不使用默认构造函数的情况下在类定义中创建类的对象

Java - 在其构造函数中实例化同一类的对象

Java:通过在初始化期间返回现有类来防止重复类

c++如何初始化数组的const元素

c++ - 初始化和设置一个 vector<int>

c# - 如何使用 C# 从网页打开事件查看器?

c# - 如何找到直线与二维椭圆相交的点 (C#)

c# - 不能对空值调用此方法或属性。数据为空

scala - 在类构造函数中使用特征方法