Как избежать повторения кода при инициализации конечных свойств? - PullRequest
4 голосов
/ 31 марта 2010
public class Code{

//many properties
//...

final String NEWLINE;// ohh a final property!

void creation() //this method is for avoid repetition of code
{        

    //final initialization can't be put here =(

    Source= new StringBuffer();

   //many other commons new's ..
   //...
}

Code()
{
    NEWLINE = System.getProperty("line.separator");
    creation();
}

Code(String name, int numberr)
{
    NEWLINE = System.getProperty("line.separator");
    creation();

    name=new Someting(name);
    number = new Magic(number);
}

}

Ответы [ 5 ]

6 голосов
/ 01 апреля 2010

Вот ваш код с 4 различными способами инициализации конечных переменных.

  1. встроенный
  2. блок анонимного инициализатора
  3. инициализируется в конструкторе
  4. явный вызов конструктора по умолчанию

Полученный результат показан ниже.

public class Code {

    // many properties
    private String name;
    private String number;
    // ...

    // 1.
    final String NEWLINE_1 = "1" + System.getProperty("line.separator");
    final String NEWLINE_2;
    final String NEWLINE_3;

    // 2.
    {
        System.out.println("initializer block invoked before Constructor");

        NEWLINE_2 = "2" + System.getProperty("line.separator");
        // final initialization CAN be put here =(

        // Source = new StringBuffer();

        // many other commons new's ..
        // ...
    }

    Code() {
        System.out.println("default constructor");
        // NEWLINE_1 = "error";     can't do this
        // NEWLINE_2 = "error";     can't do this

        // 3.
        NEWLINE_3 = "3" + System.getProperty("line.separator");
    }

    Code(String name, int number) {
        // 4.
        this();
        System.out.println("constructor(name, number)");

        name = new String("Someting(name)");
        this.number = new String("Magic(number)");
    }

    public static void main(String[] args) {
        Code code_1 = new Code();
        System.out.println(code_1.NEWLINE_1 + ":" + code_1.NEWLINE_2 + ":" + code_1.NEWLINE_3);

        Code code_2 = new Code("crowne", 2);
        System.out.println(code_2.NEWLINE_1 + ":" + code_2.NEWLINE_2 + ":" + code_2.NEWLINE_3);
    }
}

initializer block invoked before Constructor
default constructor
1
:2
:3

initializer block invoked before Constructor
default constructor
constructor(name, number)
1
:2
:3
6 голосов
/ 31 марта 2010

Все инициализаторы добавляются компилятором в начало каждого конструктора. Это включает в себя:

  • инициализация переменной экземпляра
  • блоки инициализации { .. }

Так что вам не нужно включать это везде, просто поместите это как инициализацию переменной экземпляра:

private final String NEWLINE = System.getProperty("line.separator");

или в блоке инициализации:

{
     NEWLINE = System.getProperty("line.separator");
}

Конечно, в этом точном примере вы должны сделать поле static.

3 голосов
/ 31 марта 2010

Просто сделай:

final String NEWLINE = System.getProperty("line.separator");

См .: JLS 8.3.2. Инициализация полей .

См. Также: JLS 12.5 Создание экземпляров нового класса для порядка выполнения.

1 голос
/ 01 апреля 2010

Еще один, если инициализация сложна, и вы должны сделать это во время построения, предоставьте статический метод, который возвращает результат, как в:

Code()
{
    NEWLINE = newLineValue();
    creation();
}

Code(String name, int number)
{
    NEWLINE = newLineValue();
    creation();

    name = new Something(name);
    number = new Magic(number);
}

private static String newLineValue()
{
    return System.getProperty("line.separator");
}

В этом случае newLineValue() является тривиальным, поэтому я бы не стал использовать его здесь, но если бы на самом деле было много работы, то это могло бы быть полезно. Вы также можете передать параметры из конструктора.

1 голос
/ 31 марта 2010

Если они каждый раз инициализируются одинаково, вы можете поместить код за пределы конструкторов. Java позволяет делать:

final String NEWLINE = System.getProperty("line.separator");

Вы также можете иметь все конструкторы, кроме одного без аргумента, вызывающего конструктор без аргументов. Например:

Code(String name, int number)
{
    this();

    name=new Someting(name);
    number = new Magic(number);
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...