¿Cuál es la mejor manera de implementar constantes en Java? [cerrado]


He visto ejemplos como este:

public class MaxSeconds {
   public static final int MAX_SECONDS = 25;
}

Y supone que podría tener una clase de Constantes para envolver constantes, declarándolas estáticas finales. No conozco prácticamente ningún Java y me pregunto si esta es la mejor manera de crear constantes.

Author: jjnguy, 2008-09-15

28 answers

Eso es perfectamente aceptable, probablemente incluso el estándar.

(public/private) static final TYPE NAME = VALUE;

Donde TYPE es el tipo, NAME es el nombre en mayúsculas con espacios, y VALUE es el valor constante;

Recomiendo encarecidamente NO poner sus constantes en sus propias clases o interfaces.

Como nota al margen: Las variables que se declaran finales y son mutables todavía se pueden cambiar; sin embargo, la variable nunca puede apuntar a un objeto diferente.

Para ejemplo:

public static final Point ORIGIN = new Point(0,0);

public static void main(String[] args){

    ORIGIN.x = 3;

}

Que es legal y ORIGIN entonces sería un punto en (3, 0).

 403
Author: jjnguy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-10-22 17:31:54

Desaconsejaría tener una sola clase de constantes. Puede parecer una buena idea en ese momento, pero cuando los desarrolladores se niegan a documentar constantes y la clase crece para abarcar más de 500 constantes que no están relacionadas entre sí en absoluto (están relacionadas con aspectos completamente diferentes de la aplicación), esto generalmente se convierte en el archivo de constantes siendo completamente ilegible. Lugar:

  • Si tiene acceso a Java 5+, use enumeraciones para definir su constantes para un área de aplicación. Todas las partes del área de aplicación deben referirse a enumeraciones, no a valores constantes, para estas constantes. Puede declarar una enumeración similar a como declara una clase. Las enumeraciones son quizás la característica más (y, posiblemente, la única) útil de Java 5+.
  • Si tiene constantes que solo son válidas para una clase en particular o una de sus subclases, declararlas como protegidas o públicas y colocarlas en la clase superior de la jerarquía. De esta manera, las subclases pueden acceda a estos valores constantes (y si otras clases acceden a ellos a través de public, las constantes no solo son válidas para una clase en particular...lo que significa que las clases externas que usan esta constante pueden estar demasiado acopladas a la clase que contiene la constante)
  • Si tiene una interfaz con comportamiento definido, pero los valores devueltos o los valores de argumento deben ser particulares, es perfectamente aceptable definir constantes en esa interfaz para que otros implementadores tengan acceso a ellas. Sin embargo, evite crear una interfaz solo para mantener constantes: puede llegar a ser tan malo como una clase creada solo para mantener constantes.
 235
Author: MetroidFan2002,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 19:51:44

Es una MALA PRÁCTICA usar interfaces solo para mantener constantes (llamado patrón de interfaz constante por Josh Bloch). Esto es lo que Josh aconseja:

Si las constantes están fuertemente ligadas a una clase o interfaz existente, usted debe añadirlos a la clase o interfaz. Por ejemplo, todos los clases primitivas numéricas en caja, como Integer y Double, exportar Constantes MIN_VALUE y MAX_VALUE. Si las constantes se ven mejor como miembros de an tipo enumerado, usted debe exportarlos con un enum tipo. De lo contrario, debe exportar el constantes con un no instanciable clase de utilidad.

Ejemplo:

// Constant utility class
package com.effectivejava.science;
public class PhysicalConstants {
    private PhysicalConstants() { }  // Prevents instantiation

    public static final double AVOGADROS_NUMBER   = 6.02214199e23;
    public static final double BOLTZMANN_CONSTANT = 1.3806503e-23;
    public static final double ELECTRON_MASS      = 9.10938188e-31;
}

Acerca de la convención de nomenclatura:

Por convención, tales campos tienen nombres que consten de letras mayúsculas, con palabras separadas por guiones bajos. Es crítico que estos campos contengan valores primitivos o referencias a objetos inmutables.

 120
Author: Marcio Aguiar,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-02-02 00:20:07

En Java Efectivo (2a edición), se recomienda usar enumeraciones en lugar de ints estáticos para las constantes.

Hay una buena valoración crítica de enums en Java aquí: http://java.sun.com/j2se/1.5.0/docs/guide/language/enums.html

Tenga en cuenta que al final de ese artículo la pregunta planteada es:

Entonces, ¿cuándo debe usar enumeraciones?

Con una respuesta de:

Cada vez que necesite un conjunto fijo de constantes

 36
Author: shelfoo,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-07-29 07:16:36

Simplemente evite usar una interfaz:

public interface MyConstants {
    String CONSTANT_ONE = "foo";
}

public class NeddsConstant implements MyConstants {

}

Es tentador, pero viola la encapsulación y difumina la distinción de las definiciones de clase.

 21
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 19:45:33

Utilizo el siguiente enfoque:

public final class Constants {
  public final class File {
    public static final int MIN_ROWS = 1;
    public static final int MAX_ROWS = 1000;

    private File() {}
  }

  public final class DB {
    public static final String name = "oups";

    public final class Connection {
      public static final String URL = "jdbc:tra-ta-ta";
      public static final String USER = "testUser";
      public static final String PASSWORD = "testPassword";

      private Connection() {}
    }

    private DB() {}
  }

  private Constants() {}
}

Que, por ejemplo, uso Constants.DB.Connection.URL para obtener constante. Se ve más "objeto orientado" en cuanto a mí.

 19
Author: albus.ua,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-07-12 16:35:59

Crear constantes finales estáticas en una clase separada puede meterte en problemas. El compilador Java realmente optimizará esto y colocará el valor real de la constante en cualquier clase que haga referencia a ella.

Si más tarde cambia la clase 'Constantes' y no hace una recompilación difícil en otras clases que hacen referencia a esa clase, terminará con una combinación de valores antiguos y nuevos que se utilizan.

En lugar de pensar en ellas como constantes, piense en ellas como configuración parámetros y crear una clase para gestionarlos. Haga que los valores no sean finales, e incluso considere el uso de getters. En el futuro, a medida que determine que algunos de estos parámetros en realidad deben ser configurables por el usuario o el administrador, será mucho más fácil de hacer.

 17
Author: Kevin Day,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-16 03:36:05

El error número uno que puede cometer es crear una clase accesible globalmente llamada con un nombre genérico, como Constantes. Esto simplemente se llena de basura y se pierde toda la capacidad de averiguar qué parte de su sistema utiliza estas constantes.

En su lugar, las constantes deben ir a la clase que las "posee". ¿Tienes una constante llamada TIMEOUT? Probablemente debería ir a tu clase Communications() o Connection (). MAX_BAD_LOGINS_PER_HOUR? Entra en User(). Y así sucesivamente y y así sucesivamente.

El otro uso posible es Java .archivos de propiedades cuando las "constantes" se pueden definir en tiempo de ejecución, pero no se pueden cambiar fácilmente por el usuario. Puedes empacar esto en tu casa .los frascos y se hace referencia a ellos con la Clase resourceLoader.

 13
Author: Yann Ramin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 20:26:15

Ese es el camino correcto.

Generalmente las constantes son no mantenidas en clases "Constantes" separadas porque no son detectables. Si la constante es relevante para la clase actual, mantenerlas allí ayuda al siguiente desarrollador.

 6
Author: Jason Cohen,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 19:44:16

¿Qué hay de una enumeración?

 5
Author: Sébastien D.,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 19:50:34

Prefiero usar getters en lugar de constantes. Esos getters pueden devolver valores constantes, por ejemplo public int getMaxConnections() {return 10;}, pero cualquier cosa que necesite la constante pasará por un getter.

Un beneficio es que si su programa supera la constante find encuentra que necesita ser configurable can puede cambiar cómo el getter devuelve la constante.

El otro beneficio es que para modificar la constante no tienes que recompilar todo lo que la usa. Cuando hace referencia a una estática campo final, el valor de esa constante se compila en cualquier bytecode que hace referencia a ella.

 5
Author: big_peanut_horse,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-16 01:30:29

Estoy de acuerdo en que el uso de una interfaz no es el camino a seguir. Para evitar este patrón tiene incluso su propio elemento (#18) en Bloch s Eficaz Java.

Un argumento que Bloch hace contra el patrón de interfaz constante es que el uso de constantes es un detalle de implementación, pero implementar una interfaz para usarlas expone ese detalle de implementación en su API exportada.

El patrón public|private static final TYPE NAME = VALUE; es una buena manera de declarar una constante. Personalmente, creo que es mejor evitar hacer un clase separada para albergar todas tus constantes, pero nunca he visto una razón para no hacer esto, aparte de la preferencia personal y el estilo.

Si sus constantes pueden ser bien modeladas como una enumeración, considere la estructura enum disponible en 1.5 o posterior.

Si está utilizando una versión anterior a la 1.5, todavía puede realizar enumeraciones seguras de tipo mediante el uso de clases Java normales. (Ver este sitio para más sobre eso).

 5
Author: Rob Dickerson,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-07-29 07:22:50

Basado en los comentarios anteriores, creo que este es un buen enfoque para cambiar la clase de constante global anticuada (que tiene variables finales estáticas públicas) a su equivalente enum de una manera como esta:

public class Constants {

    private Constants() {
        throw new AssertionError();
    }

    public interface ConstantType {}

    public enum StringConstant implements ConstantType {
        DB_HOST("localhost");
        // other String constants come here

        private String value;
        private StringConstant(String value) {
            this.value = value;
        }
        public String value() {
            return value;
        }
    }

    public enum IntConstant implements ConstantType {
        DB_PORT(3128), 
        MAX_PAGE_SIZE(100);
        // other int constants come here

        private int value;
        private IntConstant(int value) {
            this.value = value;
        }
        public int value() {
            return value;
        }
    }

    public enum SimpleConstant implements ConstantType {
        STATE_INIT,
        STATE_START,
        STATE_END;
    }

}

Entonces puedo referirlos como:

Constants.StringConstant.DB_HOST
 4
Author: Lorand Bendig,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-06-27 09:39:36

Un buen diseño orientado a objetos no debería necesitar muchas constantes disponibles públicamente. La mayoría de las constantes deben ser encapsuladas en la clase que las necesita para hacer su trabajo.

 3
Author: Bradley Harris,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-01-28 21:12:28

Hay una cierta cantidad de opinión para responder a esto. Para empezar, las constantes en java generalmente se declaran públicas, estáticas y finales. A continuación se presentan las razones:

public, so that they are accessible from everywhere
static, so that they can be accessed without any instance. Since they are constants it
  makes little sense to duplicate them for every object.
final, since they should not be allowed to change

Nunca usaría una interfaz para un accessor/objeto de CONSTANTES simplemente porque generalmente se espera que las interfaces se implementen. ¿No se vería esto divertido:

String myConstant = IMyInterface.CONSTANTX;

En su lugar, elegiría entre algunas formas diferentes, basadas en algunas pequeñas compensaciones, y por lo tanto depende de lo que necesidad:

1.  Use a regular enum with a default/private constructor. Most people would define 
     constants this way, IMHO.
  - drawback: cannot effectively Javadoc each constant member
  - advantage: var members are implicitly public, static, and final
  - advantage: type-safe
  - provides "a limited constructor" in a special way that only takes args which match
     predefined 'public static final' keys, thus limiting what you can pass to the
     constructor

2.  Use a altered enum WITHOUT a constructor, having all variables defined with 
     prefixed 'public static final' .
  - looks funny just having a floating semi-colon in the code
  - advantage: you can JavaDoc each variable with an explanation
  - drawback: you still have to put explicit 'public static final' before each variable
  - drawback: not type-safe
  - no 'limited constructor'

3.  Use a Class with a private constructor:
  - advantage: you can JavaDoc each variable with an explanation
  - drawback: you have to put explicit 'public static final' before each variable
  - you have the option of having a constructor to create an instance
     of the class if you want to provide additional functions related
     to your constants 
     (or just keep the constructor private)
  - drawback: not type-safe

4. Using interface:
  - advantage: you can JavaDoc each variable with an explanation
  - advantage: var members are implicitly 'public static final'
  - you are able to define default interface methods if you want to provide additional
     functions related to your constants (only if you implement the interface)
  - drawback: not type-safe
 2
Author: djangofan,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-01-08 22:06:32

¿Cuál es la mejor manera de implementar constantes en Java?

Un enfoque que realmente deberíamos evitar : el uso de interfaces para definir constantes.

Crear una interfaz específicamente para declarar constantes es realmente lo peor : frustra la razón por la que se diseñaron las interfaces : definir el contrato de método(s).

Incluso si ya existe una interfaz para abordar una necesidad específica, declarar las constantes en ellas hace que realmente no las constantes sense as no deben formar parte de la API y del contrato proporcionado a las clases cliente.


Para simplificar, tenemos aproximadamente 4 enfoques válidos .

Con static final String/Integer campo :

  • 1) usando una clase que declara constantes dentro pero no solo.
  • 1 variante) creando una clase dedicada solo a declarar constantes.

Con Java 5 enum:

  • 2) declarar la enumeración en una clase de propósito relacionada (así como una anidada clase).
  • 2 variant) creando la enumeración como una clase independiente (así definida en su propio archivo de clase).

TLDR: ¿Cuál es la mejor manera y dónde localizar las constantes ?

En la mayoría de los casos, el camino de enumeración es probablemente más fino que el camino static final String/Integer y personalmente creo que el camino static final String/Integer debe usarse solo si tenemos buenas razones para no usar enumeraciones.
Y sobre dónde debemos declarar los valores constantes, la idea es buscar si hay una sola clase existente que posee una cohesión funcional específica y fuerte con valores constantes. Si encontramos tal clase, deberíamos usarla como las constantes holder . De lo contrario, la constante no debería estar asociada a ninguna clase en particular.


static final String/ static final Integer versus enum

El uso de Enums es realmente una manera de considerar fuertemente.
Los enums tienen una gran ventaja sobre String o Integer el campo constante.
Establecieron un fuerte restricción de compilación. Si define un método que toma la enumeración como parámetro, solo puede pasar un valor de enumeración definido en la clase enumeración (o null).
Con String y Integer puede sustituirlos con cualquier valor de tipo compatible y la compilación estará bien incluso si el valor no es una constante definida en el static final String/ static final Integer fields.

Por ejemplo, debajo de dos constantes definidas en una clase como static final String campos:

public class MyClass{

   public static final String ONE_CONSTANT = "value";
   public static final String ANOTHER_CONSTANT = "other value";
   . . .
}

Aquí un método que espera tener uno de estos constantes como parámetro :

public void process(String constantExpected){
    ...    
}

Puedes invocarlo de esta manera :{[36]]}

process(MyClass.ONE_CONSTANT);

O

process(MyClass.ANOTHER_CONSTANT);

Pero ninguna restricción de compilación le impide invocarlo de esta manera :

process("a not defined constant value");

Tendría el error solo en tiempo de ejecución y solo si realiza una verificación del valor transmitido.

Con enum, las comprobaciones no son necesarias ya que el cliente solo puede pasar un valor enum en un parámetro enum.

Por ejemplo, aquí dos valores definidos en una enumeración clase (tan constante fuera de la caja):

public enum MyEnum {

    ONE_CONSTANT("value"), ANOTHER_CONSTANT(" another value");

    private String value;

    MyEnum(String value) {
       this.value = value;
    }
         ...
}

Aquí un método que espera tener uno de estos valores de enumeración como parámetro :

public void process(MyEnum myEnum){
    ...    
}

Puedes invocarlo de esta manera :{[36]]}

process(MyEnum.ONE_CONSTANT);

O

process(MyEnum.ANOTHER_CONSTANT);

Pero la compilación nunca te permitirá invocarla de esta manera :{[36]]}

process("a not defined constant value");

¿Dónde debemos declarar las constantes ?

Si su aplicación contiene una única clase existente que posee una cohesión funcional específica y fuerte con los valores constantes, el 1) y el 2) aparecen más intuitivos.
Generalmente, facilita el uso de las constantes si éstas se declaran en la clase principal que las manipula o que tiene un nombre muy natural para adivinar que la encontraremos dentro.

Por ejemplo, en la biblioteca JDK, los valores constantes exponenciales y pi se declaran en una clase que no solo declara declaraciones constantes (java.lang.Math).

   public final class Math {
          ...
       public static final double E = 2.7182818284590452354;
       public static final double PI = 3.14159265358979323846;
         ...
   }

Los clientes que utilizan funciones matemáticas se basan a menudo en la Math clase. Por lo tanto, pueden encontrar constantes con bastante facilidad y también pueden recordar dónde E y PI se definen de una manera muy natural.

Si su aplicación no contiene una clase existente que tenga una cohesión funcional muy específica y fuerte con los valores constantes, las formas 1 variant) y 2 variant) parecen más intuitivas.
Generalmente, no facilita el uso de las constantes si éstas son declaradas en una clase que las manipula mientras tenemos también 3 o 4 otras clases que las manipulan tanto como y ninguna de estas clases parece ser más natural que otras para alojar valores constantes.
Aquí, definir una clase personalizada para contener solo valores constantes tiene sentido.
Por ejemplo, en la biblioteca JDK, la enumeración java.util.concurrent.TimeUnit no se declara en una clase específica, ya que no hay realmente una y solo una clase específica JDK que aparece como la más intuitiva para mantenerla :

public enum TimeUnit {
    NANOSECONDS {
      .....
    },
    MICROSECONDS {
      .....
    },
    MILLISECONDS {
      .....
    },
    SECONDS {
      .....
    },
      .....
}      

Muchas clases declaradas en java.util.concurrent las usan : BlockingQueue, ArrayBlockingQueue<E>, CompletableFuture, ExecutorService , ... y realmente ninguno de ellos parece más apropiado para sostener la enumeración.

 2
Author: davidxxx,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-12-29 12:41:07

Una constante, de cualquier tipo, se puede declarar creando una propiedad inmutable dentro de una clase (que es una variable miembro con el modificador final). Normalmente también se proporcionan los modificadores static y public.

public class OfficePrinter {
    public static final String STATE = "Ready";  
}

Hay numerosas aplicaciones donde el valor de una constante indica una selección de una n-tupla (por ejemplo, enumeración) de opciones. En nuestro ejemplo, podemos elegir definir un Tipo Enumerado que restringirá los posibles valores asignados (es decir, mejorado seguridad de tipo):

public class OfficePrinter {
    public enum PrinterState { Ready, PCLoadLetter, OutOfToner, Offline };
    public static final PrinterState STATE = PrinterState.Ready;
}
 1
Author: Ryan Delucchi,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 21:17:31

Una sola clase de constantes genéricas es una mala idea. Las constantes deben agruparse junto con la clase con la que están más lógicamente relacionadas.

En lugar de usar variables de cualquier tipo (especialmente enumeraciones), sugeriría que use métodos. Cree un método con el mismo nombre que la variable y haga que devuelva el valor asignado a la variable. Ahora elimine la variable y reemplace todas las referencias a ella con llamadas al método que acaba de crear. Si sientes que la constante es lo suficientemente genérico como para no tener que crear una instancia de la clase solo para usarla, y luego hacer del método constant un método de clase.

 1
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 22:17:12

FWIW, un valor de tiempo de espera en segundos probablemente debería ser una configuración (leída desde un archivo de propiedades o a través de inyección como en Spring) y no una constante.

 1
Author: Tim Howland,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-16 01:33:07

¿Cuál es la diferencia

1.

public interface MyGlobalConstants {
    public static final int TIMEOUT_IN_SECS = 25;
}

2.

public class MyGlobalConstants {
    private MyGlobalConstants () {} // Prevents instantiation
    public static final int TIMEOUT_IN_SECS = 25;
}

Y utilizando MyGlobalConstants.TIMEOUT_IN_SECS donde sea que necesitemos esta constante. Creo que ambos son iguales.

 1
Author: chandrayya,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-12-05 06:15:45

No llamaría a la clase lo mismo (aparte de la carcasa) que la constante ... Tendría como mínimo una clase de "Ajustes", o "Valores", o "Constantes", donde vivirían todas las constantes. Si tengo un gran número de ellos, los agruparía en clases constantes lógicas (UserSettings, AppSettings, etc.)

 0
Author: Joel Martinez,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 19:41:23

Para ir un paso más allá, puede colocar constantes utilizadas globalmente en una interfaz para que puedan usarse en todo el sistema. Por ejemplo,

public interface MyGlobalConstants {
    public static final int TIMEOUT_IN_SECS = 25;
}

Pero no lo implementen. Simplemente refiérase a ellos directamente en código a través del nombre de clase completamente calificado.

 0
Author: Andrew Harmel-Law,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 19:45:34

Para Constantes, Enum es una mejor opción en mi humilde opinión. He aquí un ejemplo

Clase pública MyClass {

public enum myEnum {
    Option1("String1", 2), 
    Option2("String2", 2) 
    ;
    String str;
            int i;

            myEnum(String str1, int i1) { this.str = str1 ; this.i1 = i }


}
 0
Author: mmansoor,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 20:45:52

Una de las formas en que lo hago es creando una clase 'Global' con los valores constantes y hacer una importación estática en las clases que necesitan acceso a la constante.

 0
Author: Javamann,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-09-15 21:44:56

static final es mi preferencia, solo usaría un enum si el elemento fuera efectivamente enumerable.

 0
Author: wulfgarpro,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-08-31 01:49:03

Utilizo static final para declarar constantes e ir con la notación de nombres ALL_CAPS. He visto bastantes casos de la vida real donde todas las constantes están agrupadas en una interfaz. Algunas publicaciones han llamado correctamente que es una mala práctica, principalmente porque no es para eso que una interfaz es. Una interfaz debe hacer cumplir un contrato y no debe ser un lugar para poner constantes no relacionadas. Ponerlo junto en una clase que no se puede instanciar (a través de un constructor privado) también está bien si la semántica constante no pertenece a una(s) clase (es) específica (s). Siempre pongo una constante en la clase con la que está más relacionada, porque eso tiene sentido y también es fácil de mantener.

Las enumeraciones son una buena opción para representar un rango de valores, pero si está almacenando constantes independientes con énfasis en el valor absoluto (p. ej. TIMEOUT = 100 ms) usted puede simplemente ir para el enfoque static final.

 0
Author: bincob,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-05-15 12:45:24

Estoy de acuerdo con lo que la mayoría está diciendo, es mejor usar enumeraciones cuando se trata de una colección de constantes. Sin embargo, si estás programando en Android hay una mejor solución: Anotación IntDef.

@Retention(SOURCE)
@IntDef({NAVIGATION_MODE_STANDARD, NAVIGATION_MODE_LIST,NAVIGATION_MODE_TABS})
public @interface NavigationMode {}
public static final int NAVIGATION_MODE_STANDARD = 0;
public static final int NAVIGATION_MODE_LIST = 1;
public static final int NAVIGATION_MODE_TABS = 2;
...
public abstract void setNavigationMode(@NavigationMode int mode);
@NavigationMode
public abstract int getNavigationMode();

La anotación IntDef es superior a las enumeraciones de una manera simple, toma significativamente menos espacio ya que es simplemente un marcador de tiempo de compilación. No es una clase, ni tiene la propiedad automática string-conversion.

 0
Author: Quinn Turner,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-09-20 19:37:31

Es MAL hábito y terriblemente Práctica MOLESTA para citar a Joshua Bloch sin entender el fundamentalismo básico de la zona cero.

No he leído nada Joshua Bloch, así que tampoco

  • es un programador terrible
  • o las personas hasta ahora que me encuentro citándolo (Joshua es el nombre de un niño, supongo) simplemente están usando su material como guiones religiosos para justificar sus indulgencias religiosas de software.

Como en el fundamentalismo bíblico todas las leyes bíblicas se pueden resumir en

  • Ama la Identidad Fundamental con todo tu corazón y toda tu mente{[12]]}
  • Ama a tu prójimo como a ti mismo{[12]]}

Y de manera similar el fundamentalismo de la ingeniería de software se puede resumir en

  • dedícate a los fundamentos de la zona cero con toda tu capacidad de programación y mente
  • y dedícate a la excelencia de tus compañeros programadores como lo harías por ti mismo.

También, entre los círculos fundamentalistas bíblicos se dibuja un corolario fuerte y razonable

  • Primero ámate a ti mismo. Porque si no te amas mucho a ti mismo, entonces el concepto "ama a tu prójimo como a ti mismo "no tiene mucho peso, ya que" cuánto te amas a ti mismo " es la línea de referencia por encima de la cual amarías a los demás.

Del mismo modo, si no te respetas a ti mismo como programador y solo aceptas los pronunciamientos y profecías de algún guru-nath de programación SIN cuestionando los fundamentos, sus citas y la confianza en Joshua Bloch (y similares) no tienen sentido. Y por lo tanto, en realidad no tendrías respeto por tus compañeros programadores.

Las leyes fundamentales de la programación de software

  • la pereza es la virtud de un buen programador
  • usted debe hacer su vida de programación tan fácil, tan perezoso y por lo tanto tan eficaz como sea posible
  • debes hacer que las consecuencias y las entrañas de tu programación sean tan fáciles, tan perezoso y por lo tanto tan eficaz como sea posible para su neigbour-programadores que trabajan con usted y recoger sus entrañas de programación.

Constantes de patrón de interfaz ¿es un mal hábito ???

¿Bajo qué leyes de programación fundamentalmente efectiva y responsable cae este edicto religioso ?

Acaba de leer el artículo de wikipedia sobre constantes de patrón de interfaz (https://en.wikipedia.org/wiki/Constant_interface ), y las excusas tontas que dice contra interfaz-constantes de patrón.

  • Whatif-No IDE? ¿Quién en la tierra como programador de software no usaría un IDE? La mayoría de nosotros somos programadores que preferimos no tener que demostrar tener un survivalistismo escético machista evitando el uso de un IDE.

    • También - espere un segundo defensores de la programación micro-funcional como un medio de no necesitar un IDE. Espera a leer mi explicación sobre la normalización del modelo de datos.
  • Contamina el espacio de nombres ¿con variables no utilizadas dentro del ámbito actual? Podrían ser los proponentes de esta opinión

    • no son conscientes de, y la necesidad de, normalización de modelos de datos
  • Usar interfaces para imponer constantes es un abuso de interfaces. Los defensores de tales tienen un mal hábito de

    • no ver que las "constantes" deben ser tratadas como contrato. Y las interfaces se utilizan para hacer cumplir o proyectar el cumplimiento de un contrato.
  • It es difícil, si no imposible, convertir interfaces en clases implementadas en el futuro. Hah .... hmmm ... ???

    • ¿Por qué querrías participar en tal patrón de programación como tu sustento persistente? ¿Por qué dedicarse a un hábito tan ambivalente y malo de programación ?

Cualesquiera que sean las excusas, no hay EXCUSA VÁLIDA cuando se trata de ingeniería de software FUNDAMENTALMENTE EFECTIVA para deslegitimar o generalmente desalentar el uso de constantes de interfaz.

No importa cuáles fueron las intenciones originales y los estados mentales de los padres fundadores que elaboraron la Constitución de los Estados Unidos. Podríamos debatir las intenciones originales de los padres fundadores, pero lo único que me importa son las declaraciones escritas de la Constitución de los Estados Unidos. Y es responsabilidad de cada ciudadano estadounidense explotar el fundamentalismo literario escrito, no las intenciones fundacionales no escritas, de la Constitución estadounidense.

Del mismo modo, no me importa lo que el los intentos "originales" de los fundadores de la plataforma Java y el lenguaje de programación tenían para la interfaz. Lo que me importa son las características efectivas que proporciona la especificación de Java, y tengo la intención de explotar esas características al máximo para ayudarme a cumplir con las leyes fundamentales de la programación de software responsable. No me importa si se me percibe como "violando la intención de las interfaces". No me importa lo que Gosling o alguien Bloch dice sobre la "forma correcta de usar Java", a menos que lo que dicen no lo hace violar mi necesidad de cumplir con los fundamentos EFECTIVOS.

Lo Fundamental es la Normalización del Modelo de Datos

No importa cómo se aloje o transmita su modelo de datos. Si utiliza interfaces o enums o whatevernots, relacional o no-SQL, si no entiende la necesidad y el proceso de normalización de modelos de datos.

Primero debemos definir y normalizar el modelo de datos de un conjunto de procesos. Y cuando tenemos un modelo de datos coherente, solo entonces podemos utilizar el flujo de proceso de sus componentes para definir el comportamiento funcional y el proceso bloquea un campo o ámbito de aplicaciones. Y solo entonces podemos definir la API de cada proceso funcional.

Incluso las facetas de la normalización de datos como propone EF Codd ahora están severamente desafiadas y severamente desafiadas. por ejemplo, su declaración sobre 1NF ha sido criticada como ambigua, desalineada y sobre simplificada, al igual que el resto de sus declaraciones, especialmente en el advenimiento de los servicios de datos modernos, la repo-tecnología y transmisión. IMO, las declaraciones Codd de EF deben ser completamente desechadas y se debe diseñar un nuevo conjunto de declaraciones más matemáticamente plausibles.

Un defecto evidente de EF Codd y la causa de su desalineación a la comprensión humana efectiva es su creencia de que los datos multidimensionales y de dimensión mutable humanamente perceptibles pueden percibirse eficientemente a través de un conjunto de asignaciones fragmentarias de 2 dimensiones.

Los Fundamentos de la Normalización de Datos

Lo que EF Codd no pudo Express.

Dentro de cada modelo de datos coherente, estos son el orden secuencial graduado de la coherencia del modelo de datos a lograr.

  1. La Unidad e Identidad de las instancias de datos.
    • diseñe la granularidad de cada componente de datos, por lo que su granularidad está en un nivel donde cada instancia de un componente puede ser identificada y recuperada de forma única.
    • ausencia de alias de instancia. es decir, no existe ningún medio por el cual una identificación produzca más de una instancia de un componente.
  2. Ausencia de interferencia de instancia. No existe la necesidad de utilizar una o más instancias de un componente para contribuir a identificar una instancia de un componente.
  3. La unidad e identidad de los componentes/dimensiones de los datos.
    • Presencia de des-aliasing de componentes. Debe existir una definición por la cual un componente/dimensión pueda ser identificado de manera única. Que es la definición primaria de un componente;
    • donde el primario la definición no dará lugar a la exposición de sub-dimensiones o componentes miembro que no son parte de un componente previsto;
  4. Medios únicos de distribución de componentes. Debe existir una, y solo una, definición de des-aliasing de componente para un componente.
  5. Existe una, y solo una, interfaz de definición o contrato para identificar un componente padre en una relación jerárquica de componentes.
  6. Ausencia de diafonía de componentes. No existe el necesidad de utilizar un miembro de otro componente para contribuir a la identificación definitiva de un componente.
    • En tal relación padre-hijo, la definición de identificación de un padre no debe depender de parte del conjunto de componentes miembros de un hijo. Un componente miembro de la identidad de un padre debe ser la identidad completa del niño sin recurrir a hacer referencia a cualquiera o todos los hijos de un niño.
  7. Evitar las apariencias bimodales o multimodales de un modelo de datos.
    • Cuando existen dos definiciones candidatas de un componente, es una señal obvia de que existen dos modelos de datos diferentes que se mezclan como uno solo. Eso significa que hay incoherencia a nivel de modelo de datos, o a nivel de campo.
    • Un campo de aplicaciones debe usar uno y solo un modelo de datos, de manera coherente.
  8. Detectar e identificar la mutación de los componentes. A menos que haya realizado un análisis estadístico de componentes de datos enormes, probablemente no lo haga ver, o ver la necesidad de tratar, mutación componente.
    • Un modelo de datos puede tener algunos de sus componentes mutando cíclicamente o gradualmente.
    • El modo puede ser rotación de miembros o rotación de transposición.
    • La mutación de rotación de miembros podría ser un intercambio distinto de componentes secundarios entre componentes. O donde habría que definir componentes completamente nuevos.
    • La mutación transposicional se manifestaría como un miembro dimensional mutando en un atributo, vicio viceversa.
    • Cada ciclo de mutación debe ser identificado como un modal de datos distinto.
  9. Versionizar cada mutación. De tal manera que se puede sacar una versión anterior del modelo de datos, cuando tal vez surja la necesidad de tratar una mutación de 8 años del modelo de datos.

En un campo o cuadrícula de aplicaciones de componentes de servicios intermedios, debe haber uno y solo un modelo de datos coherente o existe un medio para que un modelo/versión de datos se identifique a sí mismo.

Somos sigue preguntando si podríamos usar Interfaz Constantes? ¿En serio?

Hay cuestiones de normalización de datos en juego más consecuentes que esta cuestión mundana. SI no resuelves esos problemas, la confusión que crees que causan las constantes de la interfaz es comparativamente nada. Nada de nada.

A partir de la normalización del modelo de datos, se determinan los componentes como variables, como propiedades, como constantes de la interfaz de contrato.

Luego se determina cuál entra en la inyección de valor, la propiedad marcadores de posición de configuración, interfaces, cadenas finales, etc.

Si tiene que usar la excusa de necesitar localizar un componente más fácil de dictar contra las constantes de la interfaz, significa que tiene el mal hábito de no practicar la normalización del modelo de datos.

Tal vez desee compilar el modelo de datos en una versión de vcs. Que puede extraer una versión claramente identificable de un modelo de datos.

Los valores definidos en las interfaces están completamente seguros de que no son mutables. Y compartible. ¿Por qué cargar un conjunto de cadenas finales en su clase desde otra clase cuando todo lo que necesita es ese conjunto de constantes ??

Entonces, ¿por qué no publicar un contrato de modelo de datos? Quiero decir, si puedes manejarlo y normalizarlo coherentemente, ¿por qué no? ...

public interface CustomerService {
  public interface Label{
    char AssignmentCharacter = ':';
    public interface Address{
      String Street = "Street";
      String Unit= "Unit/Suite";
      String Municipal = "City";
      String County = "County";
      String Provincial = "State";
      String PostalCode = "Zip"
    }

    public interface Person {
      public interface NameParts{
        String Given = "First/Given name"
        String Auxiliary = "Middle initial"
        String Family = "Last name"
      }
    }
  }
}

Ahora puedo hacer referencia a las etiquetas contratadas de mis aplicaciones de una manera como

CustomerService.Label.Address.Street
CustomerService.Label.Person.NameParts.Family

Esto confunde el contenido del archivo jar? Como programador Java no me importa la estructura del jar.

Esto presenta complejidad ¿al intercambio de tiempo de ejecución motivado por osgi ? Osgi es un medio extremadamente eficiente para permitir a los programadores continuar con sus malos hábitos. Hay mejores alternativas que osgi.

¿O por qué no esto? No hay fugas de las constantes privadas en el contrato publicado. Todas las constantes privadas deben agruparse en una interfaz privada llamada "Constantes", porque no quiero tener que buscar constantes y soy demasiado perezoso para escribir repetidamente"cadena final privada".

public class PurchaseRequest {
  private interface Constants{
    String INTERESTINGName = "Interesting Name";
    String OFFICIALLanguage = "Official Language"
    int MAXNames = 9;
  }
}

Tal vez incluso esto:

public interface PurchaseOrderConstants {
  public interface Properties{
    default String InterestingName(){
       return something();
    }
    String OFFICIALLanguage = "Official Language"
    int MAXNames = 9;
  }
}

El único problema con las constantes de la interfaz que vale la pena considerar es cuando se implementa la interfaz.

Esta no es la "intención original" de las interfaces? Al igual que me preocuparía por la "intención original" de los padres fundadores en la elaboración de la Constitución de los EE.UU., en lugar de cómo la Corte Suprema interpretaría las cartas escritas de la Constitución de los EE.UU. ???

Después de todo, vivo en la tierra de los libres, los salvajes y el hogar de los valientes. Sé valiente, sé libre, sé salvaje - usa la interfaz. Si mis compañeros programadores se niegan a usar medios de programación eficientes y perezosos, ¿estoy obligado por la regla de oro a disminuir mi eficiencia de programación para alinearme con la de ellos? Tal vez debería, pero esa no es una situación ideal.

 0
Author: Blessed Geek,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-01-10 12:18:44