2009-11-19 99 views
9

C#是否爲常量字符串串聯做了任何編譯時優化?如果是這樣,我的代碼如何通過編寫來利用這個優勢?C#編譯時串聯字符串常量

示例:這些在運行時如何比較?

Console.WriteLine("ABC" + "DEF"); 

const string s1 = "ABC"; 
Console.WriteLine(s1 + "DEF"); 

const string s1 = "ABC"; 
const string s2 = s1 + "DEF"; 
Console.WriteLine(s2); 

回答

15

是的,它的確如此。您可以使用ildasm或Reflector來檢查代碼。

static void Main(string[] args) { 
    string s = "A" + "B"; 
    Console.WriteLine(s); 
} 

被翻譯成

.method private hidebysig static void Main(string[] args) cil managed { 
    .entrypoint 
    // Code size  17 (0x11) 
    .maxstack 1 
    .locals init ([0] string s) 
    IL_0000: nop 
    IL_0001: ldstr  "AB" // note that "A" + "B" is concatenated to "AB" 
    IL_0006: stloc.0 
    IL_0007: ldloc.0 
    IL_0008: call  void [mscorlib]System.Console::WriteLine(string) 
    IL_000d: nop 
    IL_000e: br.s  IL_0010 
    IL_0010: ret 
} // end of method Program::Main 

也有一些是更有趣,但有關這種情況發生。如果在程序集中有字符串文字,CLR將只爲程序集中同一文字的所有實例創建一個對象。

這樣:

static void Main(string[] args) { 
    string s = "A" + "B"; 
    string t = "A" + "B"; 
    Console.WriteLine(Object.ReferenceEquals(s, t)); // prints true! 
} 

將打印 「真」 在控制檯上!這種優化稱爲string interning

6

根據Reflector

Console.WriteLine("ABCDEF"); 
Console.WriteLine("ABCDEF"); 
Console.WriteLine("ABCDEF"); 

即使在調試配置。