Это C# компилятор умнее компилятора VB.NET ?
если я посмотрю на IL, созданный в Linqpad для двух следующих фрагментов кода, мне интересно, что здесь происходит.
В C#
int i = 42;
результаты в следующем коде IL
IL_0000: ret
тогда как в VB
Dim i As Integer = 42
это
IL_0000: ldc.i4.s 2A
IL_0002: stloc.0
по-видимому, компилятор c# понимает, что значение никогда не используется и поэтому просто ничего не возвращает. В VB.NET фактический код переведен.
это из-за различий в оптимизация компилятора или что-то еще на работе?
обновление: просто чтобы прояснить это - я просто ввожу эту одну строку в LinqPad и смотрю на IL, который он создает (наиболее определенно, запустив соответствующий компилятор). Там нет
2 ответов
убрав вопрос linqpad, я побежал vbc
и csc
С /optimize+ /debug-
по этим программам:
Module f
Public Sub Main()
Dim i As Integer = 42
End Sub
End Module
и
public static class f
{
public static void Main()
{
int i = 42;
}
}
и получил эти результаты CIL от ILDASM:
для VB:
.method public static void Main() cil managed
{
.entrypoint
.custom instance void [mscorlib]System.STAThreadAttribute::.ctor() = ( 01 00 00 00 )
// Code size 4 (0x4)
.maxstack 1
.locals init (int32 V_0)
IL_0000: ldc.i4.s 42
IL_0002: stloc.0
IL_0003: ret
} // end of method f::Main
для C#:
.method public hidebysig static void Main() cil managed
{
.entrypoint
// Code size 1 (0x1)
.maxstack 8
IL_0000: ret
} // end of method f::Main
и да по крайней мере в этом отношении csc
"умнее", чем vbc
. Но я уверен, что дрожание удалит любую разницу при исполнении время.
редактировать
я проверил, и на самом деле выполненный родной код is другой, по крайней мере, в моей системе. Я вставил Console.ReadLine()
вызывает оба, чтобы дать мне возможность прикрепить отладчик, и я получил эти разборки:
из VB:
00000000 sub rsp,38h
00000004 mov dword ptr [rsp+20h],0
0000000c mov rax,7FF000434D8h
00000016 mov eax,dword ptr [rax]
00000018 test eax,eax
0000001a je 0000000000000021
0000001c call FFFFFFFFE45BA230
00000021 mov dword ptr [rsp+20h],2Ah
00000029 call FFFFFFFFE26ABF20
0000002e mov qword ptr [rsp+28h],rax
00000033 nop
00000034 jmp 0000000000000036
00000036 add rsp,38h
0000003a ret
из C#:
00000000 sub rsp,38h
00000004 mov rax,7FF000534D8h
0000000e mov eax,dword ptr [rax]
00000010 test eax,eax
00000012 je 0000000000000019
00000014 call FFFFFFFFE45AA230
00000019 call FFFFFFFFE391BF20
0000001e mov qword ptr [rsp+20h],rax
00000023 nop
00000024 jmp 0000000000000026
00000026 add rsp,38h
0000002a ret
теперь моя сборка практически не существует, но даже я вижу это
mov dword ptr [rsp+20h],2Ah
в от-VB относится к постоянному значению hex 2A
, что составляет 42 десятичных знака. Итак, вот вы идете, это тут выполните больше инструкций в конце.
Я думаю, что в случае C# компилятор выполняет часть выделения памяти и сохраняет значение int за один шаг, а в случае VB оператор DIM-это первый шаг, который просто выделяет память, а затем значение сохраняется на втором шаге. DIM является общим и используется со всеми типами данных, поэтому во всех случаях это может быть что-то вроде одного шага. Мысли?