Каким должен быть язык программирования? Анализ и критика Описание языка Компилятор
Отечественные разработки Cтатьи на компьютерные темы Компьютерный юмор Новости и прочее

Стиль языка программирования

Каждый язык программирования должен иметь свой синтаксис, и этот синтаксис должен быть выдержан в каком-то стиле. С большой долей условности можно выделить несколько стилей:

  • Стиль Си, доминирующий в данный момент. Узнаваем по «{», «}», «if (...)» и «for (i=0; i < N; i++)».
  • Стиль Algol-60, Pascal и более поздних Modula, Oberon и других. Их визитная карточка — бесконечные «begin», «end» и «then» после «if».
  • «Двухмерный» синтаксис Python, сравнительно недавнее изобретение, которое ещё не успело обрести последователей. Оригинальный синтаксис, впервые появившийся в языке ABC, вообще лишён «синтаксического сахара», если не считать пробелов. Перед его изобретателем надо снимать шляпу!
  • Basic, xBase и другие.
  • Языки типа Forth, J и другие write-only языки, на которых легче писать, а не читать. Сплошной «поток сознания». Чтобы испытывать удовольствие от программирования на таких языках, надо впасть в религиозный транс.
  • Прочие, которые не имеют запоминающегося лица. Будь такие языки людьми, им лучше всего работать в разведке — в них нет ничего запоминающегося.

        Ассортимент невелик, особого выбора нет. Можно с этим смириться и не пытаться изобретать велосипед. Но это не в нашем характере!

Придумываем свой стиль

        «Предложения», написанные на каком-то языке программирования, имеют начало и конец. Язык C использует для обозначения начала и конца «{» и «}», Pascal — «begin» и «end». Но беда этих языков в том, что «{» и «begin» находятся не на своём месте, т.е. не в начале.

        В Алгол-68 есть элегантные парные конструкции «if» — «fi», «case» — «esac», «do» — «od». В HTML эта идея воплотилась в <title> — </title>, <span> — </span>. Хочется эти мысли развить дальше и вывести на новый уровень. Конструкции вида (if — if), (title — title) выглядит ещё элегантнее! Лучше, чем if — /if, title — /title.

        Не правда ли, это замечательно смотрится? (if начинает какое-то «предложения», а if) его заканчивает. Обдумывая такое новшество, замечаешь, что ключевое слово (в данном случае «if») повторяется дважды. Расточительно. Можно сократить до (if — ), если число открывающих скобок гарантированно равно числу закрывающих. Поскольку это мы придумываем язык программирования и только от нас зависит, каким ему быть, то всё в наших руках. Мы можем гарантировать такое равенство.

        Следуя такому стилю, мы можем предложить массу конструкций языка в таком «симметричном скобочном» стиле.
(if ...
    ...    )
(for ...
    ...    )
(switch ...
    ...    )
(function ...
    ...    )
(class ...
    ...    )


        Такой стиль немного напоминает стиль языка LISP. Но в LISP большое количество скобок вызвано отсутствием приоритетов операций. Мы же не собираемся отказываться от приоритетов: это усложняет компилятор, но ведь и программист не должен «работать компилятором» (фраза критиков подобных языков). Если сравнивать такой синтаксис с синтаксисом C, то видно, что операторная скобка вынесена вперёд. В C пишется
class {
...
}
мы же предлагаем
(class 
... )
        Помимо переноса операторной скобки, мы выбираем в качестве этих скобок пару обычных скобок «(», «)», а не фигурных «{», «}».

Почему круглые скобки, а не фигурные?

        Аргументы в пользу круглых скобок:
  • Скобки «(», «)» есть на обоих раскладках клавиатуры, а вот символов «{», «}» на русской раскладке нет. Если хотим програмимировать, используя только кириллицу, то должны избегать постоянных переключений раскладок клавиатуры.
  • Единый стиль для «обособления» выражений, которые по своему смыслу отделены от контекста слева и справа:
    a = b * (c + d)
    x = b * (если  y < z; 2 иначе -1)
    
  • Операторные скобки «{» и «}» можно целиком «отдать» под коллекции. Сложилась своего рода традиция представлять множества так: { 0, 1, 2, 3 } Хотя это не очень мешает употреблять «{» и «}» в других синтаксических конструкциях.
  • Этот стиль больше соответствует принятому в математике способу записи.
        Против:
  • Программисты привыкли к фигурным скобкам; ведь они используются в целом ряде языков: C, C++, C#, Java, Perl, PHP, D, Nemerle и многих других.
        Как мы видели, открывающая операторная скобка вынесена вперёд, она предшествует любому другому оператору. Но много ли проку от такого переноса? Да, это поможет нам уже на этапе лексического анализа: сразу ясно, где начинается какой-либо блок программы, а где он заканчивается. Это позволит нашей IDE по мере набора текста проводить лексический анализ и рисовать на экране графический сахар вместо удалённого из языка синтаксического сахара. Введённый программистом текст может быть таким:
(  i = 0
   (  j = 1
      k = (i + j) * 2 )
   y = i * j * k
   (  x += y
      z = 1 / x + y ))
        Или таким, вообще без отступов:
(i = 0
(j = 1
k = (i + j) * 2 )
y = i * j * k
(x += y
z = 1 / x + y ))
        В IDE же это должно примерно выглядеть так:

( i = 0  
 
( j = 1  
  k = (i + j) * 2 )
 
  y = i * j * k  
 
( x += y  
  z = 1 / x + y )
)

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

        Приведённый выше пример, на первый взгляд, не сулит программистам особых удобств. Но если эту идею развить и применить в различных управляющих конструкциях языка программирования, то результат весьма неплох. В этом можно убедиться в следующих статьях, которые описывают         Приведённый выше пример описывает простейшие вложенные друг в друга блоки. Другие, более сложные виды блоков должны иметь более подробный «графический сахар». Фон, окантовка, пиктограммы и любые другие графические элементы оформления должны нам подчёркивать сущность употреблённый конструкции. Поскольку у всех разные вкусы, то графическое оформление должно настраиваться в IDE. Кому-то понравится полный вариант графического оформления, а кому-то подойдёт «олдскульный» аскетизм. Поскольку «графический сахар» существует отдельно от текста программы, то этот тект будет по-разному выглядеть у разных программистов при применении ими индивидуальных настроек IDE.

        Предложенный выше стиль предлагает в качестве синтаксического сахара лишь один лишний символ. Это открывающая скобка «(», которая начинает блоки. Ведь ключевых слов типа «if», «do» достаточно, чтобы начать блок. В таком случае «(» становится лишней. А чем закрывать блок, если обойтись без открывающей скобки? Если «)», теряется симметричность, для её сохранения открывающую скобку «(» лучше оставить. Если применять для окончания блока что-то типа «end if» или «end do», то мы приходим к синтаксису Паскаля. Рассмотрим этот пример:
Мама, я хочу есть! Мы скоро пойдём домой?
Мама зпт я хочу есть воскл Мы скоро пойдём домой вопр
Вторая (которая некрасивая) строка примера как раз и пародирует этот паскалевский стиль.

        Некоторые могут увидеть в вышеописанном скобочном стиле сходство с Lisp с его S-выражениями. Вот пример на Common Lisp:
(defun factorial (x)
   (if (zerop x)
       1
       (* x (factorial (- x 1)))))
        Но в Lisp все операции имеют одинаковый приоритет и в записи выражений используется префиксная нотация. Поэтому в Lisp просто вынуждены отделять выражения друг от друга скобками. Мы же не собираемся лишаться такого удобства, как приоритеты операций. Поэтому можно обойтись без многоэтажных скобочных построений. Но если количество скобок всё-таки велико, то IDE должно разложить нам всё по полочкам, как приведённом выше примере.

Может, за основу лучше взять стиль Python?

        Поставив скобки в начале и в конце какой-то лексической единицы, программист заставляет среду разработки выполнить необходимый отступ автоматически. Этот отступ делается не добавлением необходимого количества пробелов в код программы. Просто IDE меняет координату X для отображаемых строк.

        В Python формированием необходимого отступа занимается программист. Конечно, ему в этом может помочь тестовый редактор: если строка N начиналась на 10-й позиции, то при добавлении строки N+1 редактор автоматически расположит курсор на той же 10-й позиции. Эту позицию программист может изменить, тогда и следующая строка будет начинаться на новом месте. Тем не менее забота об отступах лежит на программисте. Не дай бог ему ошибиться (а человек ошибается гораздо чаще компьютера), и смысл программы может измениться.

        Возьмём уже рассматривавшийся пример:
def DumpOpen(file):
	"""
        Takes one argument (the input file) and opens it for reading
        Returns a list full of data
        """
	openedFile = open(file, "r")
	data = openedFile.readlines()
	cleanedData = []
	for line in data:
		cleanedData.append(line.rstrip())
	openedFile.close()
	return cleanedData
Для отображения этого текста в текстовом редакторе, о котором ведём речь, с нужными отступами, достаточно поставить всего лишь две скобки в начале и конце:
(def DumpOpen(file):
	"""
        Takes one argument (the input file) and opens it for reading
        Returns a list full of data
        """
	openedFile = open(file, "r")
	data = openedFile.readlines()
	cleanedData = []
	for line in data:
		cleanedData.append(line.rstrip())
	openedFile.close()
	return cleanedData)
Это очень маленькая расплата за желание автоматически получить необходимые отступы. Синтаксический сахар крайне минимален.

Недостатки синтаксиса Python.

Синтаксис Python хорош, спору нет. Но и он не идеален, на Солнце всё же есть пятна. В Python есть проблема висячего else:

if условие
// ветка then
if условие
// ветка then
else
// к какому if относится этот else?
Проблему висячего else решают правилом, что он относится к последнему if. Однако с визуальной стороны проблема всё равно остаётся. Де-юре проблема решена, а де-факто, с учётом психологических и эргономических факторов, — нет.

У синтаксиса циклов Python есть известный недостаток. Не существует цикла с проверкой условия в конце, как это делается в Си:

do {
< тело цикла >
while(< условие >);
Ведь что такое блок в Python? Это строка с отступом n пробелов и идущие ниже строки с отступом, в котором пробелов больше n.
< --- n --- > первая строка блока
< --- n+m --- > идущие ниже строки блока
А что получается с циклом с проверкой внизу? Последняя строка блока должна иметь меньший отступ, чем предшествующие строки! Это вступает в противоречие с общим стилем языка. Можно, конечно, изобрести ключевое слово «loop_with_check_below» (цикл с проверкой внизу): сама надпись сделана вверху, а действует внизу
 loop_with_check_below < условие >
< тело цикла >
Ведь в том же Си-шном операторе «for» операторы приращения написаны вверху, а выполняются внизу:
for (< инициализация >;< условие >;< операторы приращения >) {
< тело цикла >
} // а здесь выполняются операторы приращения
Но автор Python решил обойтись без «loop_with_check_below».

Отсутствие циклов с проверкой в конце не смертельно. Эту проверку можно сделать вручную:

for . . .
    < тело цикла >
    if < условие, проверяемое в конце>
       break
Но так теряется лаконичность.

Может, лучше придерживаться привычного синтаксиса Си?

        Да можно вообще ничего не придумывать. Для нас уже написано несколько тысяч языков программирования, выбирай на вкус. По поводу синтаксиса Си можно заметить, что он хоть и прывычен, но не оптимален. Например, при рассмотрении этого текста
  if (условие 1) {  операторы }
  if (условие 2) {  операторы }
  else  { операторы }
может возникнуть вопос: а к какому «if» относится «else»? Для ответа на этот вопос требуется знать стандарт языка. Об интуитивной понятности речи нет. Проблема, растущая аж из Алгола-60.

        В Си-подобных языках есть ещё проблема:
   for (i=0; i<N; i++);		// двоеточие здесь поставлено по ошибке
        <операторы>
которую в языке Rust лечат обязательностью употребления фигурных скобок:
   for (i=0; i<N; i++);		// компилятор выдаст сообщение об ошибке
        {<операторы>}
В Rust надёжность достигается увеличением количества синтаксического мусора.

Что ещё почитать на эту тему

Опубликовано: 2012.09.25, последняя правка: 2022.05.18    20:27

ОценитеОценки посетителей
   █████████████████████ 8 (50%)
   ██████████████ 5 (31.2%)
   ██████ 2 (12.5%)
   ███ 1 (6.25%)

Отзывы

     2015/04/07 04:18, misha_shar53          # 

В данном случае синтаксический сахар порождает дополнительные проблемы. Команды языка имеют разный смысл. Одни являются отдельными независимыми от других команд операторами. Другие почти всегда являются образующими блок команд. Обычно по умолчанию считается что такие команды содержат только одну команду и в этом случае все оптимально. Но в большинстве конструкций как раз наоборот. Я считаю что необходимо по умолчанию принять , что эти команды образуют блок и являются их началом, а концом может быть команда END.
for .... 
...
end;
if ...
...
elseif...
...
else
...
end;

     2015/04/07 16:36, Автор сайта          # 

Т.е. Вы настаиваете на синтаксисе языка Modula-2? А синтаксис Python Вам не нравится? Там даже «end» не надо писать.

     2015/08/02 16:05, Денис Будяк          # 

Интересные рассуждения, похожи на мои. Но давайте вот ещё что учтём: в естественных языках есть избыточность. Например, согласование родов, падежей, чисел между существительным и прилагательным в русском языке, в принципе, избыточны. В английском избыточным является ответ yes, it is. Это не "мусор" и не "сахар". На мой взгляд, это нужно для увеличения надёжности передачи информации. Вот я думаю, что для ЯП тоже нужно определить правильную меру избыточности. С превышением этой меры язык станет громоздким, а с недобором её он станет провоцировать ошибки.

И мне кажется, что вариант if..endif был бы наилучшим с точки зрения надёжности, если бы не многократное увеличение количества букв по сравнению с () или {}. А вот begin..end имеет много букв, но при этом добавляет мало надёжности, поскольку end не позволяет определить, к какому begin он относится.

Есть также вопрос частотности. Недаром начало и конец блока имеют тенденцию быть короткими, поскольку они повторяются очень часто. Но они также должны быть различными, иначе текст будет переполнен скобками, что мы наблюдаем в Лиспе. Закрывающая скобка, так же, как и слово end, не позволяет отличать концы разных блоков между собой.

В clojure задействовали несколько разных видов скобок под разделение разных частей синтаксиса, этот подход достоин рассмотрения.

     2015/08/03 13:19, Автор сайта          # 

Почитайте внимательно — закрывающая скобка однозначно говорит о том, который блок она закрывает:
(if . . . else . . . )
Единственный избыточный символ здесь — открывающая скобка, которая стоит перед ключевым словом, начинающим блок, а не после. Условные выражения, циклы и прочие конструкции целиком находятся внутри скобок, что однозначно определяет начало и конец блока.

Избыточность же предлагается перевести в другое измерение, из текстового (вводимого программистом) в графическое, формируемое IDE. Степень графической избыточности регулируется настройками этой IDE.

     2015/08/04 19:04, Денис Будяк          # 

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

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

     2015/08/05 13:40, Автор сайта          # 

Согласен с тем, что закрывающая скобка подобна «end», который завершает и условные выражения, и циклы, и определения классов, функций, структур и т.д. Некоторые мои коллеги по «придумыванию языков» предлагают задавать однозначное соответствие, дав имена блокам:
label: if . . .end label;
Ведь когда «if» вложены друг в друга, то тогда непонятно, что закрывает очередной встретившийся «endif», не правда ли?

Моё же предложение заключается в том, что блоки должны отличаться не именами или разными обозначениями конца, а разным фоном. Не программист вбивает имена, а IDE сама определяет уровень вложенности блока и выбирает ему соответствующий фон. Посмотрите, как можно оформить циклы.

     2016/04/13 13:37, rst256          # 

if (условие 1) {  операторы }
if (условие 2) { операторы }
else { операторы }

может возникнуть вопос: а к какому «if» относится «else»? Для ответа на этот вопрос требуется знать стандарт языка.

Более 90% опрошенных из целевой группы, не имеющей отношения к программированию, дадут верный ответ. Тогда как среди программистов (не учитывая тех кто знает стандарт языка) % верных ответов будет значительно ниже: полагаю, что 60%-70%. Но причем здесь тонкости психологии, мы же не людей программируем?

Меня вот настораживает фраза: "для ответа на этот вопрос требуется знать стандарт языка". Вы понимаете, что человек, который не знает стандарта языка, и близко не должен подходить к исходному коду. Особенно к коду на Си.

     2016/04/13 19:31, Автор сайта          # 

«Инженер — не тот, кто всё знает, а тот, кто знает, как узнать». Незнание не преступно, преступно нежелание его уменьшать, даже за счёт Гугла.

Висячий «else» плох тем, что об этой особенности надо помнить. Лучше надеяться не на человеческую память, а на логику. Логика умеет воссоздавать элементы, которых не хватает в памяти. Операторы «(if ...)(if ... else ...)» опираются на логику, а «if {...} if {...} else {...}» — на память.

     2016/05/11 12:19, utkin          # 

Я за обязательное использование блоков:
if <условие>
{
if <условие>
{
операторы
}
else
{
операторы
}
}
или
if <условие>
{
if <условие>
{
операторы
}

}
else
{
операторы
}
Все просто и понятно, аналогично всякие циклы, case, switch и так далее. Можно заставить на уровне компилятора обязательно писать блок, даже если в нем всего один оператор.

     2016/05/11 12:20, utkin          # 

Форматировал, форматировал, все пробельные отступы съело :)

     2016/05/11 14:04, Автор сайта          # 

Форматировал, форматировал, да так и не выформатировал :) Подправил.

Ваше видение синтаксиса языка не соответствует сформулированной ранее философии языка. А она провозглашает максимальную лаконичность до той поры, пока она не мешает ясности. Стиль
(if условие
...
else
...)
куда ближе к заявленному. В Вашем предложении, к тому же, есть проблема висячего else, которую ещё Вирт критиковал.

     2016/05/13 19:56, utkin          # 

Посмотрите внимательно. Как раз висячего Else там и нет. Совершенно ясно в каждому примере к какому именно if относится ложная ветвь условия.

     2016/05/15 18:54, Автор сайта          # 

В Вашем конкретном примере его нет. Но предлагаемый Вами синтаксис не исключает его появления: см. «условные операторы».

     2016/05/16 09:39, utkin          # 

Если заставить программиста всегда писать операторные скобки «{-}», «begin-end» в условных выражениях, запретив простую форму для одного оператора, то такой ситуации не возникнет никогда. Возможно, это не вписывается в Вашу концепцию в плане краткости синтаксиса (в том плане, что всегда требуются все эти операторные скобки), но висячих Else там не будет никогда. Тут либо лаконичность, либо понятность. На мой взгляд, ElseIf понятности не добавляет, операторные скобки со своей стороны «растягивают» код вниз, делая его визуально «длинней». Компилятору же, конечно, по барабану, конечный код будет одинаковый, но в моем случае понятней для программиста.

«Предложения», написанные на каком-то языке программирования, имеют начало и конец. Язык C использует для обозначения начала и конца «{» и «}», Pascal — «begin» и «end». Но беда этих языков в том, что «{» и «begin» находятся не на своём месте, т.е. не в начале.

А в чем беда-то собственно? Тема не раскрыта :)? То, что Вы предлагаете, это старый подход в новой оболочке.

Очень просто — ставьте свои скобки в условиях с ELSE и Вы придете ТОЧНО К ТАКОМУ ЖЕ ВИДУ КОДА, что и с begin-end. Только символически обрамление будет относится к другим оператором, СУТИ это вообще не меняет.
Ну вот как я это вижу.
(if <условие>
...оператор
...оператор

...(if <условие>
...оператор
...Else
...(оператор))
Else
(...))
И что тут поменялось? Только скобок стало больше. Это дело вкуса, но фактически Ваш вариант вообще преимуществ никаких не дает. Как задачи операторными скобками решались (форматирования и Else) так и решаются, только теперь скобки стали не операторные, а "круглые".

Проблема висячего Else рождена не скобками, а примитивными языками типа Basic'a. Исторически это было связано с тем, что Basic (и ему подобные) не имел на тот момент операторных скобок и потому ВСЕГДА мог только один оператор в условиях.

P.S. Подправьте, пожалуйста, посты, у меня что-то с Инетом. Это должно было быть одно сообщение.

     2016/05/16 12:34, Автор сайта          # 

Если заставить программиста всегда писать операторные скобки «{-}», «begin-end» в условных выражениях, запретив простую форму для одного оператора, то такой ситуации не возникнет никогда.

Вы заблуждаетесь! Хоть с операторными скобками, хоть без — висячий else имеет место быть:
// Тут висячий else: к какому if относится else?
if условие 1
...
if условие 2
...
else
...

// и тут: к какому if относится else?
if условие 1
{ ... }
if условие 2
{ ... }
else
{ ... }

// и тут тоже: к какому if относится else?
if условие 1
begin ... end
if условие 2
begin ... end
else
begin ... end

// А тут висячего else нет! Есть ясность, к какому if относится else
(if условие 1
...)
(if условие 2
...
else
...)

// И тут есть ясность!
(if условие 1
...
(if условие 2
...
else
...))
Проблема висячего else появилась в Алгол-60 — задолго до Бейсика. Была успешно решена в Алгол-68 конструкциями if ... fi, case ... esac, do ...od. Потом висячий else был успешно продублирован Виртом в Паскале. После осознания им своей ошибки он её больше не повторял: в Модуле и Обероне применяются конструкции if ... endif.

Подправьте, пожалуйста, посты, у меня что-то с Инетом.

Ещё заодно подправил полдюжины запятых.

     2016/05/16 13:08, utkin          # 

Во втором примере Else относится ко второму условию. Иначе второй if нужно запихивать в {}. Это же очевидно. В третьем примере тоже самое.

Я же приводил пример раньше. if..endif это от краткой версии условия, когда допускается ОДИН оператор после then без блока begin-end. В остальных случаях коллизий не наблюдается, так как конец блока однозначно показывает, к какому if принадлежит Else независимо от уровня вложенности.
Там где у Вас есть ясность — то же самое :). Замените Ваши круглые скобки на begin-end. Вообще ничего не поменялось :). Единственно, что Паскаль (по-крайней мере виртовский, надо в Free Pascal испытать) не допускает свободного использования блоков.

Ещё заодно подправил полдюжины запятых.

Это уже издержки общения электронным способом. Я раньше поправлял за собой и других учил. Сейчас уже давно забил на это дело.

     2016/05/16 13:28, utkin          # 

Вот специально проверил — Free Pascal в режиме {$MODE OBJFPC}, то есть в режиме совместимости с Дельфи, допускает свободное неограниченное вложение блоков begin-end. А значит, то что Вы хотите привнести, уже сейчас легко реализуется с помощью имеющихся средств. То есть банальный синтаксический сахар. Зачем городить такой огород? Пишите в Паскале, обрамляйте все операторы begin-end, ничего не изменится :). При желании можно настроить IDEшку, она на каждый Enter будет вставлять Вам пару begin-end. А вот реальная эффективность мне видится сомнительной.

Я для себя же давно взял правило: циклы, переключатели и условия всегда имеют блок, даже если имеют тело в один оператор. Все прекрасно читается и легко определяется. Единственно да, для Вас может быть неудобно писать ручками begin-end, но это не принципиальный вопрос, чем обрамлять, нравится — пишите (-), не нравится — используйте фигурные скобки.

     2016/05/16 18:24, Автор сайта          # 

Это уже издержки общения электронным способом. Я раньше поправлял за собой и других учил. Сейчас уже давно забил на это дело.

Электронный способ тут ни при чём. И издержки ложатся на меня: сижу и исправляю чужие ошибки. В остальном не буду с Вами спорить. Виртовские операторы if ... endif и мои (if ... ) исключают любую неоднозначность. И не надо городить огород что с фигурными скобками, что с begin ... end. Открывающая скобка начинает любой блок, закрывающая его закрывает. Всё логично и лаконично.

     2016/07/14 10:55, alextretyak          # 

Идея со скобочками оригинальная, но большинству программистов, скорее всего, не понравится. Недаром в новомодных языках (Nim, CofeeScript) стараются избавляться от обязательных фигурных скобок.

После осознания им своей ошибки он её больше не повторял: в Модуле и Обероне применяются конструкции if ... endif.

Что-то не видно там endif в списке ключевых слов...

// Тут висячий else: к какому if относится else?
if условие 1
...
if условие 2
...
else
...

Обычно в таких случаях всегда вставляется пустая строка после первого условия:
if условие 1
...

if условие 2
...
else
...
Ну и хорошая IDE подкрашивает блоки кода на Python (и подобном языке) таким образом, что с одного взгляда становится совершенно очевидно, к какому условию какой код относится.

     2016/07/15 17:04, Автор сайта          # 

Понравятся ли парные скобки — это, как говорится, вскрытие покажет. Стиль Питона тоже оригинален и имеет, между прочим, давнюю историю и не сразу был принят. Но нашёл своё признание. Что касается новомодных языков, то среди них есть Rust, в котором фигурные скобки просто обязательны как в условных выражениях, так и в циклах. Так что не всё однозначно.

Хорошо, в Модуле и Обероне используется «END». Перепутал. Но сути дела это не меняет.

Синтаксическая раскраска в IDE — хорошая вещь. Но желательно, чтобы текст был читаем и без неё. Например, вы хотите разместить кусок кода на каком-то форуме. Ну и есть ещё разработчики старой школы, у которых привычка обходиться простыми редакторами.

     2016/08/13 21:45, rst256          # 

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

Проверка строки на сбалансированность — это же тривиальный алгоритм. Все преимущество endif сводится к тому, что незначительно сокращается область поиска места, где была нарушена вложенность. Такой способ экономит максимум 2-3 шага при поиске разрыва, разве это того стоит?

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

if(){ }else{ } — из всех скобок при таком подходе осталась только последняя. В таком случае гораздо логичнее выглядит вариант if ... end и (if ... ). Жаль только, что в последней конструкции не используется пространство между ( и if. Его надо бы обязательно под что-нибудь приспособить, например, добавить туда каких нибудь атрибутов:
(pure if ...)
(reentrant if ... )

     2017/04/15 15:20, utkin          # 

Как вариант, ещё можно разнести два if чисто физически. Один оставить If — форма без Else, второй например Cond (как в Лиспе), будет обязательно с Else. В таком случае можно вкладывать условия друг в друга, не беспокоясь о путанице.

     2021/03/27 03:11, Виталий Монастырский          # 

Думаю, что в реальности такая программа будет просто ужасом летящим на крыльях круглых скобок. Они будут просто везде. Давайте объективно...

У нас и так очень мало знаков для выражения всех тех идей, которые необходимы нашему языку. Даже латинской раскладки не достаточно, чтобы найти знаки для всех необходимых операторов языка. И это в минимальном синтаксисе. Приходится пользоваться комбинациями двух-трех знаков для того, чтобы создать некоторые операторы. Вы же из патриотических соображений хотите перейти на голую русскую раскладку, которая имеет ещё меньше знаков и каким-то мифическим способом заставить среду разработки подставлять Вам эти самые недостающие знаки... Да Вы таким образом только хуже делаете — Вам придется делать больше нажатий клавиш для того, чтобы указать IDE где Вам и что нужно поставить. Краткое латинское # будет превращаться в (*-+).

Нет, считаю этот подход не разумным и вынужденным. Думаю здесь реальных варианта только два.

Первый — продолжаем упорно программировать на латыни, ибо там самый большой набор дополнительных знаков.

Второй — разрабатываем и выпускаем новые виды клавиатур с большим количеством клавиш, так как современными могут быть довольны только жители англоязычных стран.

Весь остальной мир страдает от нехватки клавиш. У меня такой проект есть и он преследует ещё пару дополнительных целей. Да, это не быстро, но со временем позволит провести на рынок новый тип расширенных клавиатур, куда более удобных для многих других языков мира, окромя ангельского. Ну вот тогда можно будет и поговорить о полностью русскоязычном программировании, когда у нас под рукой будут и квадратные, и фигурные скобки, и с пупырышками, и с рюшечками...

А сейчас, я считаю, особенно, если речь идет не об индивидуальном проекте типа "язык для себя любимого", нужно остановиться на латинской раскладке, как базовой, заложить в язык перспективы мультиязычности, и не заморачиваться до тех пор, пока не будет решена фундаментальная аппаратная проблема. На практике хуже будет — гарантирую.

     2021/03/27 18:37, Автор сайта          # 

Есть хорошая идея, как на обычной клавиатуре, не переключаясь с русской раскладки, набирать символы латинской раскладки. Вот её воплощение для Web, автор — Денис Будяк.

     2022/05/20 00:15, Неслучайный читатель          # 

Скобочный стиль (if . . . ) можно заменить на альтернативный. В скобочном стиле одна из скобок (как правило, открывающая) лишняя и нужна лишь для симметрии, чтобы парность скобок была согласована.

Можно попробовать заменить закрывающую скобку чем-то ещё, чтобы избавиться от лишней открывающей. Наиболее подходящий (вроде бы!) для этого символ — точка. Точка должна стоять в конце строки оператора, то есть перед символом «перевод строки» или точкой с запятой:
if <условие>
<операторы>
else
<операторы>
. // точка заканчивает условный оператор

if <условие> <операторы>.; if <условие> <операторы>. // точка в конце строки

while <условие> <операторы>. // или

while <условие>
<операторы>
.
Возможен синтаксический сахар, подобно «if» — «endif» можно придумать такой конец операторов:
if <условие>
<операторы>
else
<операторы>
if. // точка заканчивает условный оператор
if <условие> <операторы> if.; if <условие> <операторы> if. // точка в конце строки

while <условие> <операторы> while. // или

while <условие>
<операторы>
while.
Но в этом случае напрашивается такая аналогия из html:
while <условие>
<операторы>
/while
Лексеру будет нетрудно отличить точку, которой заканчивается оператор от точки, которая используется для членов структур
// Псевдо Си
time.sec++;
if (time.sec >= 60) {
time.sec = 0;
time.min ++;
. . .
}
или в константах
x = 2.0;
Недостатки такого синтаксиса:
  • Точка — едва заметный символ. Нет символа, который бы был меньше её. Визуальная незаметность может стать источником недоразумений, то есть ошибок.
  • Непонятно, как быть с циклом с проверкой внизу.
Если призадуматься, чем этот синтаксис
while <условие>
<операторы>
/while
лучше питоновского, то убедительных ответов нет. И если точку, которая заканчивает оператор, трудно заметить
while <условие>
<операторы> .
то может лучше обойтись без неё? Да, в Питоне надо заботиться об отступах, а тут не надо. Так что всё имеет свои плюсы и минусы.

Добавить свой отзыв

Написать автору можно на электронную почту
mail(аt)compiler.su

Авторизация

Регистрация

Выслать пароль

Карта сайта


Содержание

Каким должен быть язык программирования?

Анализ и критика

●  Устарел ли текст как форма представления программы

●  Русский язык и программирование

●  Многоязыковое программирование

Синтаксис языков программирования

Синтаксический сахар

●  Некоторые «вкусности» Алгол-68

●  «Двухмерный» синтаксис Python

●  Почему языки с синтаксисом Си популярнее языков с синтаксисом Паскаля?

●  Должна ли программа быть удобочитаемой?

●  Стиль языка программирования

●  Тексто-графическое представление программы

●●  Разделители

●●  Строки программы

●●  Слева направо или справа налево?

●  Комментарии

●●  Длинные комментарии

●●  Короткие комментарии

●●  Комментарии автоматической генерации документации

●●  Нерабочий код

●●  Помеченные комментарии

●  Нужны ли беззнаковые целые?

●  Шестнадцатиричные и двоичные константы

●  Условные операторы

●  Переключатель

●  Циклы

●●  Продолжение цикла и выход из него

●  Некошерный «goto»

●  Изменение приоритетов операций

●  Операции присвоения и проверки на равенство. Возможно ли одинаковое обозначение?

●  Так ли нужны операции «&&», «||» и «^^»?

●  Постфиксные инкремент и декремент

●  Почему в PHP для конкатенации строк используется «.»?

●  Указатели и ссылки в C++

●●  О неправомерном доступе к памяти через указатели

●  Обработка ошибок

●  Функциональное программирование

●●  Нечистые действия в чистых функциях

●●  О чистоте и нечистоте функций и языков

●●  Макросы — это чистые функции, исполняемые во время компиляции

●●  Хаскелл, детище британских учёных

●●  Измеряем замедление при вызове функций высших порядков

●●  C vs Haskell: сравнение скорости на простом примере

●●  Уникальность имён функций: за и против

●●  Каррирование: для чего и как

●●  О тестах, доказывающих отсутствие ошибок

●  Надёжные программы из ненадёжных компонентов

●●  О многократном резервировании функций

●  Использование памяти

●  Почему динамическое распределение памяти — это плохо

●  Как обеспечить возврат функциями объектов переменной длины?

●●  Типы переменного размера (dynamically sized types, DST) в языке Rust

●●  Массивы переменной длины в C/C++

●●  Размещение объектов в стеке, традиционный подход

●●  Размещение объектов переменной длины с использованием множества стеков

●●  Размещение объектов переменной длины с использованием двух стеков

●●  Реализация двухстековой модели размещения данных

●●  Двухстековая модель: тесты на скорость

●●  Изменение длины объекта в стеке во время исполнения

●●  Размещение объектов переменной длины с использованием одного стека

●  Можно ли забыть о «куче», если объекты переменной длины хранить в стеке

●  Безопасность и размещение объектов переменной длины в стеке

●  Массивы, структуры, типы, классы переменной длины

●  О хранении данных в стеке, вместо заключения

●  Реализация параметрического полиморфизма

Описание языка

Компилятор

Отечественные разработки

Cтатьи на компьютерные темы

Компьютерный юмор

Новости и прочее




Последние отзывы

2024/04/23 15:57 ••• Ivan
Энтузиасты-разработчики компиляторов и их проекты

2024/04/23 00:00 ••• alextretyak
Признаки устаревшего языка

2024/04/21 00:00 ••• alextretyak
Постфиксные инкремент и декремент

2024/04/20 21:28 ••• Бурановский дедушка
Русский язык и программирование

2024/04/07 15:33 ••• MihalNik
Все языки эквивалентны. Но некоторые из них эквивалентнее других

2024/04/01 23:39 ••• Бурановский дедушка
Новости и прочее

2024/04/01 23:32 ••• Бурановский дедушка
Русской операционной системой должна стать ReactOS

2024/03/22 20:41 ••• void
Раскрутка компилятора

2024/03/20 19:54 ••• kt
О многократном резервировании функций

2024/03/20 13:13 ••• Неслучайный читатель
Надёжные программы из ненадёжных компонентов

2024/03/07 14:16 ••• Неслучайный читатель
«Двухмерный» синтаксис Python

2024/03/03 16:49 ••• Автор сайта
О неправомерном доступе к памяти через указатели

2024/02/28 18:59 ••• Вежливый Лис
Про лебедей, раков и щук