2014-10-04 4 views
0

При заполнении значений для кластерной (статической) структуры данных/коллекции (в данном случае 2D-массива) обычно лучше сохранять значения непосредственно в статическом, или должна быть создана временная переменная в методе?Создание массивов класса в Java

Чтобы сделать его более ясным:

public class MyClass{ 

    private static int[][] table; 

    public void setTable(int row, int col){ 

     table = new char[row][col]; 
     // fill table (eg. table[i][j] = 5;) 
    } 


    //// OR THIS////// 

    public void setTable(int row, int col){ 

     int[][] tempTable = new tempTable[row][col]; 

     // fill tempTable 
     table = tempTable; 
    } 
} 

Создание временной переменной чувствует себя излишним и бесполезным здесь. Но есть ли случаи, когда это было бы рекомендовано? Возможность сбоя программы на полпути через выполнение метода и развращение данных? Многопоточные приложения?

Надеюсь, что вопрос не субъективен, просто хочу знать, есть ли что-то неправильное, просто заполнив его напрямую.

+0

Если статический объект может/должен быть изменен, тогда первый способ будет прекрасен. Я предпочитаю это из-за ясности, но это связано с моими предпочтениями, а не с техническими преимуществами. Но если вы хотите, чтобы он оставался неизменяемым, вы должны сделать его «static final int [] [] table = setTable (int, int)» и использовать второй подход. –

ответ

1

Во-первых, важно заметить, что ни один из двух подходов не является потокобезопасным. Если ваше приложение многопоточно или, точнее, одновременно доступны объекты MyClass, вам понадобятся дополнительные меры предосторожности. Даже присвоения ссылочных типов не гарантируются как атомарные.

В последовательной программе создание нового значения во временной и единственной перезаписке старой ссылки, как только это будет сделано, может быть более безопасным в некоторых аспектах. Самое главное, подумайте, что произойдет, если логика, заполняющая новую таблицу, выдает исключение, которое ускользает от метода setTable. Если вашей программе удастся восстановить эту ошибку, первая реализация останется за неопределенным состоянием MyClass.table, а вторая останется без изменений. Поэтому, если возможно, что процесс завершился неудачей с ошибкой, которую вы планируете восстановить, вам, вероятно, придется пойти со второй реализацией. (В C++, мы говорим, операция, которая обеспечивает такого рода «совершить или-откат» семантика предоставляет гарантиюсильного исключения, но я не видел этот термина используется в сообществе Java до сих пор.)

Наконец, вам может быть интересно услышать, что

Object obj = new Object(); 

не гарантирует, что присваивание выполняется только после того, как новый объект будет полностью построен. Если это может быть важно для вас, переместите конструкцию в метод, поскольку возврат из метода (в отличие от конструктора) устанавливает связь «произойдет до». (Назначение все равно не будет атомарным, как упомянуто выше.)

Я предполагаю, что вы знаете о последствиях, связанных с использованием изменяемой статической подачи. Просто говорю, что есть лучший способ сделать то, что вы хотите.