Enquanto pesquisava na Especificação da linguagem Java para responder a esta pergunta , aprendi que
Antes de uma classe ser inicializada, sua superclasse direta deve ser inicializada, mas as interfaces implementadas pela classe não são inicializadas. Da mesma forma, as superinterfaces de uma interface não são inicializadas antes de a interface ser inicializada.
Por curiosidade própria, experimentei e, como era de se esperar, a interface InterfaceType
não foi inicializada.
public class Example {
public static void main(String[] args) throws Exception {
InterfaceType foo = new InterfaceTypeImpl();
foo.method();
}
}
class InterfaceTypeImpl implements InterfaceType {
@Override
public void method() {
System.out.println("implemented method");
}
}
class ClassInitializer {
static {
System.out.println("static initializer");
}
}
interface InterfaceType {
public static final ClassInitializer init = new ClassInitializer();
public void method();
}
Este programa imprime
implemented method
No entanto, se a interface declara um default
método, a inicialização ocorre. Considere a InterfaceType
interface fornecida como
interface InterfaceType {
public static final ClassInitializer init = new ClassInitializer();
public default void method() {
System.out.println("default method");
}
}
então o mesmo programa acima iria imprimir
static initializer
implemented method
Em outras palavras, o static
campo da interface é inicializado ( etapa 9 no Procedimento de inicialização detalhado ) e o static
inicializador do tipo que está sendo inicializado é executado. Isso significa que a interface foi inicializada.
Não consegui encontrar nada no JLS que indicasse que isso deveria acontecer. Não me entenda mal, eu entendo que isso deve acontecer caso a classe de implementação não forneça uma implementação para o método, mas e se fornecer? Esta condição está faltando na Especificação da linguagem Java, eu perdi algo ou estou interpretando incorretamente?
interface
em Java não deveria definir nenhum método concreto. Portanto, estou surpreso que o InterfaceType
código foi compilado.
default
métodos .