【发布时间】:2021-04-30 20:11:51
【问题描述】:
我在这里有以下struct:
struct Time
{
public uint SEC;
public uint MIN;
public uint HOUR;
public uint DAY;
}
现在我要计算整个秒数:
static uint F(Time t)
{
uint r = 0;
r += t.DAY * 24 * 60 * 60;
r += t.HOUR * 60 * 60;
r += t.MIN * 60;
r += t.SEC;
return r;
}
这里的问题是C# 为我生成了以下ASM:
Program.F(Time)
L0000: mov eax, [rcx+0xc]
L0003: lea eax, [rax+rax*2]
L0006: shl eax, 3
L0009: imul eax, 0x3c ; it literally multiples one by one,
L000c: imul eax, 0x3c ; although they are int literals.
L000f: imul edx, [rcx+8], 0x3c
L0013: imul edx, 0x3c
L0016: add eax, edx
L0018: imul edx, [rcx+4], 0x3c
L001c: add eax, edx
L001e: add eax, [rcx]
L0020: ret
现在当我像这样手动计算它们时:
static uint G(Time t)
{
uint r = 0;
r += t.DAY * 86400;
r += t.HOUR * 3600;
r += t.MIN * 60;
r += t.SEC;
return r;
}
然后它会生成我正在寻找的结果:
Program.G(Time)
L0000: imul eax, [rcx+0xc], 0x15180
L0007: imul edx, [rcx+8], 0xe10
L000e: add eax, edx
L0010: imul edx, [rcx+4], 0x3c
L0014: add eax, edx
L0016: add eax, [rcx]
L0018: ret
如您所见,它删除了多个IMULs(显然)。这是我正在寻找的ASM 输出。
问题
- 我能否以某种方式提示
C#编译器为我计算整数文字?我想像第一个例子一样保持它,因为它对我来说更干净。这些示例(函数F和G)是否有所不同,或者为什么C#编译器决定不计算它们?
注意事项
- 这是SharpLab 链接。
【问题讨论】:
-
为什么不使用现有的 TimeSpan 结构?这更有可能包含编译器/抖动优化。