Язык Haskell: О пользе и вреде лени: различия между версиями

красоту навожу. Ссылки делаю
м
(красоту навожу. Ссылки делаю)
где были переменные функции, или функция возвращала в качестве
результата другую функцию? Возможность создавать переменные типа
функций в языках Си/Си++, Паскаль, Delphi есть{{ref|conscons1}}, но ею пользуются крайне редко.
Перечисленные языки em процедурные, и они не приспособлены для того, чтобы писать программы в
функциональном стиле.
 
toDigsI :: Integer->[Integer]
toDigsI n | n == 0 = []
| otherwise = (n `mod` 2) : toDigsI (n `div` 2)
| n == 0 = []
| otherwise =
(n `mod` 2) : toDigsI (n `div` 2)
countUnits = sum . toDigsI
toDigits = reverse . toDigsI
 
Функция <tt> toDigsI</tt> для данного числа ''n''
находит список его разрядов в двоичном представлении в направлении справа налево.
Стандартная функция <tt> reverse</tt> обращает список: получает на вход список и возвращает тот же
список, в котором элементы идут в обратном порядке, начиная с последнего до первого:
 
toPowers = (filter (/=0)) . (zipWith (*) powers) . toDigsI
 
Функция <tt> filter </tt> получает на вход булеву функцию (функцию, возвращающую &laquo;правду&raquo; или &laquo;ложь&raquo;)
и список, а возвращает список только из тех элементов, на которых значение
этой функции равно &laquo;правде&raquo;. В данном случае мы оставляем только ненулевые элементы:
<tt>toPowers (16+8+1) <math>\Rightarrow</math> [1,8,16]. </tt>
 
Функция &laquo;<tt> zipWith </tt> &raquo; получает три аргумента.
Если указано только два аргумента, то она превращается в функцию от одного аргумента.
Это позволяет использовать выражение &laquo;<tt> (zipWith (*) powers) </tt> &raquo;
неё первый аргумент &mdash; &laquo;<tt> (/=0) </tt>&raquo; &mdash; это функция сравнения с нулём.
Второй аргумент остался неопределённым. Он достанется ей по цепочке как значение
функции &laquo;<tt> (zipWith (*) powers) </tt> &raquo; на том, что вернёт ей функция
<tt> toDigsI </tt>, применённая к тому, что даст пользователь в качестве аргумента функции
<tt> toPowers </tt>.
 
Точки в определении функции <tt> toPowers </tt> играют роль операции &laquo;|&raquo; (pipe) в стандартной оболочке Linux.
С помощью этой операции происходит передача результатов вычисления одной функции
* Software AG, одна из главных программистских компаний Германии, разработала на функциональном языке экспертную систему Natural Expert. Пользователи с огромным удовольствием пишут для этой системы свои приложения.
Система работает на мейнфреймах IBM.
* Компания Ericsson разработала функциональный язык [http://www.erlang.org Erlang] для создания системы управления телефонных станций.
* Исследователи в корпорации MITRE используют Haskell для [[:w:прототипирование|прототипирования]]{{ref|conscons2}} приложений обработки цифровых сигналов.
 
Для многих программистов не секрет, что на процедурных языках
* [[w:Haskell|Язык программирования Haskell]], статья в Википедии
* [[Основы функционального программирования]], курс лекций в Викиучебнике
* [http://www.haskell.ru/ Российский сайт про Haskell]
* [http://wtk.norilsk.net/pm/fp/haskell.html Введение в язык Haskel Михаила Потанина]
 
== Примечания ==
 
# {{note|conscons1}} Когда в языке Си определяется переменная типа функции, необходимо указать типы аргументов функции и тип возвращаемого значения. Например, &laquo;<tt> int (*)(int, int) </tt>&raquo; &mdash; это тип функции, возвращающей число типа <tt> int </tt> и принимающей в качестве аргументов два числа типа <tt> int </tt>.
# {{note|conscons2}} Прототипирование &mdash; это быстрая &laquo;черновая&raquo; реализация базовой функциональности для анализа работы системы в целом. Для прототипирования используют языки высокого уровня абстракции (Java, Perl, Python, Haskell, ...). После этапа прототипирования обязательно следуют этапы пересмотрения архитектуры системы, разработки, реализации и тестирования конечного продукта. На этапе разработки подготавливают систему тестов, по работе которых буду судить о качестве продукта. При реализации решения обычно используют другой, &laquo;более машинноориентированный&raquo; язык программирования (Си, Си++, ...), пишут более аккуратный,документированный код, а на тестирование системы тратят сравнительно большое количество усилий для достижения качественного результата.
:На этапе прототипирования выявляются важные архитектурные ошибки, вносятся поправки в интерфейсы модулей (перераспределяется функциональность между кусочками системы). Прототипирование по мнению многих программистов является самым приятным этапом разработки, так как малыми усилиями создается нечто более-менее работающее. Кроме того, во время прототипирования на программистов обычно &laquo;снисходит понимание&raquo; и они начинают &laquo;видеть&raquo;, как система должна быть устроена.
481

правка