2011-12-22 27 views
5

En lenguaje de programación de Java, ensanchar y boxear no funciona, pero ¿cómo funciona en el siguiente ejemplo?Ampliación y boxeo con java

final short myshort = 10; 
Integer iRef5 = myshort; 

¿Por qué funciona esto? ¿No es esto lo mismo que ensanchar y luego boxear?

Pero si escribo el siguiente código:

final int myint = 10; 
Long myLONG = myint; 

por qué no funciona?

+1

¿Qué compilador usa para llegar a sus resultados? Parece que funciona con el compilador de Eclipse, pero no con el compilador 'javac' –

+0

No puedo hacer que ninguno de ellos funcione (usando ideone.com). –

Respuesta

1

con Java 7, tanto los ejemplos no están trabajando. Obtendrá debajo de la excepción:

Type mismatch: cannot convert from short to Integer 
Type mismatch: cannot convert from int to Long 

Porque el problema no es debido al boxeo sino a causa de la conversión.

1

Ninguno funciona como está (usando javac 1.6.0_26 de Sun/Oracle, en Linux). Véase también here.

b.java:4: incompatible types 
found : short 
required: java.lang.Integer 
     Integer iRef5 = myshort; 
         ^
b.java:7: incompatible types 
found : int 
required: java.lang.Long 
     Long myLONG = myint; 
        ^
2 errors 
+0

El primer ejemplo funciona para mí en Java 6 (compilador de Eclipse) ...? –

+0

¿Podría ser que se comporten de manera diferente? Estoy usando el compilador de Sun, mira [aquí] (http://ideone.com/6W7xi) – Vlad

+0

Podría ser. He visto diferencias en el pasado, pero no con casos tan simples, vea [esta pregunta, por ejemplo] (http: // stackoverflow.com/questions/5361513/reference-is-ambiguous-with-generics) –

1

Puede ensanchar o encajonar, pero no puede hacer ambas cosas.

Usted puede hacer

final int myint = 10; 
Long myLONG = (long) myint; 
+0

Tiene que haber una sutileza con el casting/promoción implícito de 'short' a' int' aplicado al primer ejemplo, antes del auto-boxing. ¿Sabes por qué regla? –

+0

Puede boxear y luego ampliar –

+0

'Objeto myLONG = 10L;' es perfectamente válido –

0

Estas son las reglas de la promoción que se aplican a las expresiones en Java

todo bytes y cortos valores son promovidos a int

Si un operando es largo, toda la expresión se promovido a largo

Si un operando es flotador, toda la expresión es ascendido a flotador

Si un operando es doble, toda la expresión es ascendido a doble

valor Por lo tanto corta es promovido a int. Esto no se está ampliando. "La conversión de un subtipo a uno de sus supertipos se llama ampliación"


0

Puede box continuación wide pero no se puede widen y luego box

Así

final short myshort = 10; 
Integer iRef5 = myshort; 

es equivalente a

final short myshort = 10; 
Integer iRef5 = 10; 

que es perfectamente válido

pero

Long myLONG = 10;//this won't compile , 

Pero tratar con 10L será por lo que se casilla, entonces puede tener que objetar demasiado decir Object o = 10L;


Véase también

+0

¿Está seguro de que el primer ejemplo es perfectamente válido? Parece haber una diferencia entre el compilador Eclipse y el compilador javac. ¿Cuál es la correcta? –

2

siguiendo lo que otros han dicho, puedo confirmar que puedo compilar el primer ejemplo con el compilador de Eclipse, pero no el segundo. Con el compilador javac, ambos no se compilan, como dice Vlad

¡Esto parece ser un error en cualquiera de los compiladores! Consultemos el JLS para averiguar, ¿cuál es la derecha :-)

+0

El compilador de eclipse tiene algunos errores conocidos y muy sutiles que no están presentes en 'javac'. Recuerdo otro con el uso de genéricos que nos dejó preguntándonos por un tiempo. – lsoliveira

+0

@lsoliveira: Puede tener razón, vea también [este número] (http://stackoverflow.com/questions/5361513/reference-is-ambiguous-with-generics). Sin embargo, también sucedió al revés en el pasado. –

+0

Supongo que siempre hay una posibilidad (aunque nunca me pasó a mí ni a nadie que yo sepa :-)). – lsoliveira

1

Vamos a examinar lo que estamos tratando de hacer con detalle:

final short myshort = 10; 
Integer iRef5 = myshort; 

El compilador tratará de la primera caja que corta en un objeto, para que luego pueda realizar la asignación (no puede ampliarse directamente, ya que se trata de diferentes tipos: un objeto y una primitiva).

En resumen, esto es equivalente a:

final short myshort = 10; 
final Short box = new Short(myshort); // boxing: so that objects are assignable. 
Integer iRef5 = box; // widening: this fails as Integer is not a superclass of Short 

El mismo razonamiento se puede aplicar a su segundo ejemplo (que también falla), como es visible here. Si su compilador no se queja en el primero, entonces puede haber un error con el compilador, porque esto es lo que se define en el JLS. Consulte el conjunto completo de reglas para la conversión/promoción en JLS here.

Cuestiones relacionadas