Как стать автором
Обновить

К вопросу об идентификаторах

Время на прочтение4 мин
Количество просмотров672
Разрабатываем мы язык тут потихоньку. И кроме огромного количества синтаксических и семантических вопросов приходится решать и вопросы интерфейсные (так их можно назвать): насколько секси выглядит код, насколько быстро человек врубается в написанное и так далее. Так вот один из таких вопросов — это вопрос о том, из каких символов позволить составлять программисту идентификаторы, и делать ли их case sensitive. Вопрос нетривиальный, и вот почему:


Небольшой interscriptum :). Вообще, я почти всегда писал в стиле this_is_the_variable, и если бы я не видел код Plan9, то у меня бы и не возникло вопросов: мы бы в языке сделали идентификаторы «как в Си», но так уж случилось, что Plan9 я почитал, и у меня вызвал острое непонимание тот факт, что мне понимать исходники Plan9 гораздо проще, чем исходники Linux. И это при том, что в Plan9 переменные, обычно именуются так: wrblock, lzput, hufftabinit, quotefmtinstall, а в Linux так: spin_lock_irqsave, rt_mutex_adjust_prio_chain, dma_chan_busy, seq_puts. Почему так? При попытках дать себе объяснение, возникли некоторые мысли, которые, смею надеяться, будут полезны кому-нибудь.

Как известно, есть несколько популярных лексических схем именования переменных:
this_is_the_var
thisIsTheVar
thisisthevar

Так вот, какая из них лучше для восприятия кода — вопрос открытый. Есть стандартная точка зрения: this_is_the_var — вариант наилучший, потому что сразу можно разобрать слова, из которых составлен идентификатор. Но, хорошо это или плохо — вопрос спорный. Потому что…

Во-первых, должны ли мы стремится к выражению смысла идентификатора через описание абстрагируемого им процесса? Например, все знают, что printf — это printf, и никто особо не задумывается о том, что это на самом деле: print_values_with_formatting_on_standart_output. Или, все знают, что stdout — это stdout. Имеет ли смысл идентификатора закладывать в его названии, или для восприятия и написания текста программы лучше когда смысл идентификатора выводится из текста программы? И если верно второе, то наоборот, не мешают ли длинные названия восприятию текста? Кроме того, не мешают ли длинные названия пониманию текста? Ведь, в случае this_is_the_variable программисту приходится работать на двух уровнях: оценивать смысл словосочетания, которым обозначен идентификатора, и оценивать связь самого идентификатора со всей программой. Как примеры:

while((current_character = getc(stdin)) != EOF)
{
	do_something();
}

и
while((с = getc(stdin)) != EOF)
{
	do_something();
}


Примеры простые, но, в первом случае нужно сначала прочитать current_character, понять, что это текущий символ, потом связать это понимание с тем, как работает getc, после чего каждый раз, когда в тексте встречается символ current_character, читающий должен оценивать у себя в голове эту ментальную конструкцию (это никакой не научный факт, а просто моя — неспециалиста гипотеза). Во втором примере такого не происходит, смысл c 'иероглифический', то есть, он заложен в идентификатор не апелляцией к внешнему языку, а прямо здесь, в тексте (можно сказать изображении, поэтому и иероглифический) программы. Полезно ли это? Мне лично не известно, но, вполне вероятно, задумываться об этом стоит (?).

Во-вторых, и это дополняет предыдущее, идентификаторы в стиле this_is_the_variable просто сбивают мозг с восприятия идентификатора как единого целого. Рассматривая GitHub, например, в некоторых случаях я просто относительно долго читал строчку по слогам, пытаясь понять, где же начинается объявление переменной. Или можно сравнить: lpfnWndProc с window_event_handling_procedure_ptr, что воспринимается, как единое целое?

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

Всё это приводит к вопросу: а нужно ли позволять в идентификаторах использовать подчёркивание, стимулируя тем самым программистов к многословию и к многобуквию?

Другой вопрос: а должны ли быть идентификаторы чувствительными к регистру? Общепринятый ответ на этот вопрос: да, должны. Но тут тоже можно высказать сомнения: такие, например. Нечувствительность к регистру даёт больше свободы во взаимодействии программистов: одному удобнее писать lpfnWndProc, а другому lpfwndproc, третий же помечает различным внешним видом for — различные виды циклов: например foR — это пробег по списку, а FOR — это итерационный поиск численного решения.

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

Разбираясь с различными спорами и рассуждениями вокруг этой темы, я наткнулся на замечание о том, что делать идентификаторы case insensitive и без подчёркиваний плохо, потому что есть огромное количество библиотек, которые написаны на Си (или Ассемблере), для которых чувствительность к регистру и underscore важны. Но в нашем языке будет возможность создавать такие идентификаторы: ID.'вам нужен такой идентификатор? они есть у нас!', и их можно будет использовать для связи с библиотеками на C и любом другом case sensitive языке. Так стоит ли делать переменные с подчёркиванием и чувствительностью к регистру? И не будет ли отсутствие этих возможностей способствовать написанию лучшего кода, и лучшему потом его пониманию?

Такой вот текст получился. Спасибо за внимание.

P.S. Вот что писал о правилах программирования на Си один из разработчиков Plan9 — Rob Pike: www.lysator.liu.se/c/pikestyle.html

Теги:
Хабы:
Если эта публикация вас вдохновила и вы хотите поддержать автора — не стесняйтесь нажать на кнопку
Всего голосов 8: ↑4 и ↓40
Комментарии10

Публикации

Ближайшие события