c#3.0中的对象初始值设定项比常规方式更快吗?
这更快吗?
Object object = new Object
{
id = 1;
}
Run Code Online (Sandbox Code Playgroud)
比这个 ?
Object object = new Object()
object.id = 1;
Run Code Online (Sandbox Code Playgroud)
SLa*_*aks 23
在发布模式下,它们将编译为完全相同的 IL代码(假设您实际上使用的是具有id属性的类型而不是Object)
因此,根据定义,将没有性能差异.
我不知道哪一个编译速度会更快,但编译时间差别很小,你可能不在乎.
但是,对象初始化程序语法写得更快(更少打字),因此您应该使用它.
好的,根据[SLaks] [2]的评论,并在阅读后测试自己,结果证明我在这里描述的差异只出现在调试模式中.如果您为发布版编译,它们都会编译为相同的代码.每天学些新东西 :)
(所以其余的答案都假定为调试模式.)
还有就是在IL的差异产生的,相反的是其他人在这里已经回答了,但不同的是可以忽略不计,而不是实际上应该对你的程序的任何性能影响的.
区别在于使用对象初始值设定项,如下所示:
Object object = new Object
{
id = 1;
}
Run Code Online (Sandbox Code Playgroud)
代码实际上是编译好像你写的那样:
Object temp = new Object();
temp.id = 1;
Object object = temp;
Run Code Online (Sandbox Code Playgroud)
(当然,除非Object没有Id字段/属性,否则在不使用逐字标识符语法"@object"的情况下实际上无法命名变量"object".)
这为什么重要?好吧,您可能注意到的一个区别是,如果任何赋值抛出异常(将值写入对象,或者从表达式或函数中获取值抛出异常),那么使用对象初始值设定项,您就赢了实际上看到变量中的任何对象,而在"手动"代码中,对象将在那里,初始化直到发生异常的点.
一个微小的差异,不应该有很大的性能差异,但可能会改变您的程序的行为.
这可以通过查看IL来验证.拿这个C#程序:
using System;
namespace ConsoleApplication3
{
class Test
{
public Int32 Id { get; set; }
}
class Program
{
static void Main(string[] args)
{
M1();
M2();
}
static void M1()
{
Test t = new Test();
t.Id = 1;
}
static void M2()
{
Test t = new Test { Id = 1 };
}
static void M3()
{
Test t;
Test temp = new Test();
temp.Id = 1;
t = temp;
}
}
}
Run Code Online (Sandbox Code Playgroud)
并编译它,通过Reflector运行它,你将获得M1,M2和M3:
.method private hidebysig static void M1() cil managed
{
.maxstack 2
.locals init (
[0] class ConsoleApplication3.Test t)
L_0000: nop
L_0001: newobj instance void ConsoleApplication3.Test::.ctor()
L_0006: stloc.0
L_0007: ldloc.0
L_0008: ldc.i4.1
L_0009: callvirt instance void ConsoleApplication3.Test::set_Id(int32)
L_000e: nop
L_000f: ret
}
.method private hidebysig static void M2() cil managed
{
.maxstack 2
.locals init (
[0] class ConsoleApplication3.Test t,
[1] class ConsoleApplication3.Test <>g__initLocal0)
L_0000: nop
L_0001: newobj instance void ConsoleApplication3.Test::.ctor()
L_0006: stloc.1
L_0007: ldloc.1
L_0008: ldc.i4.1
L_0009: callvirt instance void ConsoleApplication3.Test::set_Id(int32)
L_000e: nop
L_000f: ldloc.1
L_0010: stloc.0
L_0011: ret
}
.method private hidebysig static void M3() cil managed
{
.maxstack 2
.locals init (
[0] class ConsoleApplication3.Test t,
[1] class ConsoleApplication3.Test temp)
L_0000: nop
L_0001: newobj instance void ConsoleApplication3.Test::.ctor()
L_0006: stloc.1
L_0007: ldloc.1
L_0008: ldc.i4.1
L_0009: callvirt instance void ConsoleApplication3.Test::set_Id(int32)
L_000e: nop
L_000f: ldloc.1
L_0010: stloc.0
L_0011: ret
}
Run Code Online (Sandbox Code Playgroud)
如果查看代码,M2和M3之间唯一不同的是第二个本地(<>g__initLocal0vs temp)的名称.
但正如其他人已经回答的那样,差异不会使你应该注意到任何性能差异.