Pregunta

Sólo he encontrado un estático anidada interfaz en nuestra base de código.

class Foo {
    public static interface Bar {
        /* snip */
    }
    /* snip */
}

Nunca he visto esto antes.El desarrollador original está fuera de su alcance.Por lo tanto, tengo que preguntar ASÍ:

¿Cuáles son los semántica detrás de una interfaz estática?Lo que iba a cambiar, si me quito la static?Por qué iba alguien a hacer esto?

¿Fue útil?

Solución

La palabra clave static en el ejemplo de arriba es redundante (anidada interfaz es automáticamente "estática") y puede ser eliminado con ningún efecto sobre la semántica;Se lo recomendaría a ser eliminado.Lo mismo va para el "público" en la interfaz de los métodos y la "final" en la interfaz de campos - los modificadores son redundantes y sólo tiene que añadir el desorden en el código fuente.

De cualquier manera, el desarrollador es simplemente declarar un interfaz llamado Foo.De la barra.No hay más asociación con la clase envolvente, salvo que el código que no puede tener acceso a Foo no será capaz de acceder a Foo.Bar cualquiera.(A partir del código fuente - bytecode o reflexión puede acceder a Foo.Bar incluso si Foo es un paquete-privado!)

Es aceptable estilo para crear un entramado de interfaz de esta manera, si usted espera que sea utilizado sólo desde el exterior de la clase, de modo que usted no cree un nuevo nivel superior nombre.Por ejemplo:

public class Foo {
    public interface Bar {
        void callback();
    }
    public static void registerCallback(Bar bar) {...}
}
// ...elsewhere...
Foo.registerCallback(new Foo.Bar() {
    public void callback() {...}
});

Otros consejos

La pregunta ha sido respondida, pero una buena razón para utilizar un anidada interfaz es si su función está directamente relacionada con la clase en que se encuentra.Un buen ejemplo de esto es un Listener.Si había una clase Foo y usted quería que las demás clases para ser capaz de escuchar para eventos en él, puede declarar una interfaz denominada FooListener, que está bien, pero probablemente sería más claro para declarar una anidados interfaz y tienen las otras clases que implementan Foo.Listener (una clase anidada Foo.Event no es malo, junto con esto).

Miembro de las interfaces son implícitamente estática.El modificador static en su ejemplo, se puede quitar sin cambiar la semántica del código.Ver también la Especificación del Lenguaje Java 8.5.1.Miembro Estático Tipo De Declaraciones

Un interno de la interfaz tiene que ser estático para ser visitada.La interfaz no está asociado con las instancias de la clase, pero con la misma clase, por lo que se accede con Foo.Bar, así:

public class Baz implements Foo.Bar {
   ...
}

En la mayoría de formas, esto no es diferente de una clase interna estática.

Jesse respuesta es cerca, pero creo que hay un mejor código para demostrar por qué su interior, una interfaz puede ser útil.Mirar el código de abajo antes de que usted lea en.Puede usted averiguar por qué el interior de la interfaz es útil?La respuesta es que la clase DoSomethingAlready puede ser instanciado con cualquier clase que implementa a y C;no sólo la clase concreta del Zoológico.Por supuesto, esto puede lograrse incluso si AC no es interior, pero imagino que la concatenación de nombres más largos (no solo a y C), y hacer esto para otras combinaciones (es decir, a y B, la C y la B, etc.) y usted puede fácilmente ver cómo las cosas se salgan de control.Por no hablar de que la gente de revisar el árbol de origen será abrumado por las interfaces que son significativas sólo en una clase.Entonces, para resumir, un interno de la interfaz permite la construcción de tipos personalizados y mejora su encapsulación.

class ConcreteA implements A {
 :
}

class ConcreteB implements B {
 :
}

class ConcreteC implements C {
 :
}

class Zoo implements A, C {
 :
}

class DoSomethingAlready {
  interface AC extends A, C { }

  private final AC ac;

  DoSomethingAlready(AC ac) {
    this.ac = ac;
  }
}

Para responder a su pregunta muy directa, mirar el Mapa.De entrada.

Mapa.La entrada

también esto puede ser útil

Estática Anidada Inerfaces Entrada en el blog

Normalmente veo estática de las clases internas.Estática de las clases internas no puede hacer referencia a la que contienen las clases wherease no estática de las clases.A menos que usted está corriendo en algún paquete de colisiones (que ya es una interfaz denominada Bar en el mismo paquete Foo) creo que me gustaría hacer es propio archivo.También podría ser una decisión de diseño para hacer cumplir la conexión lógica entre los Foo y Bar.Tal vez la intención del autor de la Barra para ser utilizado solamente con Foo (a pesar de una interna estática de la interfaz de no cumplir esto, sólo una conexión lógica)

Si va a cambiar de clase Foo en la interfaz de Foo el "público" de la palabra clave en el ejemplo anterior será también redundantes, porque

interfaz definida dentro de otra interfaz implícitamente público estática.

En 1998, Felipe Wadler sugiere una diferencia entre la estática de interfaces y no estático interfaces.

Por lo que puedo ver, la única diferencia en la toma de una interfaz estática no es que ahora pueden incluir no estático interior clases;así que el cambio no invalida cualquier existentes de Java programas.

Por ejemplo, propuso una solución a la La Expresión Del Problema, que es el desajuste entre la expresión como "¿cuánto puede su idioma express", por un lado, y la expresión "los términos están tratando de representar en su idioma" en el otro lado.

Un ejemplo de la diferencia entre estáticos y no estáticos anidada interfaces puede ser visto en su código de ejemplo:

// This code does NOT compile
class LangF<This extends LangF<This>> {
    interface Visitor<R> {
        public R forNum(int n);
    }

    interface Exp {
        // since Exp is non-static, it can refer to the type bound to This
        public <R> R visit(This.Visitor<R> v);
    }
}

Su propuesta nunca se ha hecho en Java 1.5.0.Por lo tanto, todas las otras respuestas son correctas:no hay ninguna diferencia estáticos y no estáticos anidada interfaces.

En Java, la interfaz estática/clase permite que la interfaz y la clase que se utiliza como una clase de nivel superior, es decir, puede ser declarada por otras clases.Así, usted puede hacer:

class Bob
{
  void FuncA ()
  {
    Foo.Bar foobar;
  }
}

Sin la estática, la de arriba produciría un error de compilación.La ventaja de esto es que usted no necesita un nuevo archivo de código fuente sólo para declarar la interfaz.También visualmente los asociados de la Barra de la interfaz para la clase Foo ya que tienes que escribir Foo.Bar y se supone que la clase Foo hace algo con las instancias de Foo.De la barra.

Una descripción de los tipos de clase en Java.

Estático significa que cualquier parte de la clase del paquete(en el proyecto) puede acceder sin el uso de un puntero.Esto puede ser útil o entorpeciendo dependiendo de la situación.

El ejemplo perfecto de la usefullnes de "estática" métodos de la clase Math.Todos los métodos en Matemáticas son estáticos.Esto significa que usted no tiene que salir de su camino, hacer una nueva instancia, declarar variables y almacenarlos en incluso más variables, solo tiene que introducir sus datos y obtener un resultado.

Estática no siempre es útil.Si usted está haciendo caso-comparación por ejemplo, puede que desee almacenar datos de diferentes formas.Usted no puede crear tres métodos estáticos con firmas idénticas.Se necesitan 3 diferentes instancias, no estático, y, a continuación, usted puede comparar, caus si es estática, los datos no van a cambiar junto con la entrada.

Los métodos estáticos son buenas para un tiempo de devoluciones y cálculos rápidos o fáciles de los datos obtenidos.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top