2012-04-29 19 views
6

Este es extraño. Tengo el siguiente código:'volátil' en la firma del método?

class A 
{ 
    protected A clone() throws CloneNotSupportedException 
    { 
     return (A) super.clone();  
    } 
} 

cuando de-compilado su código de bytes a través de 'showmycode.com', me mostraron el siguiente código:

class A 
{ 

    A() 
    { 
    } 

    protected A clone() 
    throws clonenotsupportedexception 
    { 
     return (A)super.clone(); 
    } 

    protected volatile object clone() 
    throws clonenotsupportedexception 
    { 
     return clone(); 
    } 
} 

¿Qué significa para un tipo de retorno del método ser volátil en el segundo método 'clon'? (Este código fue compilado a través del compilador JDK 1.6 predeterminado de Eclipse).

+5

Creo que esta respuesta se aplica aquí: http://stackoverflow.com/questions/6651867/why-make-a-method-volatile-in-java –

+0

THX @bunting. Podrías plmenciónalo en tu respuesta para poder aceptarlo? – shrini1000

Respuesta

4

La máscara de modificación para campos y métodos es similar pero no exactamente igual. El Decompiler es muy probable que tenga el método toString aquí

http://grepcode.com/file/repository.grepcode.com/java/root/jdk/openjdk/6-b14/java/lang/reflect/Modifier.java

pero lo que no hace es manejar todos los bits

// Bits not (yet) exposed in the public API either because they 
// have different meanings for fields and methods and there is no 
// way to distinguish between the two in this class, or because 
// they are not Java programming language keywords 

Lo que su no maneja los bits es lo que puede significar synthetic y bridge que identifican el código generado por el compilador.

Si volatile significa algo aquí, podría significar que no se elimina el método aunque no haga nada.

+0

No es un error. Parece que los métodos generados que se requieren para los genéricos y se insertan silenciosamente en las clases compiladas, se marcan como "volátiles", incluso si este no es su significado exacto. – Panayotis

1

Es un error en su decompilador.

volatile es solo un modificador válido para un campo.

Te recomiendo que leas this aricle.

+1

Entiendo eso. Mi pregunta es: ¿por qué el código descompilado tiene 'volátil' en la firma del método * cuando el código original no *? Parece que solo los métodos de puente muestran este síntoma. – shrini1000

+0

@ shrini1000, intente compilar el código descompilado; verá que no compila. En Java no se puede marcar el método con el modificador volátil. Supongo que es un error de la herramienta que usas para descompilar. – aviad

4

No significa nada. Es un error en el decompilador. Fin de la historia.

(El error probablemente se relaciona con el hecho de que ciertos marcadores usados ​​en el formato de archivo de clase están "sobrecargados", lo que significa cosas diferentes en el contexto de una clase, campo o método. También recuerdo vagamente que algunos "nuevos usos" en revisiones de especificaciones de JVM recientes.)

8

Esta respuesta ya se ha cubierto en la pregunta Why make a method volatile in java? Pero aquí hay más información.

Cuando sobrecarga métodos (posiblemente solo métodos genéricos en la superclase), el método se marca como "bridge method". De java.lang.reflect.Modifier:

static final int BRIDGE = 0x00000040; 

Por desgracia, este es el mismo bit que se utiliza para marcar campos como volatile:

public static final int VOLATILE   = 0x00000040; 

Si imprime los modificadores de ese método que va a ver algo como:

public volatile 

Esto es una limitación en el método Modifiers.toString(int) que no sabe si se trata de un campo o método.

public static String toString(int mod) { 
    StringBuffer sb = new StringBuffer(); 
    ... 
    if ((mod & VOLATILE) != 0) sb.append("volatile "); 
    // no mention of BRIDGE here 
    ... 
    return sb.toString().substring(0, len-1); 
} 
Cuestiones relacionadas