Про ФП #2

    Было время, когда функциональные языки котировались если не больше, то наравне с императивными. Время прошло и даже известно почему. Почему-то считается, что программирование на функциональном языке это «взрыв мозга». Не спорю, иногда действительно взрыв, но это буквально дружеский хлопок по ушам, по сравнению с взрывами мозга, которые мне периодически приходится испытывать разбираясь в чужих исходниках на C#. Я очень хочу, что бы история была спиралевидной (-:

    Божественный Язык Математики™

    Как-то так у человечества получилось, что все существующие методики программирования придумали математики. Может быть и странно, но вполне объяснимо, а большинство основополагающих, базовых, несущих шаблонов программирования либо процедурные, либо функциональные. Ооп придумали для облегчения создания Больших И Сложных систем. И если смотреть на ооп теоретически — действительно, очень удобно. Это удобство рушится, когда возникает необходимость использования сторонних библиотек (а она всегда возникает). Большое счастье, если создатели были хорошими и чуткими людьми, пожалели ваши нервы и многократно прогнали свой код через Unit-тесты, да еще снабдили всё это хозяйство логичной и понятной иерархичностью. Если они этого не сделали, код становится нечитабельным совершенно. У «эзотерических лиспов» с этим дела обстоят значительно лучше. Всё, что вам нужно знать — имя библиотечной функции, её параметры и что она даёт на выходе. Отлаживать такую систему намного проще (в том числе за счет отсутствия сайд-эффектов).

    Миф о нечитабельности и эзотеричности ФП языков основан на разнице в восприятии кода программистами. Упор в императивных языках делается и на «человеческое, последовательное восприятие» кода. Например:
    int life()
    { // начнём
        human Peter = new human(); // Петя, пожалуйста родись
        storage shelf = new storage();  // Полка, пожалуйста появись
    
        Peter.Status = "Something good"; // Петя, ты молодец
        Peter.getPie(shelf); // Возьми пирожок с полки
        return 0; // У нас тут все хорошо, мы закончили, всем спасибо
    } // закончим
    


    Функциональные языки, как ни странно, нисколько не менее читабельны. Просто в них описывается не процесс, а решение, результат.
    Вот например, функция переворачивающей список (Erlang):
    reverse(List) ->
        reverse(List,[]).
    
    reverse([Head | Tail], ResultList) ->
         reverse(Tail, [Head | ResultList]);
    reverse([], ResultList) ->
        ResultList.
    


    Она трудна для восприятия нетренированным взглядом, за счёт своей рекурсивной природы, но если немножко принять на грудь приглядеться, можно понять, что здесь прямым текстом написано следующее: «Ко мне пришел список. Он мне не нравится, я хочу его перевернуть. Мне нравится хвост. Я его оставлю себе, а остальное склею и отложу. А если хвост вдруг кончился, значит я перевернул список и можно его выбросить».
    Периодически очень трудно понять, а где, собственно, происходит действие? По-моему это великий Дзен, уметь писать программы, которые работают за счёт определений.
    AdBlock похитил этот баннер, но баннеры не зубы — отрастут

    Подробнее
    Реклама

    Комментарии 14

      –1
      У любых декларативных языков есть один недостаток. То что делается левой ногой на императивных языках делается довольно сложно на декларативных. Простой пример интерфейс взаимодействия с пользователем. Не CLI а к примеру банальные меню или GUI с интерактивным вводом.
        0
        Подозреваю, именно потому, что GUI пишут на императивных языках.
        А вообще да. Приходится использовать всякие "спайки".
          0
          >Подозреваю, именно потому, что GUI пишут на императивных языках.
          Вообще нет. Функциональное программирование хорошо заточено под пакетные задания. Интерактив же с пользователем или требует ожидания поступления какого либо события. Каким образом вы это будете реализовывать ? :)
            0
            Я вообще никакой проблемы не вижу, реализовать ожидание события в функциональном языке.
            Во-первых есть понятие tail-recursion, которая эквивалентна циклу.
            Во-вторых живой пример:

            sender(PID) ->
            PID ! {"Hello",self()},
            receive
            Message ->
            io:format("~nReceived ~p",[Message])
            end.


            Всё тот же клятый Эрланг. Функция будет ждать, пока не получит ответ на отправленное сообщение.
              0
              >Во-первых есть понятие tail-recursion, которая эквивалентна циклу.
              Есть. Но шутка довольно искуственная.

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

                    p.s. Вы простите, что я всё про эрланг, да про эрланг. Раскрываю карты, я хочу тут вести эрланговый днимничок.
                      +1
                      Пишите шура пишите они золотые ;)
        • НЛО прилетело и опубликовало эту надпись здесь
            0
            Я про низкий уровень. Создание псевдографические менюшки на prolog это удовольствие ниже среднего. Хотя зато вот какая нибудь логическая шняга на prolog'е писалась на ура, но в императивном требовала довольно некислого количества телодвижений.
            • НЛО прилетело и опубликовало эту надпись здесь
                0
                А можно не извращаться и комбинировать :)
            0
            На intuit.ru есть отличный курс "Стили и методы программирования", рассказывается про традиционный, функциональный и другие методы программирования. Там же есть "Введение в программирование на Лиспе". Вот даже скачал IDE для Lisp - Jabberwocky (лучшее, что накопал, ато скучно в консольке то :)(а Jabberwocky на Java написан =), да решил изучить побольше чем как-то-где-то-видел-вроде.

            Только полноправные пользователи могут оставлять комментарии. Войдите, пожалуйста.

            Самое читаемое