2012-06-22 2 views
21
public class Foo { 
    public static void main(String[] args) { 
     float f; 
     System.out.println(f); 
    } 
} 

Оператор печати вызывает следующую ошибку во время компиляции,Java: Почему мне требуется инициализировать примитивную локальную переменную?

Локальная переменная F не может быть инициализирована

Если примитивов в Java уже есть default value (float = 0.0f), почему я обязательно определить один?


Edit:

Таким образом, это работает

public class Foo { 
    float f; 
    public static void main(String[] args) { 
     System.out.println(new Foo().f); 
    } 
} 

Спасибо, все!

+6

re edit: да, что работает, но продвижение локального поля, чтобы избежать инициализации, может быть не разумным примером :-) – fvu

+1

@fvu, это пример, поэтому он служит какой-то цели. : D – user1329572

ответ

41

Потому что это локальная переменная. Вот почему ему ничего не назначено:

Локальные переменные несколько отличаются; компилятор никогда не присваивает значение по умолчанию неинициализированной локальной переменной. Если вы не можете инициализировать свою локальную переменную там, где она объявлена, убедитесь, что присвойте ей значение, прежде чем пытаться ее использовать. Доступ к неинициализированной локальной переменной приведет к ошибке времени компиляции.

Редактировать: Почему Java вызывает ошибку при компиляции? Если мы посмотрим на файл IdentifierExpression.java класса, мы найдем этот блок:

... 
if (field.isLocal()) { 
      LocalMember local = (LocalMember)field; 
      if (local.scopeNumber < ctx.frameNumber && !local.isFinal()) { 
       env.error(where, "invalid.uplevel", id); 
      } 
      if (!vset.testVar(local.number)) { 
       env.error(where, "var.not.initialized", id); 
       vset.addVar(local.number); 
      } 
      local.readcount++; 
     } 
... 

Как указано (if (!vset.testVar(local.number)) {) проверяет JDK (с testVar), если переменная присваивается (Vset's source code, где мы можем найти testVar код). Если нет, то возникает ошибка var.not.initialized из properties file:

... 
javac.err.var.not.initialized=\ 
    Variable {0} may not have been initialized. 
... 

Source

+5

О, ничего себе, сегодня полностью узнал что-то новое! : D – user1329572

+1

На самом деле это не * объясняет * «почему», не так ли? – kryger

+1

@kryger См. Редактирование. – Zakaria

5

Поля классов (не равно final) в любом случае инициализируются значениями по умолчанию. Локальных переменных нет.

Не обязательно назначать значение при объявлении поля. Поля, объявленные, но не инициализированные, будут установлены на разумный по умолчанию компилятор.

Так (не final) поле как f в

class C { 
    float f; 
} 

инициализируется 0f но локальной переменной f в

void myMethod() { 
    float f; 
} 

не будет.

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

+1

+1, отличная информация о бит не-финал! : D – user1329572

13

В самом деле, компилятор не присвоить значение по умолчанию для вашего float f, потому что в этом случае это локальная переменная - а не поле:

Локальные переменные немного отличаются; компилятор никогда не присваивает значение по умолчанию неинициализированной локальной переменной. Если вы не можете инициализировать свою локальную переменную там, где она объявлена, не забудьте присвоить ей значение, прежде чем пытаться его использовать. Доступ к неинициализированной локальной переменной приведет к ошибке времени компиляции.

2

На самом деле локальные переменные хранятся в stack.Hence есть шанс взять любое старое значение подарок для местного variable.It является большой проблемой для соображений безопасности. Java говорит, что перед использованием вы должны инициализировать локальную переменную.

1

Привет, ребята, решение прост. значения, хранящиеся в памяти кучи, инициализируются типом данных на основе компилятора, но локальные переменные хранятся в памяти стека, поэтому мы должны их инициализировать.

Смежные вопросы