Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Sharing constant strings in Java across many classes?

Tags:

java

string

I'd like to have Java constant strings at one place and use them across whole project (many classes).

What is the recommended way of achieveing this?

like image 431
Danijel Avatar asked Jun 05 '12 11:06

Danijel


People also ask

How do you manage a constant in Java?

To make any variable a constant, we must use 'static' and 'final' modifiers in the following manner: Syntax to assign a constant value in java: static final datatype identifier_name = constant; The static modifier causes the variable to be available without an instance of it's defining class being loaded.

Which of the following is a best way to create named constants in Java?

The public|private static final TYPE NAME = VALUE; pattern is a good way of declaring a constant.

How do you make a string constant in Java?

So to declare a constant in Java you have to add static final modifiers to a class field. Example: public static final String BASE_PATH = "/api"; You should follow Java constant naming convention – all constant variables should be in upper case, words should be separated by the underscore.

What are the benefits of using constants in Java?

A constant can make our program more easily read and understood by others. In addition, a constant is cached by the JVM as well as our application, so using a constant can improve performance. To define a variable as a constant, we just need to add the keyword “final” in front of the variable declaration.


4 Answers

public static final String CONSTANT_STRING="CONSTANT_STRING"; 

constants should be:

  1. public - so that it can be accessed from anywhere
  2. static - no need to create an instance
  3. final - since its constants shouldnt be allowed to change
  4. As per Java naming convention should be capitalized so that easy to read and stands out in Java documentation.

There are instances where interfaces are used just to keep constants, but this is considered a bad practice because interfaces are supposed to define the behavior of a type.

A better approach is to keep it in the class where it makes more sense.

for e.g.

JFrame has EXIT_ON_CLOSE contant, any class which subclasses JFrame will have access to it and it also makes sense to keep in JFrame and not in JComponent as not all components will have an option to be closed.

like image 89
mprabhat Avatar answered Oct 08 '22 02:10

mprabhat


As @mprabhat answered before, constants should be public, static, final, and typed in capital letters.

Grouping them in a class helps you:

  1. Don't need to know all the constants you have. Many IDEs (like Eclipse) show you the list of all the fields a class has. So you only press CTRL+SPACE and get a clue of which constants you can use.

  2. Making them typesafe at compile time. If you used Strings, you might misspell "DATABASE_EXCEPTION" with "DATABSE_EXSCEPTION", and only notice during execution (if you are lucky and notice it at all). You can also take profit of autocompletion.

  3. Helping you save memory during execution. You'll only need memory for 1 instance of the constant. I.E: (a real example) If you have the String "DATABASE_EXCEPTION" 1000 times in different classes in you code, each one of them will be a different instace in memory.

Some other considerations you might have:

  1. Add javadoc comments, so programmers who use the constants can have more semantic information on the constant. It is showed as a tooltip when you press CTRL+SPACE. I.E:

    /** Indicates an exception during data retrieving, not during connection. */ public static final String DATABASE_EXCEPTION = "DATABASE_EXCEPTION"; /** Indicates an exception during the connection to a database. */ public static final String DATABASE_CONNECTION_EXCEPTION =" DATABASE_CONNECTION_EXCEPTION"; 
  2. Add semantic to the identifier of the constant. If you have the constant "Y", and sometimes means yes and other times year, consider using 2 different constants.

    public static final String Y = "Y"; // Bad public static final String YEAR = "Y"; public static final String YES = "Y";  

    It will help you if, in the future, decide to change the values of the constants.

    /** Year symbol, used for date formatters. */ public static final String YEAR = "A"; // Year is Año, in Spanish. public static final String YES = "S"; // Yes is Sí, in Spanish. 
  3. You might not know the value of your constants until runtime. IE: You can read them from configuration files.

    public class Constants {   /** Message to be shown to the user if there's any SQL query problem. */   public static final String DATABASE_EXCEPTION_MESSAGE; // Made with the 2 following ones.   public static final String DATABASE_EXCEPTION = "DATABASE_EXCEPTION";   public static final String MESSAGE = "MESSAGE";    static {     DATABASE_EXCEPTION_MESSAGE = DATABASE_EXCEPTION + MESSAGE; // It will be executed only once, during the class's [first] instantiation.   } 

    }

  4. If your constants class is too large, or you presume it'll grow too much in the future, you can divide it in different classes for different meanings (again, semantic): ConstantDB, ConstantNetwork, etc.

Drawbacks:

  1. All the members of your team have to use the same class(es), and the same nomenclature for the constants. In a large project it wouldn't be strange to find 2 definitions:

    public static final String DATABASE_EXCEPTION = "DATABASE_EXCEPTION"; public static final String EXCEPTION_DATABASE = "DATABASE_EXCEPTION";  

    separated several hundreds of lines or in different constant classes. Or even worse:

    /** Indicates an exception during data retrieving, not during connection. */ public static final String DATABASE_EXCEPTION = "DATABASE_EXCEPTION"; /** Indicates an exception during data retrieving, not during connection. */ public static final String EXCEPTION_DATABASE = "EXCEPTION_DATABASE";  

    different identifiers, for different values, having the same meaning (and used for the same purposes).

  2. It might make readability worse. Having to write more for doing the same:

    if ("Y".equals(getOptionSelected()) { 

    vs

    if (ConstantsWebForm.YES.equals(getOptionSeleted()) { 
  3. How should constants be ordered in the class? Alphabetically? All related constants together? In order as they are created/needed? Who sould be responsible of the order being correct? Any (big enough) reordering of constants would be seen as a mess in a versioning system.

Well, it's taken longer than what I expected. Any help/critics is/are welcome.

like image 38
J.A.I.L. Avatar answered Oct 08 '22 03:10

J.A.I.L.


You should create a class of the constants that stores all the constants.

like ProjectNameConstants.java

which contains all the constant string static as you can access it through the classname.

e.g.

classname :  MyAppConstants.java

public static final String MY_CONST="my const string val";

you can access it as

MyAppConstants.MY_CONST
like image 43
Hemant Metalia Avatar answered Oct 08 '22 03:10

Hemant Metalia


Best practice is to use Java Enum (After Java 5)

Problems with the class approach:

  1. Not typesafe
  2. No namespace
  3. Brittleness

Please check java docs.

public enum Constants {

    CONSTANT_STRING1("CONSTANT_VALUE1"), 
    CONSTANT_STRING2("CONSTANT_VALUE2"), 
    CONSTANT_STRING3("CONSTANT_VALUE3");

    private String constants;

    private Constants(String cons) {
        this.constants = cons;
    }
}

Enums can be used as constants.

Edit: You can call this Constants.CONSTANT_STRING1

like image 39
amicngh Avatar answered Oct 08 '22 04:10

amicngh