Doppelte ternäre Integer-Initiierung verursacht einen Nullzeiger

9

Warum ist das in Ordnung, wenn x auf null gesetzt ist:

%Vor%

Und das ist gut, wenn x auf 2 gesetzt ist:

%Vor%

Aber das, wo x auf Null gesetzt werden sollte, verursacht eine java.lang.NullPointerException

%Vor%

Eine Lösung ist zu verwenden:

%Vor%

Aber ich bin nicht sehr klar darüber, warum ein einzelner ternärer Operator gut funktioniert, aber kein Double.

    
MarkL 05.08.2014, 09:42
quelle

1 Antwort

1

(Ich denke immer noch, dass es sich um ein Duplikat handelt, nachdem Sie etwas getan haben Auspacken, aber hey ...)

Erweitern Sie die eine Aussage in zwei:

%Vor%

Das ist nicht genau dasselbe, weil es condition2 ? 2 : null auswertet, auch wenn condition1 falsch ist - Sie könnten es stattdessen mit einem Methodenaufruf modellieren, aber in dem Fall, um den Sie sich sorgen, sowohl condition1 als auch condition2 sind falsch.

Nun könnt ihr fragen, warum wir die Besetzung in int haben. Das liegt an JLS 15.25.2 :

  

Der Typ eines numerischen bedingten Ausdrucks wird wie folgt bestimmt:

     
  • ...
  •   
  • Wenn einer der zweiten und dritten Operanden vom primitiven Typ T ist und der Typ des anderen Operators das Ergebnis der Anwendung der Boxenkonvertierung (§5.1.7) auf T ist, dann ist der Typ des Bedingungsausdrucks T.
  •   
  • ...
  •   

Wir haben int und Integer , also stimmt das für T = int ... überein und das Ergebnis des "inneren" Bedingungsausdrucks wird bei Bedarf unboxed ... und das verursacht ein Problem.

Das Umwandeln von 1 in Integer ändert dies, so dass der Typ des äußeren Ausdrucks auch Integer ist (weil sowohl der zweite als auch der dritte Operand dann den Typ Integer haben), also gibt es kein Unboxing.

Beachten Sie, dass in unserer Erweiterung tmp ein Integer ist, und das ist wirklich der Typ des "inneren" Bedingungsausdrucks, weil der Typ des dritten Operanden der Null-Typ ist, nicht Integer . Sie können es mit nur einem bedingten auch scheitern lassen:

%Vor%

Grundsätzlich wird ein Bedingungsoperator mit zweiten und dritten Operanden vom Typ int bzw. Integer das Unboxing des dritten Operanden durchführen (und das Ergebnis ist int ), aber ein Bedingungsoperator mit zweiten und dritten Operanden vom Typ int und null werden jeweils nicht aufgelöst, und der Ergebnistyp ist Integer .

    
Jon Skeet 06.08.2014 06:52
quelle

Tags und Links