C#变量初始化问题

时间:2009-06-04 19:10:08

标签: c# initialization default-value

我是否初始化整数变量如:

有什么不同
int i = 0;
int i;

编译器或CLR是否将此视为同一事物? IIRC,我认为他们都被视为同一件事,但我似乎无法找到这篇文章。

8 个答案:

答案 0 :(得分:14)

如果变量 i 是一个实例变量,则会自动为其赋值0。如果它是方法中的局部变量,则它是未定义的,因此在使用它之前需要为其赋值。

例如:

class Program
{
    static void Main(string[] args)
    {
        intTest it;

        it = new intTest();

        Console.ReadLine();
    }

    class intTest
    {
        int i;

        public intTest()
        {
            int i2;

            Console.WriteLine("i = " + i);
            Console.WriteLine("i2 = " + i2);
        }
    }
}

以上不会编译因为i2未分配。但是,通过将0分配给i2,即

int i2 = 0;

并编译,然后运行,将显示两者现在都被指定为0。

答案 1 :(得分:6)

我查看了IL(使用ildasm),并确认只有int设置为0才真正在构造函数中设置为0.

public class Class1
{
    int setToZero = 0;
    int notSet;
}

生成:

.method public hidebysig specialname rtspecialname 
        instance void  .ctor() cil managed
{
  // Code size       15 (0xf)
  .maxstack  8
  IL_0000:  ldarg.0
  IL_0001:  ldc.i4.0
  IL_0002:  stfld      int32 ClassLibrary1.Class1::setToZero
  IL_0007:  ldarg.0
  IL_0008:  call       instance void [mscorlib]System.Object::.ctor()
  IL_000d:  nop
  IL_000e:  ret
} // end of method Class1::.ctor

答案 2 :(得分:4)

是的,它几乎是一回事。

您可以参考Coding Horror

上的这篇文章

答案 3 :(得分:1)

如以下链接所述,它们完全相同:

http://msdn.microsoft.com/en-us/library/aa664742%28VS.71%29.aspx

答案 4 :(得分:1)

通过所有这些讨论,值得一提的是C#中的“default”关键字。

即。 int i;相当于int i = default(int);,相当于int i = 0; MyClass o = default(MyClass);相当于MyClass o = null;

这在使用.SingleOrDefault()等linq方法时尤其重要,因为您始终可以使用以下方法使代码更具可读性:

int someValue = collection.<various linq methods>.SingleOrDefault();
if (someValue == default(int))
{
  //Code for the default case
}

MyClass someValue = collection.<various linq methods>.SingleOrDefault();
if (someValue == default(MyClass))
{
  //Code for the default case
}

答案 5 :(得分:1)

这里的各种回应都有误导性,包括“编码恐怖”网站中引用的文章。

当配置为优化生成的代码时,编译器将优化您的代码以删除所有“不必要的”初始化。请注意,这是在“发布”模式下编译时的默认行为。

我认为,初始化所有变量总是非常有用。在调试模式下,性能命中率最低,在发布模式下没有,但是对于未来维护代码的任何人来说,明确设置变量的好处将是巨大的,在更好的“带代码的文档代码”样式中。我记得我非常有经验的同事认为Int32的默认值是Int32.MinValue而不是0.这些类型的混淆总是发生在代码中的含义中,对我来说,在大多数情况下应该避免它们。 / p>

答案 6 :(得分:0)

每次在C#中创建一个类型时,它都会自动填充填充的零。在类(引用类型)的情况下,这相当于空指针。因此,从技术上讲,每当您使用课程时,以下内容都是相同的:

MyClass class;
MyClass class2 = null;

使用值类型(任何结构,包括int / float / double / etc),类型以零传递,因此以下内容是等效的:

int i;
int j = 0;

但是,在方法中,编译器会在使用之前检查您是否为类型指定了值。如果您执行以下操作,编译器将会抱怨:

int i;
Console.WriteLine{"{0}",i);

从技术上讲,上面应该没问题 - 但由于它是程序员错误的常见来源,编译器专门检查未分配的局部变量,并抱怨。但是,这是一个编译时投诉,而不是CLR问题。你可以让IL做上面的事情,它运行正常。

答案 7 :(得分:0)

这些仅对于字段(类变量)是等效的。在初始化类时,会自动为字段分配默认值。在方法或属性中,未分配的变量保持未分配状态,如果您尝试访问它的值,将导致编译器错误。