.net中的结构构造函数:任何开销?

Mir*_*vec 1 .net structure

关于使用结构构造函数; 这两个代码块的性能相同吗?

使用构造函数:

Dim pt As Point
For i As Integer = 1 To 1000
    pt = New Point(i, i)
Next

没有构造函数:

Dim pt As Point
For i As Integer = 1 To 1000
    pt.X = i
    pt.Y = i
Next

第一个是更短的,特别是如果构造函数有更多的参数,但在循环中使用它是明智的(让游戏循环每秒发射60次)?或者这两个编译成相同的机器代码?

Han*_*ant 6

定时此代码是不可能的.如果您运行代码的Release版本,您将只获得实际的计时结果.这也踢JIT优化器.并且它足够聪明地看到"pt"实际上并未在任何地方使用,它会删除分配它的所有代码.你会在完全相同的时间结束,但仍然不知道任何事情.

要强制JIT优化器实际发出赋值代码,您必须使用"pt"执行某些操作.喜欢:

Console.WriteLine(pt)
Run Code Online (Sandbox Code Playgroud)

但是现在你将计算Console.WriteLine()需要多长时间,而不是找到关于赋值效率的任何信息.但是,在这种情况下,有价值的是查看生成的机器代码.这是我的x86 JIT编译器在Release版本中启用优化器时生成的注释版本:

00000008  xor         eax,eax                               ; New Point
0000000a  mov         dword ptr [ebp-10h],eax               ; pt.X = 0
0000000d  mov         dword ptr [ebp-0Ch],eax               ; pt.Y = 0
[first fragment]
00000010  mov         esi,1                                 ; i = 1
            pt = New Point(i, i)
00000015  mov         dword ptr [ebp-10h],esi               ; pt.X = i
00000018  mov         dword ptr [ebp-0Ch],esi               ; pt.Y = i
[elided]
00000036  add         esi,1                                 ; i = i + 1
00000039  jo          0000007D                              ; overflow check
0000003b  cmp         esi,3E8h                              ; i <= 1000?
00000041  jle         00000015                              ; Yes: loop
[2nd fragment]
00000043  mov         esi,1                                 ; i = 1
            pt.X = i
00000048  mov         dword ptr [ebp-10h],esi               ; pt.X = i
            pt.Y = i
0000004b  mov         dword ptr [ebp-0Ch],esi               ; pt.Y = i
[elided]
00000069  add         esi,1                                 ; i = i + 1
0000006c  jo          0000007D                              ; overflow check
0000006e  cmp         esi,3E8h                              ; i <= 1000?
00000074  jle         00000048                              : Yes: loop
Run Code Online (Sandbox Code Playgroud)

[elided]部分是Console.WriteLine()调用.仔细查看机器代码说明:

它是完全相同的代码.

JIT编译器很酷.如果您要求它执行相同的工作,它会生成相同的代码.常见的建议是为了清晰而不是效率而编码.虽然这种陈述通常不经过验证,但通常是准确的.