Frage

Bedenken Sie

        int i = 2147483647;
        var n = i + 3;
        i = n;

        Console.WriteLine(i);           // prints -2147483646    (1)
        Console.WriteLine(n);           // prints -2147483646    (2)
        Console.WriteLine(n.GetType()); // prints System.Int32   (3)

Ich bin verwirrt mit dem Folgen

  • (1) Wie könnte int den Wert -2147483646 halten?(int-Bereich = -2.147.483.648 bis 2.147.483.647)
  • (2) Warum gibt dies -2147483648 aus, aber nicht 2147483648 (der Compiler sollte Entscheiden Sie sich für einen besseren Typ als int-Bereich überschreitet)
  • (3) wenn es irgendwo konvertiert wird, warum gibt n.GetType() System.Int32 ?

Edit1: Habe die Korrektur vorgenommen:Jetzt bekommen Sie, was ich bekomme.(das tut mir leid)

var n = i + 1;Zu

var n = i + 3;

Edit2: Noch etwas: Wenn es sich um einen Überlauf handelt, warum wird dann keine Ausnahme ausgelöst?

Zusatz: Wenn der Überlauf auftritt, ist es nicht richtig, den Typ festzulegen

var n

in Aussage var n = i + 3; zu einem anderen Typ entsprechend?


Sie können gerne einen besseren Titel vorschlagen, da dies keinen Sinn ergibt....ich zumindest

Danke

War es hilfreich?

Lösung

Aktualisieren :. Poster richtete seine Frage

1) Dies ist Ausgabe zu erwarten ist, weil Sie 3 bis int.MaxValue hinzugefügt einen Überlauf zu verursachen. In .NET standardmäßig ist dies eine rechtliche Operation in nicht kontrollierten Code umlaufendem auf negative Werte geben, aber wenn Sie einen checked Block um den Code hinzufügen, wird es stattdessen eine OverflowException werfen.

2) Der Typ einer Variablen deklariert mit var bei der Kompilierung nicht Laufzeit bestimmt wird. Es ist eine Regel, dass das Hinzufügen von zwei int32s einem Int32 gibt, keinen UInt32, ein Int64 oder etwas anderes. So auch zur Laufzeit allerdings kann man sehen, dass das Ergebnis ist zu groß für ein Int32, es hat immer noch eine Int32 zurück.

3) Es ist nicht in einem anderen Typ umgewandelt werden.

Andere Tipps

 1)  -2147483646 is bigger than -2,147,483,648
 2) 2147483648 is out of range
 3) int is an alias for Int32

1)
Zunächst einmal wird der Wert in der Variablen ist nicht -2147483646, ist es -2147483648. Führen Sie den Test erneut und überprüfen Sie das Ergebnis.

Es gibt keinen Grund, dass ein int den Wert nicht halten konnte -2147483646. Es ist im Bereich -2147483648..2147483647.

2)
Der Compiler wählt den Datentyp der Variablen der Typ des Ergebnisses des Ausdrucks zu sein. Der Ausdruck gibt einen int-Wert, und auch wenn die Compiler einen größeren Datentyp für die Variable wählen würden, gibt den Ausdruck immer noch ein int und Sie den gleichen Wert wie Ergebnis.

Es ist der Betrieb in dem Ausdruck, dass überläuft, ist es nicht, wenn das Ergebnis der Variablen zugewiesen wird, dass es überläuft.

3)
Es ist nicht konvertiert überall.

  1. Das ist ein Überlauf, Ihre Zahl drehte sich um und wurde negativ
  2. Dies ist nicht die Aufgabe des Compilers, da eine Schleife zur Laufzeit dasselbe verursachen kann
  3. int ist ein Alias ​​oder System.Int32 Sie sind in .Net gleichwertig.

Dies ist wegen der Bit-Darstellung

Sie verwenden Int32, aber das gleiche gilt für char (8 Bit)

das erste Bit hält das Zeichen, dann die folgenden Bits halten die Zahl

so mit 7 Bits können Sie 128 Zahlen repräsentieren 0111 1111

Wenn Sie den 129., 1000 0001 versuchen, erhalten die Vorzeichenbits so eingestellt, dass der Computer denkt, dass sein -1 statt

Arithmic Operationen in .NET nicht den tatsächlichen Typ ändern.
Sie beginnen mit einem (32bit) integer aus und die drei nicht, dass sich ändern.

Deshalb sollten Sie auch eine unerwartete runde Zahl, wenn Sie dies tun:

int a = 2147483647;
double b = a / 4;

oder

int a = 2147483647;
var b = a / 4;

für diese Angelegenheit.

Bearbeiten :
Es gibt keine Ausnahme, weil .NET die Zahl überläuft.
Der Überlauf Ausnahme wird nur bei Zuweisungsoperationen auftreten oder als Mark erklärt, wenn Sie die Bedingungen, die Ausnahme zu erzeugen.

Sie können diese leichter auf uns alle durch Hex-Notation.

Nicht jeder weiß, dass der achte Mersenne-Primzahl 0x7FFFFFFF ist

Just Sayin

Wenn Sie eine Ausnahme ausgelöst werden, schreiben

abc = checked(i+3)

statt. Das wird prüfen für überläuft.

Auch in c #, ist die Standardeinstellung nicht Ausnahmen werfen überläuft. Aber Sie können diese Option irgendwo einschalten Ihr Projekt Eigenschaften.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top