Про точку с запятой

| Нет комментариев

Точка с запятой в перле необязательна, если она приходится на конец блока:

sub doit {
    say 123
}

В отличие от, например, C++, где аналогичная конструкция вызовет ошибку компиляции:

int main() {
   return 0
}

s.cpp: In function 'int main()':
s.cpp:3: error: expected ';' before '}' token

Различие здесь в том, чем точка с запятой является с точки зрения языка. В перле это разделитель инструкций, в C++ — признак окончания выражения.

В JavaScript ситуация еще интереснее: там точки с запятой допустимо опускать не только в конце блока, но и в конце строки:

x += id.value
alert(x)

При этом разрешено продолжать выражение на следующей строке:

x +=
   id.value
alert(x)

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

Промежуточное резюме: на C++ компилятор строг настолько, что просит явно сообщать, где заканчивается очередная порция кода, а на JavaScript допускаются вольности, но за счет дополнительных действий во время анализа кода.

В перле иногда очень соблазнительно не только опускать точку с запятой в конце блока, но и ключевое слово return в последней инструкции подпрограммы:

sub add {
    my ($a, $b) = @_;
    $a + $b
}

Результат выражения $a + $b — последнее значение, вычисленное в теле подпрограммы — считается результатом, который и нужно передать вызывающему коду.

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

Ситуация очень похожа на рекомендацию ставить запятую после последнего элемента при объявлении хеша:

my %x = (
    alpha => 'a',
    beta => 'b',
);

Перл создает в хеше ровно два элемента, но запятая помогает при добавлении новых элементов (которые часто добавляются копированием и вставкой последней строки). Этот фокус не проходит с яваскриптом: если поставить запятую после последнего элемента массива, то будет создан еще один элемент со значением undefined.

В перле отсутствие точки с запятой в конце строки может привести к тому, что ее отсутствие не будет замечено, когда после этой строки потребуется дописать новые инструкции:

sub add {
    my ($a, $b) = @_;
    $a + $b
    warn $a;
}

Даже на время отладки не хочется искажать написанный ранее код, поэтому пропущенная точка с запятой просится в начало строки:

sub add {
    my ($a, $b) = @_;
    $a + $b
;    warn $a;
}

Такие трюки с пропущенной запятой — один из приемов, которые малыми шажками ведут код к read-only-модели.

Например, продолжая такую идеологию возможно было бы записать функцию так:

sub add {
    shift() + shift
}

Но лучше так не делать. Или только ради развлечения и изучения возможностей языка.

Комментировать

Страницы

  • img

Об этой записи

Сообщение опубликовано 11.09.2009 22:37. Автор — ash.

Предыдущая запись — Croatian Perl Workshop 2008 — что было за кадром

Следующая запись — Far East Perl 2008 — что было до и после

Смотрите новые записи на главной странице или загляните в архив, где есть ссылки на все сообщения.