Где вы храните константы, используемые в вашем приложении?

интерфейс является приемлемым местом для хранения my

public static final Foo bar

экстраполируете ли вы их для чтения из-за пределов программы? Вы составляете для него супер-класс?

Как вы это делаете, когда ситуация представляет себя?

5 ответов


Я бы поместил каждую константу в класс или интерфейс, с которым она наиболее тесно связана (например, потому, что она будет использоваться его методами).

очень соблазнительная, но в конечном счете очень глупая идея-иметь один "класс констант" (или интерфейс), который содержит все константы, используемые в приложении. Это выглядит "аккуратно" на первый взгляд, но не хорошо для ремонтопригодности, потому что вы хотите группировать вещи по функциональности, которую они реализуют, а не по техническим деталям, таким как константы (будет вы поместили все интерфейсы в специальный пакет? Все абстрактные классы?).

идея также глупа, потому что любое изменение этого класса/интерфейса (из - за постоянной вставки) требует, чтобы все классы, которые используют любую из констант, были перестроены-т. е. почти все приложение. Таким образом, чем больше приложение становится, тем чаще вам нужна такая полная перестройка, и тем дольше это занимает. Я работал над таким проектом, где этот вопрос привел к 15-минутной паузе примерно через день для каждого разработчик...


Если вы говорите о простом приложении Constants классный подход в порядке:

public class Constants {
    private Constants() {} // no way to instantiate this class
    public static final String MY_VAL = "123";
}

Если вы создаете большее приложение, вы должны использовать инъекцию зависимостей, взгляните на как я могу ввести значение свойства в Spring Bean, который был настроен с помощью аннотаций?


я использовал подход Абдуллы Джибали, но используя вложенные классы, что обеспечивает хороший способ группировки минусов. Я видел, что это идет на 3 уровня глубоко, и если выбраны хорошие имена, он все еще может работать довольно хорошо.

для этого можно использовать final classes вместо interface classes, чтобы избежать нарушения пункта # 19 в списке Джоша Блоха (эффективное Java 2nd edition).

public final class Const {
    private Const() {} // prevent instantiation

    /** Group1 constants pertain to blah blah blah... */
    public static final class Group1 {
        private Group1() {} // prevent instantiation

        public static final int MY_VAL_1 = 1;
        public static final int MY_VAL_2 = 42;
    }

    /** Group2 constants pertain to blah blah blah... */
    public static final class Group2 {
        private Group2() {} // prevent instantiation

        public static final String MY_ALPHA_VAL = "A";
        public static final String MY_ALPHA_VAL = "B";
    }

}

Это плохая практика. Классы должны быть независимыми друг от друга, поэтому вы должны избегать глобальных переменных любой ценой. Более реалистичным подходом является наличие конфигурационного файла, обычно в JSON, YAML или XML формат файла, и ваша программа читается из этого файла при запуске.


Я бы использовал abstract final class поскольку это было бы более явное объявление модификаторов, а не использование интерфейса. Но, как сказал Майкл, они должны быть логически сгруппированы и быть частью существующего класса или интерфейса, если они семантически принадлежат там.