В чем заключается индустрия software с технической стороны: программисты пишут программы, пользователи их покупают. Пользователям нравится, когда купленные за эти (зачастую немеряные) деньги программы работали. Желательно всегда.Потому что иначе пользователи начинают терять время и деньги, еще более немеряные. А если у пользователей деньги кончатся, программы они покупать перестанут.
Почему программы не работают? Очень просто. В программах есть баги. Баги доставляют программистам много-много увлекательных минут работы с отладчиком и кучу веселья (ну мне лично, по крайней мере ;), но баги все-таки юзеров очень раздражают, и багов поэтому должно быть поменьше и исправляться они должны побыстрее.
Что является основным источником багов? Нет, не программисты, поскольку программисты тоже люди, они совершают ошибки всегда. Однако ошибки совершать намного сложнее, когда работаешь с простой и насквозь понятной системой. А непонятной и запутанной системой software становится, когда в нем появляются разного рода побочные эффекты. То есть один раз нажимаем пимпу на диалоге -- все хорошо, второй раз нажимаем --программа падает. И, главное, программисту совершенно неясно, почему -- код тот же, данные входные те же(нажатие на кнопку) -- очевидный вывод: что-то где-то изменилось и все пошло не так. Что-то -- это какая-то глобальная переменная, состояние какого-то объекта и т.п. Вникать, что именно, программист будет доолго.
Знакомая ситуация?
Посмотрим теперь на другой аспект, процесс отладки в целом. Что происходит: тестер баг наш нашел, пожаловался и сидит радуется. Что должен сделать программист: повторить баг, под отладчиком, понять, куда ставить брейкпоинт, 250 тыщ раз нажать Step Over/Step Into, следя за тем, что и куда записалось, состояние какой переменной изменилось, и че из этого вышло. Причем связи все эти "что и куда", в программе, написаной на C#/Delphi/C++/Java, нифига не очевидны и хорошо просматриваются только в динамике, когда программа запущена. Программист тратит кучу времени.
А решение этих проблем -- это декларативные, а особенно функциональные языки. Когда все логические связи очевидны, по возможности статичны и строго типизированы. Это позволяет отловить огромную часть ошибок на этапе компиляции. Более того, в таких языках по сути отсутствует понятие порядка выполнения программы. Мы просто описываем связи между данными, преобразования, а интерпретатор вычисляет ответ. Поэтому не надо дебаггером проходить всю программу. Выяснить, какая именно связь не в порядке -- в декларативном языке в разы легче, и связь эту, как правило, можно очень просто отдельно протестировать (unit тесты как будто специально придуманы для ФЯ).
Проблемы -- во-первых, не очень высокая производительность. Но это неважно в большинстве случаев, да и есть ФЯ Ocaml который может поспорить по скорости с C++. Во-вторых -- и это главное -- learning curve тут намного круче. Особенно для программиста, не привыкшего к такому способу мышления. Сейчас, правда, они становятся все популярнее. C# 3.0 заимствует фичи из ФЯ, функциональный язык Nemerle становится, кажется, самой модной темой на рсдн.ру..
Хотя я лично в то, что "скоро не будет ни кино, ни театров, а будут сплошные ФЯ" не верю. Мейнстрим это все-таки промышленный дешевый процесс разработки software руками тысяч гастарбайтеров -- индусов, китайцев, и, может быть, русских. :) Индустриализация, промышленный переворот, от кустарного производства -- к заводам и фабрикам ПО :)
Тем не менее, сложные задачи решать на ФЯ намного удобнее. И самая большая з/п (спускаясь на землю :) -- есть и будет у людей с редкими навыками в специфических областях индустрии.
Примеры успешного применения ФЯ покажу потом :)
Monday, August 21, 2006
Декларативное программирование
Posted by lrrr at 12:00 PM
Subscribe to:
Post Comments (Atom)
8 comments:
Кстати, функциональное програмированние вроде бы декларативным не считается. Декларативным считается только логическое вроде бы (пролог и все его модификации).
Да нет, щас вот в гугле специально потыкался -- все его таковым считают. Что и логично -- декларативное(как оно почти везде определяется) подразумевает описание проблемы без явного описания алгоритма решения, в виде последовательности действий. ФЯ вполне сюда подпадают.
По-моему, стоит различать эти понятия. Декларативное - это всякие там атрибуты, top-level синтаксические макросы а ля Немерле и. т.п.
Функциональное - это когда функции являются first-class values.
Да, ФЯ может иметь декларативные средства, но эти понятия не взаимозаменяемы.
Я понимаю что на википедию ссылаться это не комильфо.. ;)
но все-таки:
en.wikipedia.org/wiki/Declarative_programming
"a program is "declarative" if it describes what something is like, rather than how to create it"
В большинстве статей ФЯ относят к декларативным языкам, то есть я как-то даже не встречал, чтоб не относили :)
"a program is "declarative" if it describes what something is like, rather than how to create it"
И как это связано с ФП?
Кстати, там же есть и другое определение:
According to a different definition, a program is "declarative" if it is written in a purely functional programming language, logic programming language, or constraint programming language. The phrase "declarative language" is sometimes used to describe all such programming languages as a group, and to contrast them against imperative languages.
Т.о., под декларативным языком можно понимать и неимперативный, о чём ты и говоришь :) .
Как человек, за последние два года ни разу не воспользовавшийся отладчиком, скажу: да, в функциональных языках что-то есть :)
Однако декларативное программирование - это только полумера. И на C++ написали симпатишный декларативный парсер EBFN-грамматики, только от этого программы на С++ менее глючными не станут.
Для меньшего количества глюков необходима еще куча вещей:
* garbage collector - меньше memory leak-ов
* интерпретатор - чтобы быстрее проверять работоспособность кода
* отсутствие адресной арифметики и проверка обращений к памяти - чтобы ее не засрать
* отсутствие NULL-а - чтобы к нему не обращаться
* наличие exceptions по каждой ошибке - чтобы программа сразу падала, а не через полгода
* traceback - чтобы тебе сказали - где упало (хотя core.dump тож ниче)
* ... и многое другое
А отсутствие shared mutable state - это скорее архитектурные вопросы. И в хаскеле можно все загадить IORef-ами :)
Да, это ведь все очень сильно связанные вещи -- строгая система типов, отсутствие указателей, gc.. В ФЯ это красиво и органично вписывается.
Да, неплохо также иметь "правильные" механизмы синхронизации и flow control, сообщения, continuation'ы. Они в ФЯ тоже очень хорошо и понятно работают.
Всякие там spirit'ы и phoenix'ы -- по мне так скорее это proof-of-concept, что в C++ тоже можно что-то похожее изобразить.
Post a Comment