2015-11-27 12 views
6

Ich habe folgendes Programm, um die Werte hinzuzufügen. Wenn ich Kommen hinzufügen Methodenaufruf in Hauptmethode und Blick in ILDASM.EXE Maxstack Größe ist 2. Und nach dem Auskommentieren maxstack Größe wird 4.Berechnung von maxstack Wert in IL-Code

Warum im Fall der Main-Methode alle Variablen nicht in Stapel als Stapel gehen Größe bleibt nur 2, während im Fall von Add-Methode Aufruf jede Variable in den Stapel geht? Ist dies der Fall, dass die Berechnung der Hauptmethode nacheinander erfolgt, so dass nur zwei Variablen gleichzeitig benötigt werden.

Bitte löschen Sie meine Verwirrung.

static void Main(string[] args) 
{ 
    int x = 2; 
    int y = 3; 
    int a = 4; 
    int b = 5; 
    int c = 6; 

    Console.WriteLine(x + y + a + b + c); 
    Console.WriteLine(Add(10, 20, 30, 40)); 
    Console.ReadLine(); 
} 

static int Add(int x, int y, int z, int a) 
{ 
    return x + y + z + a; 
} 

Antwort

7

Jede Variable Initialisierung:

int x = 2; 

Wird der Wert erfordern auf dem Stapel zu sein: (Stack-Größe: 1, so weit erforderlich)

.locals init ([0] int32 x, 
     [1] int32 y, 
     [2] int32 a, 
     [3] int32 b, 
     [4] int32 c) 
IL_0000: ldc.i4.2 // push 2 to the stack 
IL_0001: stloc.0 // load local variable 0 from stack (x = 2) 

Diese Operationen nacheinander passieren, deshalb Die maximale erforderliche Stapelgröße ist 1, während:

int y = 3; 
int a = 4; 
int b = 5; 
int c = 6; 

Und wenn es dazu kommt:

Console.WriteLine(x + y + a + b + c); 

alle zwei Variablen hinzuzufügen, eine Stapelgröße von 2 erforderlich:

IL_000b: ldloc.0 // copy to stack x, max stack size required is still 1. 
IL_000c: ldloc.1 // copy to stack y, max stack size required is 2 now. 
IL_000d: add  // execute add, will cause the sum x + y to be on stack 
IL_000e: ldloc.2 // copy to stack a 
IL_000f: add  // execute add... (adds a to the result of x + y) 
.... 

Das Differential IL, wenn Sie Kommentar- die Add-Methode ist unten.

Wenn eine Methode aufrufen, müssen Sie die Instanz Bezug auf den Stapel schieben (was bedeutet, wenn die Add-Methode nicht statisch gewesen war, sollte die Instanz Zeiger auf seine Erklärung der Art auf den Stapel geschoben werden)

Dann sollte jedes Argument, das an die Methode übergeben werden soll, ebenfalls auf den Stapel geschoben werden.

Daher ist es die Anzahl der Parameter der Add-Methode in Ihrem Fall, die die maximale Stackgröße definiert. Fügen Sie einen Parameter zu dieser Add-Methode, und Sie werden sehen, dass die maximale Stapelgröße auf 5 erhöhen:

// method is static so no need to push an instance pointer to the stack 
IL_001a: ldc.i4.s 10 // push to stack 
IL_001c: ldc.i4.s 20 // push to stack 
IL_001e: ldc.i4.s 30 // push to stack 
IL_0020: ldc.i4.s 40 // push to stack 
IL_0022: call  int32 Program::Add(int32, 
             int32, 
             int32, 
             int32) 
IL_0027: call  void [mscorlib]System.Console::WriteLine(int32) 
+0

Ich würde leicht die Formulierung an der Spitze zwicken - es ist nicht die * Erklärung *, die Stapelspeicher verwendet, es ist die * Initialisierung *. –

+0

@Damien_The_Unbeliever Danke für die Überprüfung und Korrektur. Es reparieren. –

+0

So ist es wie IL wird Zeile für Zeile nicht generiert. Ich meine zu sagen ist, wie x = 2 einen Stapel Spack dann warum nicht andere Wertangabe nimmt? Ist es so, als ob der Compiler gewusst hätte, dass es nur eine Addition erfordert, so dass 2 Leerzeichen im Stack entstehen. – TBAG