1. Булеві операції

Оператори | і & можна застосовувати не тільки до чисел, а й до виразів зі значенням типу boolean.

Однак, як ви вже знаєте, для логічних виразів є оператори && і ||. Що ж нам дасть використання | замість || і використання & замість &&? Чи є взагалі в цьому сенс? Виявляється, є. Іноді.

Логічні оператори || і && виконуються зліва направо за принципом так званих лінивих обчислень.

(вираз1) || (вираз2) || (вираз3)

Якщо вираз1 дорівнює true, немає сенсу обчислювати вираз2 й вираз3: результат все одно буде true.

Тому під час обчислення виразів (а вони обчислюються один за одним зліва направо), щойно ми отримали true, обчислення решти виразів не виконується. І якщо вирази вираз2 й вираз3 містили виклики якихось функцій, то ці функції не викликаються!

Те саме відбувається й у випадку з логічним оператором &&:

(вираз1) && (вираз2) && (вираз3)

Якщо вираз1 дорівнює false, немає сенсу обчислювати вираз2 й вираз3: результат все одно буде false.

Це важливий момент, який дозволяє писати ось такі речі:

String s = null;
if (s != null && s.length() > 0) {

У прикладі вище ми ніколи не отримаємо NullPointerException, оскільки вираз s.length() виконуватиметься, тільки якщо перша частина, s != null, дорівнює true.

Якщо s виявиться рівним null, ліворуч від оператора && буде значення false, і результат усього логічного виразу буде false, тому обчислення другої частини (s.length() > 0) не виконується.

От до чого це все:

якщо в логічному виразі використати оператор | або оператор &, то лінивого обчислення не вийде — у всіх випадках буде обчислено всі вирази.


9
Задача
Java Syntax Zero,  9 рівень7 лекція
Недоступна
Логічні оператори
Виправ метод taskForCondition() так, щоб він виводив у консоль число 30. Змінювати можна лише логічні оператори: && на & і || на |.

2. Пріоритет операцій у Java

Як ви, певно, пам'ятаєте зі шкільного курсу математики, операція множення має вищий пріоритет, ніж операція додавання. А дужки мають іще вищий пріоритет: спочатку обчислюються вирази в дужках, а потім уже виконуються множення/ділення й додавання/віднімання.

Оператори в Java теж мають пріоритет, тільки: а) їх дещо більше, б) деякі оператори виконуються зліва направо, а інші — справа наліво.

Отакий вигляд має таблиця з усіма операторами Java:

Категорія Оператор Асоціативність
Постфікс () [] . Зліва направо
Унарний ++ -- ! ~ Справа наліво
Мультиплікативний * / % Зліва направо
Адитивний + - Зліва направо
Зсув >> >>> << Зліва направо
Реляційний > >= < <= Зліва направо
Рівність == != Зліва направо
Побітове І (AND) & Зліва направо
Виключне АБО (XOR) ^ Зліва направо
Побітове АБО (OR) | Зліва направо
Логічне І (AND) && Зліва направо
Логічне АБО (OR) || Зліва направо
Умовний ?: Справа наліво
Присвоювання = += -= *= /= %= >>= <<= &= ^= |= Справа наліво
Кома , Зліва направо

У верхньому рядку розташовані найпріоритетніші оператори. Круглі дужки () використовуються для явного встановлення пріоритету. Квадратні дужки [] використовуються для індексування змінної-масиву. Оператор . використовується для отримання полів і методів від посилання на об'єкт або клас.

Що нижче оператори розташовані в таблиці, то нижче їхній пріоритет.

Якщо ви використовуєте у виразі кілька операторів, не лінуйтеся — ставте дужки.

Так, у Java можна написати щось на кшталт if (a & 1<<b > ~c), але так робити не варто. Ви пишете код не лише для компілятора, але й для інших програмістів. Що читабельнішим буде код, то краще.


9
Задача
Java Syntax Zero,  9 рівень7 лекція
Недоступна
Пріоритети
Виправ метод main() так, щоб він виводив у консоль число 12.

3. Префіксний і постфіксний інкременти

Як ви вже знаєте, у Java є оператор інкременту (++) і оператор декременту (--), які збільшують і зменшують значення змінної на 1.

Однак ви, напевно, не знаєте, що є два види цих операцій: префіксні (оператор ставиться перед змінною) і постфіксні (оператор ставиться після змінної). І працюють ці оператори трохи по-різному.

У Java можна написати такий вираз:

int a = 5;
int b = a++;

Якщо оператор ++ стоїть після змінної та водночас ця змінна входить в якийсь вираз (як у прикладі вище), то у виразі буде використано поточне значення змінної, а тільки потім його буде збільшено на 1.

Інакше кажучи, відбудеться приблизно от що:

int a = 5;
int b = a;
a = a + 1;

Тобто b матиме значення 5, а не 6, як це могло здатися спочатку.

Якщо ж оператор ++ стоїть перед змінною і змінна входить в якийсь вираз, її значення спочатку буде збільшено на 1, а тільки потім використано у виразі.

int a = 5;
int b = ++a;

Приклад вище еквівалентний такому прикладу:

int a = 5;
a = a + 1;
int b = a;

Отут вже значення b дорівнюватиме 6.

Є навіть один приклад, який використовують Java-програмісти, щоб визначити, чи їхній співрозмовник — теж Java-програміст:

int a = 5;
int b = ++a + ++a;

Так, це теж правильний запис.

Цей приклад відмінно скомпілюється й перетвориться приблизно на таке:

int a = 5;

a = a + 1;
int v1 = a;

a = a + 1;
int v2 = a;

int b = v1 + v2;

Для оператора -- все відбувається аналогічно.


9
Задача
Java Syntax Zero,  9 рівень7 лекція
Недоступна
Інкременти
Виправ метод main() так, щоб він виводив у консоль число 20. У методі можна змінювати лише постінкремент на преінкремент і навпаки, а також постдекремент на предекремент і навпаки.