Страница:
Из первоязыков еще стоит упомянуть Cobol (1959), чудовищный как язык, но крайне успешный как платформа для создания бизнес-приложений. Что показательно.
Следующее десятилетие — эпоха экспериментов на ниве создания «самого лучшего языка». В широком использовании продолжают царствовать Fortran/Cobol, к ним добавляются языки класса «все-все-все-в-одном» PL/I и CPL [В этот же период созданы Lisp и Snobol, речь о которых — в следующей статье], тяжелые и для изучения, и для реализации. В районе 70-х происходит первая «большая чистка»: парк компьютеров растет лавинообразно, возникает необходимость в языках простых и практичных, которые легко выучить, легко реализовать под различные аппаратные платформы, легко писать и читать код; при этом возрастает количество «программ-ради-программ», не решающих некую бизнес-задачу, а облегчающие работу с самим компьютером.
Си вкупе с Unix; разномастные Бейсики как встраиваемые языки для первых домашних (и мелких недомашних) компьютеров; Pascal в Apple II/Apple III, чуть позже Паскали от фирмы Borland для простого написания программ под DOS, Windows — все это языки весьма простые [Basic, в частности, настолько прост, что даже структурного программирования в нем не было. Зато это давало возможность сделать крайне нетребовательную к ресурсам реализацию языка, что поспособствовало его распространению на «несерьезных» компьютерах. С ростом ресурсов этих компьютеров (и запросов программистов) структурность в Бейсике появилась (в середине 80-х)] и практичные; это, по большому счету, те языки, с которыми программирование стало действительно массовым занятием.
По мере расширения круга задач, решаемых на «простых» языках, количества повторно используемых библиотек и «времени жизни» этих библиотек стали возникать концепции более сложного структурирования кода. Самая популярная из них — объектно-ориентированное программирование; совмещение концепций «набора процедур и данных (модуля)» и «типа данных со сложной внутренней структурой» дало понятие «класса» и «объекта» [Большая часть концепций классического ООП была разработана в середине 60-х в рамках работы над языком Simula (Ole-Johan Dahl, Kristen Nygaard). Судьба его достаточно близка к судьбе Алгола: разработанные концепции были приняты и воплощены во многих успешных проектах, но сам язык использовался весьма ограниченно]. Мэйнстримовая разновидность ООП [О более радикальном наборе концепций с тем же названием — в следующей статье.9 Интересно, что другая разновидность «объектно-ориентированного C», известная под именем Objective C и зачастую воспринимаемая как забавный курьез, была языком вполне постмодернистским, смешавшим концепции классического C и модернистского Smalltalk. Распространение этого (и других «странных») языков исключительно в мире Apple весьма показательно] — естественное эволюционное развитие структурно-императивного подхода. Неудивительно, что и объектно-ориентированные языки, принятые «широкими массами», были естественным развитием все тех же C, Pascal, Basic — Visual Basic, C++ [Интересно, что другая разновидность «объектно-ориентированного C», известная под именем Objective C и зачастую воспринимаемая как забавный курьез, была языком вполне постмодернистским, смешавшим концепции классического C и модернистского Smalltalk. Распространение этого (и других «странных») языков исключительно в мире Apple весьма показательно], Object Pascal (позже Delphi).
Далее мэйнстримовая, структурная парадигма некоторое время дополнялась (например, шаблонами C++, позволяющими писать «обобщенные» классы и «обобщенные» алгоритмы). Но картина мира вновь начала меняться, что привело к очередной «большой чистке» языков и смене расклада, двадцать лет казавшегося незыблемым. По своей важности эти перемены близки к событиям, в результате которых Fortran, Cobol и PL/I сменились Cи, Бейсиком и Паскалем.
Причин тому было много, так что нельзя выделить одну, главную. Важнейшие, видимо, таковы: рост производительности железа, с одной стороны, и востребованности программистов (даже неквалифицированных) — с другой. Поскольку надежность софта становится важнее его быстродействия [В определенных, естественно, пределах. Тем не менее некогда одна из важнейших целей разработчиков C++ — «почти бесплатность (по производительности)» новых концепций — стала анахронизмом]; возникновение и популяризация компьютерных сетей «для всех» (в том числе и Интернета/веба), в результате чего «сетевое программирование» стало всеобщей деятельностью. С точки зрения пресловутых «парадигм» программирования важнейшая тенденция «нового времени» — компонентно-ориентированное программирование: независимые друг от друга компоненты могут быть написаны на разных языках, поставляться в скомпилированной форме, заменяться на лету, взаимодействие между ними должно быть легким, надежным и масштабируемым.
Попытки использования «компонентного» стиля без смены языка (COM/OLE, CORBA) выявили некоторые концептуальные трудности; собственно, попытка создать целостное решение этих трудностей и породила платформы Java и .Net [История Java, впрочем, довольно извилиста; в разное время у Sun было множество разных версий насчет «что это мы делаем и зачем оно надо». Тем не менее на сегодняшний день платформа Java — более или менее прямой конкурент и аналог .Net.]. Их свойства (богатая стандартная библиотека, автоматическое управление временем жизни объектов, наличие виртуальной машины и т. п.) — прямой ответ на те вызовы, которые бросает компонентность. Что же касается языков Java и C# [Заметим, что платформа .Net принципиально многоязычна; Java, изначально бывшая «платформой для одного языка», сегодня движется в том же направлении. Тем не менее мы-то здесь рассматриваем в первую очередь историю языков программирования], то их архитектура и дала мне основания назвать происшедшее «второй большой чисткой»: как в свое время C, эти языки стремились вобрать в себя все «хорошие идеи» своего времени, но вдобавок избавиться от наследственной сложности, неоднозначности и других проблем, свойственных C++/Delphi/Visual Basic. Первые версии обоих новых языков таки были проще предшественников, но дальнейшее развитие снова пошло по спирали накопления возможностей и впитывания концепций. Сегодняшний C# — сложный, лаконичный и мультиконцептуальный язык; Java — консервативнее в своем стремлении к простоте и однозначности, но постепенно подбирается к той же планке.
Перечисленные языки — неотъемлемая часть истории развития средств написания программ; тем не менее всеобщая популярность обошла их стороной.
Линейка Pascal. Дело в том, что тот Паскаль, который стал популярным в руках фирмы Borland и который многие из нас учили в школе, от изначальной концептуально-чистой разработки Никлауса Вирта отличается довольно сильно, причем одни считают суть этого отличия «практичностью», другие — концептуальной грязью. Сам Вирт придерживается последнего мнения; будучи невысокого мнения о целостности и чистоте вообще всех широко используемых языков, Вирт и его ученики разработали несколько своих, «чистых и красивых» (Oberon, Modula, Zonnon).
Eiffel. Судьба Эйфелей и их создателя Бертрана Мейерса похожа на судьбу «настоящих Паскалей». Мейерс, как и Вирт, достаточно амбициозен в продвижении своих идей (в основном — об объектно-ориентированном программировании), называя их «единственно правильными»; распространен Eiffel нешироко, влияние его огромно.
Ada. Наконец, создатели самых разных языков программирования среди «вдохновляющих» называют язык Ada, разработанный в 80-х под руководством Пентагона. В каком-то смысле он был аналогом PL/I (не слишком удачная попытка собрать все возможные концепции в одном языке), но некоторые элементы Ada (в частности, ее система типов) оказали большое влияние на мышление авторов других языков.
Во-первых, это юниксовский sh и его производные (bash, ksh, csh и далее со всеми остановками). Первые оболочки *nix-систем ведут свой род от Алгола; юниксовский подход к объединению маленьких самостоятельных утилит считается одним из первых примеров компонентно-ориентированного программирования. Среди отдаленных потомков sh — как постмодернистский Perl (о нем мы еще поговорим), так и безусловно классицистический Tcl (а о нем не будем).
Во-вторых, язык веб-программирования PHP — тоже вполне популярен и вполне классицистичен. Его часто называют среди наследников Perl, но от последнего PHP перенял в основном способ именования переменных и область применения; в остальном первые PHP — это почти чистый C (вплоть до имен библиотечных функций). Небывалый успех PHP — это успех не языка программирования (часто критикуемого за концептуальную уродливость), а успех утилиты для легкой разработки веб-приложений. Так и повелось.
http://research.microsoft.com/~simonpj/papers/excel/index.htm).
Следующее десятилетие — эпоха экспериментов на ниве создания «самого лучшего языка». В широком использовании продолжают царствовать Fortran/Cobol, к ним добавляются языки класса «все-все-все-в-одном» PL/I и CPL [В этот же период созданы Lisp и Snobol, речь о которых — в следующей статье], тяжелые и для изучения, и для реализации. В районе 70-х происходит первая «большая чистка»: парк компьютеров растет лавинообразно, возникает необходимость в языках простых и практичных, которые легко выучить, легко реализовать под различные аппаратные платформы, легко писать и читать код; при этом возрастает количество «программ-ради-программ», не решающих некую бизнес-задачу, а облегчающие работу с самим компьютером.
Си вкупе с Unix; разномастные Бейсики как встраиваемые языки для первых домашних (и мелких недомашних) компьютеров; Pascal в Apple II/Apple III, чуть позже Паскали от фирмы Borland для простого написания программ под DOS, Windows — все это языки весьма простые [Basic, в частности, настолько прост, что даже структурного программирования в нем не было. Зато это давало возможность сделать крайне нетребовательную к ресурсам реализацию языка, что поспособствовало его распространению на «несерьезных» компьютерах. С ростом ресурсов этих компьютеров (и запросов программистов) структурность в Бейсике появилась (в середине 80-х)] и практичные; это, по большому счету, те языки, с которыми программирование стало действительно массовым занятием.
По мере расширения круга задач, решаемых на «простых» языках, количества повторно используемых библиотек и «времени жизни» этих библиотек стали возникать концепции более сложного структурирования кода. Самая популярная из них — объектно-ориентированное программирование; совмещение концепций «набора процедур и данных (модуля)» и «типа данных со сложной внутренней структурой» дало понятие «класса» и «объекта» [Большая часть концепций классического ООП была разработана в середине 60-х в рамках работы над языком Simula (Ole-Johan Dahl, Kristen Nygaard). Судьба его достаточно близка к судьбе Алгола: разработанные концепции были приняты и воплощены во многих успешных проектах, но сам язык использовался весьма ограниченно]. Мэйнстримовая разновидность ООП [О более радикальном наборе концепций с тем же названием — в следующей статье.9 Интересно, что другая разновидность «объектно-ориентированного C», известная под именем Objective C и зачастую воспринимаемая как забавный курьез, была языком вполне постмодернистским, смешавшим концепции классического C и модернистского Smalltalk. Распространение этого (и других «странных») языков исключительно в мире Apple весьма показательно] — естественное эволюционное развитие структурно-императивного подхода. Неудивительно, что и объектно-ориентированные языки, принятые «широкими массами», были естественным развитием все тех же C, Pascal, Basic — Visual Basic, C++ [Интересно, что другая разновидность «объектно-ориентированного C», известная под именем Objective C и зачастую воспринимаемая как забавный курьез, была языком вполне постмодернистским, смешавшим концепции классического C и модернистского Smalltalk. Распространение этого (и других «странных») языков исключительно в мире Apple весьма показательно], Object Pascal (позже Delphi).
Далее мэйнстримовая, структурная парадигма некоторое время дополнялась (например, шаблонами C++, позволяющими писать «обобщенные» классы и «обобщенные» алгоритмы). Но картина мира вновь начала меняться, что привело к очередной «большой чистке» языков и смене расклада, двадцать лет казавшегося незыблемым. По своей важности эти перемены близки к событиям, в результате которых Fortran, Cobol и PL/I сменились Cи, Бейсиком и Паскалем.
Причин тому было много, так что нельзя выделить одну, главную. Важнейшие, видимо, таковы: рост производительности железа, с одной стороны, и востребованности программистов (даже неквалифицированных) — с другой. Поскольку надежность софта становится важнее его быстродействия [В определенных, естественно, пределах. Тем не менее некогда одна из важнейших целей разработчиков C++ — «почти бесплатность (по производительности)» новых концепций — стала анахронизмом]; возникновение и популяризация компьютерных сетей «для всех» (в том числе и Интернета/веба), в результате чего «сетевое программирование» стало всеобщей деятельностью. С точки зрения пресловутых «парадигм» программирования важнейшая тенденция «нового времени» — компонентно-ориентированное программирование: независимые друг от друга компоненты могут быть написаны на разных языках, поставляться в скомпилированной форме, заменяться на лету, взаимодействие между ними должно быть легким, надежным и масштабируемым.
Попытки использования «компонентного» стиля без смены языка (COM/OLE, CORBA) выявили некоторые концептуальные трудности; собственно, попытка создать целостное решение этих трудностей и породила платформы Java и .Net [История Java, впрочем, довольно извилиста; в разное время у Sun было множество разных версий насчет «что это мы делаем и зачем оно надо». Тем не менее на сегодняшний день платформа Java — более или менее прямой конкурент и аналог .Net.]. Их свойства (богатая стандартная библиотека, автоматическое управление временем жизни объектов, наличие виртуальной машины и т. п.) — прямой ответ на те вызовы, которые бросает компонентность. Что же касается языков Java и C# [Заметим, что платформа .Net принципиально многоязычна; Java, изначально бывшая «платформой для одного языка», сегодня движется в том же направлении. Тем не менее мы-то здесь рассматриваем в первую очередь историю языков программирования], то их архитектура и дала мне основания назвать происшедшее «второй большой чисткой»: как в свое время C, эти языки стремились вобрать в себя все «хорошие идеи» своего времени, но вдобавок избавиться от наследственной сложности, неоднозначности и других проблем, свойственных C++/Delphi/Visual Basic. Первые версии обоих новых языков таки были проще предшественников, но дальнейшее развитие снова пошло по спирали накопления возможностей и впитывания концепций. Сегодняшний C# — сложный, лаконичный и мультиконцептуальный язык; Java — консервативнее в своем стремлении к простоте и однозначности, но постепенно подбирается к той же планке.
Заполняя пропуски: Концепции
Некоторые языки программирования, близкие «классицизму», но не попавшие в статью, весьма достойны упоминания — хотя бы совсем краткого.Перечисленные языки — неотъемлемая часть истории развития средств написания программ; тем не менее всеобщая популярность обошла их стороной.
Линейка Pascal. Дело в том, что тот Паскаль, который стал популярным в руках фирмы Borland и который многие из нас учили в школе, от изначальной концептуально-чистой разработки Никлауса Вирта отличается довольно сильно, причем одни считают суть этого отличия «практичностью», другие — концептуальной грязью. Сам Вирт придерживается последнего мнения; будучи невысокого мнения о целостности и чистоте вообще всех широко используемых языков, Вирт и его ученики разработали несколько своих, «чистых и красивых» (Oberon, Modula, Zonnon).
Eiffel. Судьба Эйфелей и их создателя Бертрана Мейерса похожа на судьбу «настоящих Паскалей». Мейерс, как и Вирт, достаточно амбициозен в продвижении своих идей (в основном — об объектно-ориентированном программировании), называя их «единственно правильными»; распространен Eiffel нешироко, влияние его огромно.
Ada. Наконец, создатели самых разных языков программирования среди «вдохновляющих» называют язык Ada, разработанный в 80-х под руководством Пентагона. В каком-то смысле он был аналогом PL/I (не слишком удачная попытка собрать все возможные концепции в одном языке), но некоторые элементы Ada (в частности, ее система типов) оказали большое влияние на мышление авторов других языков.
Итоги: завтра была война
Эволюционно нынешние «главные языки» ушли бесконечно далеко от машинных кодов. Накопление парадигм и подходов (а равно и снижение актуальности «простой модели компьютера», которая лежит в основе императивного программирования) практически исчерпало потенциал «классического», структурно-императивного взгляда на программирование, который в сегодняшних компонентных приложениях узнается с трудом. Что придет ему на смену? — этот вопрос мы пытаемся рассмотреть в заключительной статье темы.Заполняя пропуски: Реализации
Следует упомянуть и еще несколько языковых проектов, вполне классицистических, вполне успешных, но стоящих слегка на отшибе от «главного исторического вектора».Во-первых, это юниксовский sh и его производные (bash, ksh, csh и далее со всеми остановками). Первые оболочки *nix-систем ведут свой род от Алгола; юниксовский подход к объединению маленьких самостоятельных утилит считается одним из первых примеров компонентно-ориентированного программирования. Среди отдаленных потомков sh — как постмодернистский Perl (о нем мы еще поговорим), так и безусловно классицистический Tcl (а о нем не будем).
Во-вторых, язык веб-программирования PHP — тоже вполне популярен и вполне классицистичен. Его часто называют среди наследников Perl, но от последнего PHP перенял в основном способ именования переменных и область применения; в остальном первые PHP — это почти чистый C (вплоть до имен библиотечных функций). Небывалый успех PHP — это успех не языка программирования (часто критикуемого за концептуальную уродливость), а успех утилиты для легкой разработки веб-приложений. Так и повелось.