Поговори с машиной: как Ваш компьютер и телефон понимают, чего Вы от них хотите

Что происходит, когда Вы нажимаете цифры в калькуляторе или набираете сообщение в мессенджере? Молодой ученый Сергей Лисицын рассказал, как устроены переводчики с человеческого языка на машинный, а именно компиляторы, и как принцип их работы может помочь нам выучить два языка и больше.





Что нужно знать прежде всего

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

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

Для всех остальных языков вроде C++ или Java нужны переводчики, которые перепишут нашу программу в понятную компьютеру форму. Одна из разновидностей таких переводчиков и называется компилятором.

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

Первый переводчик в СССР — или, как его тогда называли, ПП, программирующая программа — был написан еще в 1954 году. Сегодня переводчики бывают самые разные: бесплатные для скачивания и редактирования (или с открытым исходным кодом) и платные, которые корректировать нельзя.

 

Вжиться в роль компилятора

Переводить язык программы на язык компьютера можно по-разному. Существует вариант брать отдельно каждую строчку и объяснять ее компьютеру, однако часто правильнее прочитать всю программу целиком, обработать ее, сделать более оптимальной для понимания компьютером, а затем уже оформить в виде машинного кода. Переводчики первого типа называются интерпретаторами, а второго — компиляторами.

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





Однако стоит пояснить еще один крайне важный момент. Если вы переводчик-интерпретатор, то для каждого прочтения перевода вы переписываете каждую строчку заново. Иначе говоря, книги на полке с финальным переводом с корейского языка на русский у вас не остается.

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

 

Дальше — больше

Что же находится внутри компилятора, или как работают профессиональные переводчики? Условно компилятор можно разделить на три части: frontend, middle-end и backend. Остановимся подробно на каждой из них.

Frontend работает непосредственно с языком, с которого мы хотим перевести книгу. И это безумно удобно (позже читатель поймет почему). Компилятор производит лексический, синтаксический и семантический анализ. Говоря языком книг, здесь предложения разбиваются на слова, находится сказуемое и подлежащее, устанавливается связь между частями предложения и всеми остальными предложениями.

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

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

Бывает, что перед вами не стоит задача редактировать автора. Более того, если вы считаете себя недостаточно умным, чтобы говорить ему, что нужно, а что нет, вы можете не редактировать текст совсем. То есть компьютер может не оптимизировать и никак не менять код автора, переведенный на промежуточное представление, может делать это с какими-то ограничениями, а может — полностью по своему усмотрению. Оптимальный путь зависит от ситуации.

Совершенно неоптимизированный код, особенно написанный новичками, часто оказывается медленным и неэффективным. Поэтому какие-то элементы оптимизации вводить рекомендуют. Но полностью оптимизировать код тоже не всегда стоит — например, на языке C, где программист может распоряжаться памятью по своему усмотрению, учитывая последующие задачи: это фактор, который компьютер не может предусмотреть.





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

 

Компиляторы как суть прогресса

В мире постоянно создаются новые и дорабатываются старые языки. Постоянно совершенствуется и архитектура компьютера — то, каким образом машина воспринимает и считывает информацию. Получается, что любые изменения в архитектуре или языках требуют заново переписывать компилятор? Нет.

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

Аналогично ситуация выглядит и в случае изменения архитектуры. Так как именно последний этап, backend, работает с переводом из промежуточного представления в финальный код, изменения только его части вполне достаточно, чтобы компилятор заработал и под другой архитектурой. Возвращаясь к аналогии с литературными переводчиками, при изучении нового языка, например иврита, достаточно запомнить перевод всех слов с иврита на французский, а потом переводить их на любой другой язык. Это крайне удобно. С такой ситуацией сталкивался любой человек, имеющий опыт изучения более двух языков.

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

Автор: Сергей Лисицын  

P.S. И помните, всего лишь изменяя свое потребление — мы вместе изменяем мир! ©

Присоединяйтесь к нам в Facebook , ВКонтакте, Одноклассниках

Источник: theoryandpractice.ru/posts/12435-compilers