open atlas
↑ К треку
Логика с нуля LOGIC · 01 · 01

Высказывания и истинность: что на самом деле проверяет ваш if

Высказывание — это утверждение, которое либо истинно, либо ложно: третьего не дано. «x > 3» становится высказыванием, лишь когда x получает значение, а каждое условие if — высказывание в момент выполнения. Баги truthiness начинаются там, где кончается строгая истинность.

LOGIC Основы ◷ 16 min
Уровень
ОсновыJuniorMiddleSenior

Подумайте про обычные предложения. «Идёт дождь» — это то, что можно просто назвать истинным или ложным, выглянув в окно. «Закрой окно!» — нет: это приказ, а не утверждение, и называть его «ложным» бессмысленно. «Опаздывает ли автобус?» — вопрос, который просит ответ «истина или ложь», а не даёт его. Вся логика построена на предложениях первого вида — тех, что обязаны быть либо истинными, либо ложными, — и на них же построено каждое решение вашего кода. Платёжный стартап однажды выкатил правку в одну строку: читать флаг администратора из конфига вместо базы. В файле значилось isAdmin: "false" — строка. Проверка if (user.isAdmin) стала проходить у каждого пользователя: в JavaScript непустая строка truthy. Шесть часов любой видел панель возвратов. Баг был не опечаткой — это была подмена высказываний.

Цель

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

1

Высказывание — предложение ровно с одним значением истинности. Высказывание (proposition) — это повествовательное предложение, которое либо истинно, либо ложно: ровно одно из двух, никогда оба, никогда ни одно. «7 — чётное число» — высказывание: оно ложно, и это нормально — ложное утверждение остаётся полноценным высказыванием. «Закрой дверь!» — не высказывание: команду можно выполнить или проигнорировать, но нельзя назвать истинной или ложной.

2

Вопросы и суждения вкуса тоже исключены. «Сервер работает?» запрашивает значение истинности, а не утверждает его. «Эта пицца восхитительна» — дело вкуса, и классическая логика его не принимает. Два значения истинности записывают И и Л (или true и false). Логику не волнует, о чём высказывание — она следит только за этим одним битом.

3

Предложение со свободной переменной — не высказывание, а открытое предложение. Взгляните на «x > 3». Истина или ложь? Сказать нельзя — всё зависит от x. Предложение со свободной переменной (заполнителем без значения) называется открытым предложением (предикатом). Подставьте значение — и оно замкнётся: связать x = 7 → «7 > 3», истинное высказывание; связать x = 1 → «1 > 3», ложное.

4

Условие if — открытое предложение, которое рантайм замыкает. Каждый if, while и тернарник — это рантайм, строящий и вычисляющий высказывание. Вы пишете открытое предложение; выполнение связывает переменные; результат обязан схлопнуться в один бит: войти в ветку или нет. В языках с приведением типов, как JavaScript, любое значение втискивается в истину или ложь по правилам truthiness — поэтому строка "false" ведёт if так же уверенно, как true.

Разбор примера

Классифицируйте каждое предложение: высказывание, открытое предложение или ни то ни другое?

  1. «HTTP-запрос вернул статус 200.»
  2. «Закрой соединение!»
  3. «count > limit» (где count и limit — несвязанные переменные)
  4. «count > limit» (где count = 50000 и limit = 100)

Предложение 1 — высказывание: оно утверждает факт, который либо истинен, либо ложен.

Предложение 2 — ни то ни другое: команда; её можно выполнить или проигнорировать, значения истинности нет.

Предложение 3 — открытое предложение: обе переменные свободны, значения истинности пока нет.

Предложение 4 — высказывание: связав count = 50000 и limit = 100, замыкаем предложение. «50000 > 100» — истинно.

Практический вывод: каждый написанный вами if (count > limit) — это предложение 3 в момент написания кода. Рантайм превращает его в предложение 4 — а если limit так и не был присвоен, JavaScript молча вычисляет 50000 > undefined, что через NaN даёт false. Настоящее высказывание, только не то, что вы имели в виду.

Почему это работает

Почему логика настаивает на ровно одном значении истинности? Потому что всё дальнейшее — таблицы истинности, доказательства, эквивалентности из следующих уроков — работает, отслеживая, как истинность перетекает из малых утверждений в большие. Если бы предложение могло быть одновременно истинным и ложным, можно было бы «доказать» что угодно. Булева колонка с тремя состояниями (true, false, NULL) — знаменитый источник багов по той же причине: третье состояние ломает все допущения, написанные для двух.

Практика 0 / 5

Является ли «7 — простое число» высказыванием? Напишите да или нет.

Является ли «Выключи свет!» высказыванием? Напишите да или нет.

Является ли «x + 1 > 5» при несвязанном x высказыванием? Напишите да или нет.

Свяжем x = 10 в «x + 1 > 5». Истина или ложь?

В JavaScript выполняется ли ветка if('false')? Напишите да или нет.

Проверь себя
Викторина

Что из перечисленного является высказыванием?

Итог

Высказывание — это повествовательное предложение ровно с одним значением истинности: истина или ложь, никогда оба, никогда ни одно. Команды, вопросы и дела вкуса тест не проходят; ложные утверждения проходят, потому что входное условие — нести значение истинности, а не быть истинным. Предложение со свободной переменной — открытое предложение: само по себе не высказывание, а шаблон, который становится им после связывания каждой переменной значением. Каждое условие if — открытое предложение, написанное на этапе кодирования, которое рантайм замыкает при выполнении. Опасная зона — зазор между высказыванием, которое вы имели в виду, и тем, которое строит машина: неприсвоенная переменная всё равно связывается (с undefined, и 50000 > undefined через NaN даёт false), а языки с приведением типов вычисляют truthiness, и непустая строка «false» ведёт if так же уверенно, как true. Дисциплина: превращайте недоверенный строковый ввод в настоящие були на границе, сравнивайте строго, и всегда умейте сказать, какое именно высказывание вычисляет ваше условие.

Практика

Начни сверху. Задачи идут от простого к сложному: вспомнить факт, применить к случаю, затем senior-уровень. Открой, попробуй, потом открой ответ.

вспомнитьприменитьуглубить0 из 5 завершено

Что-то непонятно?

Задай вопрос по этому уроку. Вопросы анонимны и попадают напрямую автору — урок станет лучше.

Примени это

Примени этот урок в реальном проекте.

хоткеи развернуть
поиск
K
пред. пьеса
k
след. пьеса
j
тиры
t
это меню
?
sources3
expand
  1. 01
  2. 02
  3. 03

Trademarks belong to their respective owners. Editorial reference only.