public class Test { static int x; public Test() { } public static void main(String[] args) { Test t = new Test(); t.test(5); System.out.println("Member value x = " + x); } private void test(int x){ this.x = x + 5; System.out.println("Local value x = " + x); } }
В результате работы этого примера на консоль будет выведено:
Local value x = 5 Member value x = 10
На следующем примере продемонстрируем, что область видимости локальной переменной ограничена областью видимости блока, или оператора, в пределах которого данная переменная объявлена.
public class Test { static int x = 5; public Test() { } public static void main(String[] args) { Test t = new Test(); { int x = 1; System.out.println("First block x = " + x); } { int x = 2; System.out.println("Second block x =" + x); } System.out.print("For cycle x = "); for(int x =0;x<5;x++) { System.out.print(" " + x); } } }
Данный пример откомпилируется без ошибок и на консоль будет выведен следующий результат:
First block x = 1 Second block x =2 For cycle x = 0 1 2 3 4
Следует помнить, что определение локальной переменной есть исполняемый оператор. Если задана инициализация переменной, то выражение исполняется слева направо и его результат присваивается локальной переменной. Использование неинициализированных локальных переменных запрещено и вызывает ошибку компиляции.
Следующий пример кода
public class Test { static int x = 5; public Test() { } public static void main(String[] args) { Test t = new Test(); int x; int y = 5; if( y > 3) x = 1; System.out.println(x); } }
вызовет ошибку времени компиляции, т.к. возможны условия, при которых переменная x может быть не инициализирована до ее использования (несмотря на то, что в данном случае оператор if(y > 3) и следующее за ним выражение x = 1; будут выполняться всегда).
Пустой оператор
Точка с запятой ( ; ) является пустым оператором. Данная конструкция вполне применима там, где не предполагается выполнение никаких действий. Преждевременное завершение пустого оператора невозможно.
Метки
Любой оператор, или блок, может иметь метку. Метку можно указывать в качестве параметра для операторов break и continue. Область видимости метки ограничивается оператором, или блоком, к которому она относится. Так, в следующем примере мы получим ошибку компиляции:
public class Test { static int x = 5; static { } public Test() { } public static void main(String[] args) { Test t = new Test(); int x = 1; Lbl1: { if(x == 0) break Lbl1; } Lbl2:{ if(x > 0) break Lbl1; } } }
В случае, если имеется несколько вложенных блоков и операторов, допускается обращение из внутренних блоков к меткам, относящимся к внешним.
Этот пример является вполне корректным:
public class Test { static int x = 5; static { } public Test() { } public static void main(String[] args) { Test t = new Test(); int L2 = 0; Test: for(int i = 0; i< 10;i++) { test: for(int j = 0; j< 10;j++) { if( i*j > 50) break Test; } } } private void test() { ; } }
В этом же примере можно увидеть, что метки используют пространство имен, отличное от пространства имен переменных, методов и классов.
Традиционно использование меток не рекомендуется, особенно в объектно-ориентированных языках, поскольку серьезно усложняет понимание порядка выполнения кода, а значит, и его тестирование и отладку. Для Java этот запрет можно считать не столь строгим, поскольку самый опасный оператор goto отсутствует. В некоторых ситуациях (как в рассмотренном примере с вложенными циклами) использование меток вполне оправданно, но, конечно, их применение следует ограничивать лишь самыми необходимыми случаями.
Оператор if
Пожалуй, наиболее распространенной конструкцией в Java, как и в любом другом структурном языке программирования, является оператор условного перехода.
В общем случае конструкция выглядит так:
if (логическое выражение) выражение или блок 1 else выражение или блок 2
Логическое выражение может быть любой языковой конструкцией, которая возвращает булевский результат. Отметим отличие от языка C, в котором в качестве логического выражения могут использоваться различные типы данных, где отличное от нуля выражение трактуется как истинное значение, а ноль - как ложное. В Java возможно использование только логических выражений.
Если логическое выражение принимает значение "истина", то выполняется выражение или блок 1, в противном случае - выражение или блок 2. Вторая часть оператора ( else ) не является обязательной и может быть опущена. Т.е. конструкция if(x == 5) System.out.println("Five") вполне допустима.
Операторы if-else могут каскадироваться.