La conversión ascendente está permitida en Java, sin embargo, la reducción genera un error de compilación.
El error de compilación se puede eliminar agregando un reparto, pero de todos modos se rompería en el tiempo de ejecución.
En este caso, ¿por qué Java permite el downcasting si no se puede ejecutar en tiempo de ejecución?
¿Hay algún uso práctico para este concepto?
public class demo {
public static void main(String a[]) {
B b = (B) new A(); // compiles with the cast,
// but runtime exception - java.lang.ClassCastException
}
}
class A {
public void draw() {
System.out.println("1");
}
public void draw1() {
System.out.println("2");
}
}
class B extends A {
public void draw() {
System.out.println("3");
}
public void draw2() {
System.out.println("4");
}
}
Respuestas:
Se permite el downcasting cuando existe la posibilidad de que tenga éxito en tiempo de ejecución:
En algunos casos esto no tendrá éxito:
Cuando un lanzamiento (como este último) falla en tiempo de ejecución
ClassCastException
, se lanzará un .En otros casos funcionará:
Tenga en cuenta que algunos lanzamientos se rechazarán en el momento de la compilación, porque nunca tendrán éxito en absoluto:
fuente
Object o = new Object(); String s = (String) o;
Me está funcionando bien ...: O ¿Cómo?Usando su ejemplo, podría hacer:
fuente
Creo que esto se aplica a todos los idiomas estáticamente escritos:
La tipología dice efectivamente: suponga que esta es una referencia a la clase de conversión y úsela como tal. Ahora, digamos que o es realmente un número entero, suponiendo que se trata de una cadena no tiene sentido y dará resultados inesperados, por lo tanto, debe haber una verificación de tiempo de ejecución y una excepción para notificar al entorno de tiempo de ejecución que algo está mal.
En el uso práctico, puede escribir código trabajando en una clase más general, pero convertirlo en una subclase si sabe qué subclase es y necesita tratarlo como tal. Un ejemplo típico es anular Object.equals (). Supongamos que tenemos una clase para automóvil:
fuente
Todos podemos ver que el código que proporcionó no funcionará en tiempo de ejecución. Eso es porque sabemos que la expresión nunca
new A()
puede ser un objeto de tipo .B
Pero no es así como lo ve el compilador. Para cuando el compilador verifica si el reparto está permitido, solo ve esto:
Y como otros han demostrado, ese tipo de elenco es perfectamente legal. La expresión de la derecha podría muy bien evaluar a un objeto de tipo
B
. El compilador ve esoA
yB
tiene una relación de subtipo, por lo que con la vista de "expresión" del código, el reparto podría funcionar.El compilador no considera el caso especial cuando sabe exactamente qué tipo de objeto
expression_of_type_A
realmente tendrá. Simplemente ve el tipo estático comoA
y considera que el tipo dinámico podría serA
o cualquier descendienteA
, incluidoB
.fuente
Creo que esto se debe a que no hay forma de que el compilador sepa en tiempo de compilación si el elenco tendrá éxito o no. Para su ejemplo, es simple ver que el elenco fallará, pero hay otros momentos en que no está tan claro.
Por ejemplo, imagine que todos los tipos B, C y D extienden el tipo A, y luego un método
public A getSomeA()
devuelve una instancia de B, C o D dependiendo de un número generado aleatoriamente. El compilador no puede saber qué tipo de tiempo de ejecución exacto devolverá este método, por lo que si luego envía los resultadosB
, no hay forma de saber si el lanzamiento tendrá éxito (o fallará). Por lo tanto, el compilador debe asumir que los lanzamientos tendrán éxito.fuente
@ Cartel original: vea los comentarios en línea.
fuente
Downcast funciona en el caso cuando se trata de un objeto upcasted. Upcasting:
Así que ahora esta
objValue
variable siempre se puede descartarint
porque el objeto que se echó es unInteger
,pero debido a que
objValue
es un Objeto no se puede lanzarString
porqueint
no se puede lanzarString
.fuente
Downcasting es muy útil en el siguiente fragmento de código. Lo uso todo el tiempo. Por lo tanto, probar que el downcasting es útil.
Almaceno String en la lista vinculada. Cuando recupero los elementos de la Lista vinculada, se devuelven los Objetos. Para acceder a los elementos como cadenas (o cualquier otro objeto de clase), el downcasting me ayuda.
Java nos permite compilar código abatido confiando en que estamos haciendo lo incorrecto. Aún así, si los humanos cometen un error, se detecta en tiempo de ejecución.
fuente
void*
punteros en C ++. No me parece una buena idea en absoluto.Considere el siguiente ejemplo
aquí creamos el objeto de la subclase Bone y lo asignamos a la referencia de superclase AOne y ahora la referencia de superclase no conoce el método método2 en la subclase, es decir, Bone durante el tiempo de compilación. Por lo tanto, debemos reducir esta referencia de superclase a la referencia de subclase la referencia resultante puede conocer la presencia de métodos en la subclase, es decir, Bone
fuente
Para hacer downcasting en Java y evitar excepciones en tiempo de ejecución, tome una referencia del siguiente código:
Aquí, Animal es la clase principal y Perro es la clase secundaria.
instanceof es una palabra clave que se usa para verificar si una variable de referencia contiene un tipo dado de referencia de objeto o no.
fuente
La transformación de conversión de objetos no es posible. Solamente
es posible
fuente