2009-09-13 17 views
184

En Java, las variables finales estáticas son constantes y la convención es que deben estar en mayúsculas. Sin embargo, he visto que la mayoría de la gente declara los registradores en minúsculas, que aparece como una infracción en PMD.¿Debería declararse un "Registrador final estático" en MAYÚSCULAS?

por ejemplo:

private static final Logger logger = Logger.getLogger(MyClass.class); 

Sólo la búsqueda google o SO para "registrador static final" y verá esto por sí mismo.

¿Deberíamos estar usando LOGGER en su lugar?

+0

PMD o Checkstyle son prematuras ingenuos intentos para aumentar la legibilidad pero pueden causar más daño que beneficio. Un estilo más legible puede cambiar caso por caso según el contexto. Ver Guava, o el JDK src, esos no siguen ninguna plantilla de estilo estricta, pero hechos por profesionales es incuestionable. ejemplo: DelegatedExecutorService @ docjar.com/html/api/java/util/concurrent/Executors.java.html –

Respuesta

228

La referencia del registrador no es una constante, sino una referencia final, y NO debe estar en mayúsculas. Un VALOR constante debe estar en mayúscula.

private static final Logger logger = Logger.getLogger(MyClass.class); 

private static final double MY_CONSTANT = 0.0; 
+31

referencias finales estáticas son constantes si son inmutables. según esta lógica, nunca tendrías cadenas constantes porque cualquier cadena final estática es una referencia. –

+21

Pero java.lang.String ** es ** inmutable y un tipo especial de clase de todos modos (consulte String.intern(), documentación sobre el grupo de Sring, etc.) –

+2

inmutable significa que el estado del objeto no puede cambiar después de la construcción. ver mi publicación a continuación. los madereros no son necesariamente mutables –

5

Personalmente creo que se ve muy grande en mayúsculas. Además, dado que es una clase que no está directamente relacionada con el comportamiento de la clase, no veo un problema importante al usar logger en lugar de LOGGER. Pero si vas a ser estrictamente pedante, entonces usa LOGGER.

2

No necesariamente. Lea esto - Naming Conventions

RESUMEN: Los nombres de las variables constantes de clase declarados y de ANSI constantes deben estar en mayúsculas con palabras separadas por guiones bajos ("_").

+0

Todo lo que el enlace dice es que las 'constantes de clase' usan mayúsculas. No ofrece consejos sobre si un registrador es una constante. De hecho, observe los ejemplos en ese documento - todas las primitivas invariantes, no las referencias a Objetos. – Air

10

Si está utilizando una herramienta automatizada para verificar sus estándares de codificación y viola dichos estándares, entonces o los estándares deben ser reparados. Si está utilizando un estándar externo, arregle el código.

La convención en Sun Java es mayúscula para las constantes estáticas públicas. Obviamente, un registrador no es constante, pero representa una cosa mutable (de lo contrario no habría ningún método de invocación de puntos en él con la esperanza de que algo suceda); no hay un estándar específico para campos finales no constantes.

+8

¿Por qué dice que el registrador no es constante? Parece constante de hecho. El registro se produce es un efecto secundario de llamar a sus métodos, pero no cambia su estado observable. ¿Me he perdido algo? – KLE

+0

Comprueba la API. Tiene un par de métodos add/get. Pero tu razonamiento es defectuoso de todos modos. El registro es observable (de lo contrario, ¿cuál es el punto?) –

+2

Si fuera un StringBuilder en lugar de un registrador, entonces quizás sería más obviamente no constante. Incluso para los registradores, los métodos como Logger.setLevel() mutan el receptor de forma observable. Generalmente mayúsculas es para esas constantes que los idiomas tratan como constantes y se alinearán. –

8

Si busca en Google esto, puede encontrar que, en algunos casos, los registradores no se definen como estáticos finales. Agregue un poco de copiar y pegar rápido a esto, y esto podría explicarlo.

Utilizamos LOGGER en todo nuestro código, y esto corresponde a nuestra convención de nomenclatura (y nuestro CheckStyle está contento con él).


Incluso vamos más allá, aprovechando la estricta convención de nombres en Eclipse. creamos una nueva clase con una plantilla de código de:

// private static final Logger LOGGER = Logger.getLogger(${enclosing_type}.class); 

El registrador está comentada, como en un principio que no lo necesitamos. Pero si lo necesitamos más tarde, simplemente lo descomentamos.

Luego, en el código, usamos plantillas de código que esperan que este registrador esté presente.Ejemplo con la plantilla try-catch:

try { 
     ${cursor} or some other template 
    } catch (Exception t) { 
     LOGGER.error("${methodName} ${method parameters}", t); 
    } 

tenemos algunas más plantillas que lo utilizan.

La estricta convención nos permite ser más productivos y coherentes con las plantillas de código.

+4

La captura de Throwable es una mala práctica, a menos que inicie sesión y la vuelva a lanzar. Recuerde los errores: OutOfMemeoryError, etc. La excepción de evento no es tan segura de ser capturada y manejada por usted mismo en aplicaciones de múltiples hilos. –

+0

Correcto. Cambio el código para reflejar su visión. – KLE

+2

La sintaxis de Eclipse es: Logger.getLogger ($ {enclosing_type} .class); – dogbane

3

Normalmente las constantes están en mayúsculas.

Los madereros, sin embargo, no deberían ser estáticos sino que buscaron cada "nuevo" de la clase que los contenía si usaban la fachada slf4j. Esto evita algunos problemas desagradables del cargador de clases en contenedores notablemente web, además permite que el marco del registrador haga cosas especiales dependiendo del contexto de invocación.

1

Si sus estándares de codificación, si tiene alguno, diga que debería estar en mayúsculas, entonces sí.

No veo ninguna razón estricta para una forma u otra. Creo que depende totalmente de tus gustos personales resp. los estándares de codificación de su empresa.

Por cierto: yo prefiero "Logger" ;-)

4

No se olvide que el PMD respetar un comentario con

// NOPMD 

en ella. Esto hará que PMD omita la línea de sus cheques, esto le permitirá elegir el estilo que desee.

+6

O no use PMD, siempre están equivocados y su código es perfecto – IAdapter

+1

Si siempre tiene que excluir un cheque cada vez, entonces el cheque no tiene sentido. – keiki

+0

No podría estar más de acuerdo, sin embargo ... es útil saber el comentario de exclusión – Fortyrunner

34

desde Java efectiva, 2ª ed.,

La única excepción a las anteriores preocupaciones de reglas “campos constante”, cuyos nombres deben consistir en una o más palabras en mayúsculas separadas por el carácter de subrayado, por ejemplo, VALUES o NEGATIVE_INFINITY. Un campo constante es un campo final estático cuyo valor es inmutable. Si un campo final estático tiene un tipo primitivo o un tipo de referencia inmutable (Elemento 15), entonces es un campo constante. Por ejemplo, las constantes enum son campos constantes. Si un campo final estático tiene un tipo de referencia mutable , aún puede ser un campo constante si el objeto al que se hace referencia es inmutable.

En resumen, constante == static final, más si es una referencia (frente a un tipo simple), inmutabilidad.

Mirando el registrador slf4j, http://www.slf4j.org/api/org/slf4j/Logger.html

es inmutable. Por otro lado, el registrador JUL es mutable. El registrador log4j también es mutable. Entonces, para ser correcto, si está usando log4j o JUL, debería ser "logger", y si está usando slf4j, debería ser LOGGER.

Tenga en cuenta que la página slf4j javadocs vinculada anteriormente tiene un ejemplo donde usan "registrador", no "REGISTRADOR".

Estas son, por supuesto, solo convenciones y no reglas. Si está usando slf4j y quiere usar "logger" porque está acostumbrado a eso de otros frameworks, o si es más fácil de escribir, o de legibilidad, siga adelante.

+2

Basado en este razonamiento, la definición simplista de checkstyle es inapropiada ¿no? – robert

+2

no sé las reglas del estilo de verificación. si se trata simplemente de insistir en que cualquier final estático debe ser en mayúsculas, entonces sí, está mal. –

+4

¿Cómo es exactamente la interfaz 'Logger' ** ** * inmutable *? Solo una 'clase final' (como' String' o 'Integer') puede garantizar la inmutabilidad. Incluso si no puede encontrar ninguna implementación mutable del SLF4J 'Logger', nadie puede evitar que escriba uno usted mismo. –

177

Para añadir más valor a la respuesta de crunchdog, Java Coding Style Guide Los estados esta en el párrafo 3.3 de nomenclatura de campos

Los nombres de los campos que se utiliza como constantes debe ser todo en mayúsculas, subrayado con la separación de palabras. Los siguientes son considerados como constantes:

  1. Todos static final tipos primitivos (Recuerde que todos los campos de interfaz son inherentemente static final).
  2. Todos los tipos de referencia de objeto static final que nunca son seguidos por "." (punto).
  3. Todas las matrices static final que nunca son seguidas por "[" (punto).

Ejemplos:

MIN_VALUE, MAX_BUFFER_SIZE, OPTIONS_FILE_NAME 

Siguiendo esta convención, logger es una referencia static final objeto como se indica en el punto 2, pero debido a que es seguido de "." cada vez que se utiliza, no se puede considerar como una constante y, por lo tanto, debe ser minúscula.

+11

La mejor definición que he visto para esto todavía. El documento vinculado parece haberse movido aquí está la actualización http://www.cs.bilgi.edu.tr/pages/standards_project/java_CodingStyle.pdf#page7 – robert

+11

No obtengo el punto 2. ¿Qué es un ejemplo de un tipo de objeto que nunca es seguido por un punto. Todos los tipos de objeto heredan de 'Objeto' y puede llamar a un método como' .equals' en ellos. – dogbane

+4

Tienes razón. Y al mirar algunas constantes de Java como Boolean.TRUE, Boolean.FALSE, TimeUnit.MINUTES, String.CASE_INSENSITIVE_ORDER o Collections.EMPTY_LIST, pueden ir seguidas de '.' también. – cbliard

25

me gusta tomar de Google en él (Google Java Style)

Cada constante es un campo static final, pero no todos los campos estáticos finales son constantes. Antes de elegir el caso constante, considere si el campo realmente se siente como una constante. Por ejemplo, si cualquiera de los estados observables de esa instancia puede cambiar, es casi seguro que no es una constante. Simplemente, intentar nunca mutar el objeto generalmente no es suficiente.

Ejemplos:

// Constants 
static final int NUMBER = 5; 
static final ImmutableList<String> NAMES = ImmutableList.of("Ed", "Ann"); 
static final Joiner COMMA_JOINER = Joiner.on(','); // because Joiner is immutable 
static final SomeMutableType[] EMPTY_ARRAY = {}; 
enum SomeEnum { ENUM_CONSTANT } 

// Not constants 
static String nonFinal = "non-final"; 
final String nonStatic = "non-static"; 
static final Set<String> mutableCollection = new HashSet<String>(); 
static final ImmutableSet<SomeMutableType> mutableElements = ImmutableSet.of(mutable); 
static final Logger logger = Logger.getLogger(MyClass.getName()); 
static final String[] nonEmptyArray = {"these", "can", "change"}; 
+2

Creo que la primera frase lo resume sucintamente: "Cada constante es un campo final estático, pero no todos los campos finales estáticos son constantes". Es fácil usar el pensamiento mecánico y simplemente tener cada campo estático final en mayúsculas (y he estado haciendo esto hasta ahora), pero esto es para perder la sutileza del lenguaje. – ayahuasca

+0

Según esa cita, se reduce a si el campo "realmente se siente" como una constante. Somos ingenieros, no psiquiatras. –

Cuestiones relacionadas