4

C# 的 switch 语句可以编译为 CIL switch 指令或 if/else 指令,具体取决于此处提到的语句中的情况。有没有办法强制编译器总是在代码块中生成 if/else 变体?

4

4 回答 4

7

最简单的方法是在代码中使用 if/else。除此之外,这让读者更清楚这就是你想要发生的事情,而不是使用开关。

编辑:好的,所以可读性对你来说并不重要——但基本上如果你想改变编译的代码,源代码就必须改变。您可以使用 Mono 编译器并自己修改它,但我怀疑是否有任何方法可以让 Microsoft 编译器有效地忽略您正在使用 switch 语句。

于 2009-04-18T10:38:01.823 回答
2

您是否尝试过不同的编译器(即 Mono),或者尝试将有问题的类放在单独的程序集中并为它切换到不同的语言?

于 2009-04-18T11:18:16.750 回答
0

你是如何让编译器做到这一点的?我用VS2008做了一个测试:

public static int DoSomething(int i) {
    switch (i) {
        case 1: return 0;
        case 100: return 1;
        case 1000: return 2;
        default: return 3;
    }
}

编译为:

.method public hidebysig static int32 DoSomething(int32 i) cil managed
{
    .maxstack 2
    .locals init (
        [0] int32 CS$1$0000,
        [1] int32 CS$4$0001)
    L_0000: nop 
    L_0001: ldarg.0 
    L_0002: stloc.1 
    L_0003: ldloc.1 
    L_0004: ldc.i4.1 
    L_0005: beq.s L_0016
    L_0007: ldloc.1 
    L_0008: ldc.i4.s 100
    L_000a: beq.s L_001a
    L_000c: ldloc.1 
    L_000d: ldc.i4 0x3e8
    L_0012: beq.s L_001e
    L_0014: br.s L_0022
    L_0016: ldc.i4.0 
    L_0017: stloc.0 
    L_0018: br.s L_0026
    L_001a: ldc.i4.1 
    L_001b: stloc.0 
    L_001c: br.s L_0026
    L_001e: ldc.i4.2 
    L_001f: stloc.0 
    L_0020: br.s L_0026
    L_0022: ldc.i4.3 
    L_0023: stloc.0 
    L_0024: br.s L_0026
    L_0026: ldloc.0 
    L_0027: ret 
}

那里没有切换指令。

也许您应该向 Microsoft 提交错误?

于 2009-04-18T11:49:55.690 回答
0

不,您无法控制 C# 编译器如何发出 CIL 指令。即使可以,由于高级编译器优化,AOT 或 JIT 编译器可能会将 CIL 指令转换为本地机器代码指令,这与您所期望的大不相同。

于 2010-06-07T05:04:15.593 回答