Как программист на Java / C # / C ++ я много слышал о функциональных языках, но никогда не находил необходимости изучать их. Я также слышал, что более высокий уровень мышления, представленный в функциональных языках, делает вас лучшим программистом ООП / процедурного языка.
Кто-нибудь может это подтвердить? Каким образом это улучшает ваши навыки программирования?
Каков хороший выбор языка для изучения с целью улучшения навыков на менее сложном языке?
Ответы:
Я в основном согласен с ответом FrustratedWithFormsDesign , но вы также спросили, как изучение новой парадигмы помогает развивать свои навыки. Я могу привести пару примеров из собственного опыта.
Начиная с изучения функционального программирования, я намного больше осознаю, какие концепции, с которыми я работаю, более естественно рассматриваются как «объекты» (обычно там, где имеет место мутация), а какие более естественно рассматриваются как неизменные «ценности» (я думаю, что есть важное различие касаясь того, где ОО имеет смысл, по сравнению с тем, когда имеет смысл ФП, но это только мое мнение).
Я замечаю, где мой код включает в себя побочные эффекты, и я более осторожен, чтобы изолировать эти места, делая большинство моих функций «чистыми» функциями. Это значительно улучшает тестируемость моего OO-кода.
Я больше осознаю циклы в моем представлении данных. (Например, я не думаю, что вы можете написать функцию для преобразования связанного списка в двусвязный список в Haskell, поэтому вы замечаете, что циклы на этом языке немного больше.) Избегание циклов уменьшает количество синхронизации вам нужно выполнить, чтобы ваши структуры данных были внутренне согласованными, что облегчает бремя разделения этих структур между потоками.
Я с большей вероятностью полагаюсь на рекурсию (рекурсивные циклические конструкции схемы - это красота). Дейкстра коснулся важности этого в « Заметках по структурированному программированию» - рекурсивные алгоритмы очень точно отображают математическую индукцию, которая, как он полагает, является единственным средством интеллектуального доказательства правильности наших циклов. (Я не предлагаю, чтобы мы доказали, что наш код верен, но чем проще нам сделать это для себя, тем больше вероятность, что наш код верен.)
Я более склонен использовать функции более высокого порядка. Статья Джона Хьюза « Почему функциональное программирование имеет значение» . Это подчеркивает возможность компоновки, которую вы получаете, используя методы функционального программирования, причем функции высшего порядка играют главную роль.
Кроме того, как уже упоминалось в ответе Jetti , вы обнаружите, что многие идеи FP внедряются в новые ОО-языки. Ruby и Python предоставляют много функций более высокого порядка, я слышал, что LINQ описывается как попытка обеспечить поддержку монадического понимания в C #, даже в C ++ теперь есть лямбда-выражения.
источник
1 + 2
математически эквивалентно2 + 1
, но1.+(2)
реализовано иначе, чем2.+(1)
. Существует целый ряд проблем SW, которые можно понять более естественно при использовании операций, чем при использовании объектных интерфейсов.Я бы не сказал, что это гарантирует, что вы станете лучшим программистом ООП, но это познакомит вас с новым мышлением, которое поможет вам лучше решать проблемы в целом, а не только с точки зрения ООП.
источник
Изучение функционального языка - Lisp для меня - действительно помогает при создании параллельных приложений. Функциональные методы (основанные на состоянии, без побочных эффектов) намного легче синхронизировать, и их легче сделать потокобезопасными, поскольку они зависят только от их ввода. Это означает, что единственные данные, которые необходимо отслеживать для данной области кода, - это параметры, которые вы передаете. Это также облегчает отладку.
источник
Thread
объекты ... неуклюжи.Изучение любой другой парадигмы программирования улучшит ваши навыки программирования в целом. Программирование, когда оно не является академическим научным материалом (и даже тогда, часто), в основном является решением проблем. Думая одним словом. Различные парадигмы - это разные способы мышления о проблемах и их решениях. Так что не думайте об этом как о «изучении функционального языка». Думайте об этом как о «изучении другого способа думать о проблемах и их решениях». Тогда вы увидите преимущества изучения языка, даже если вы никогда его не используете.
Чтобы ответить на ваш конкретный вопрос, я был программистом на C ++ еще в те времена (еще до того, как появился стандарт для C ++). Я следовал за всеми обычными вещами с объектами, содержащими состояние, управляемое методами и т. Д. И т. Д. И т. Д. Затем я наткнулся на Хаскелл и изучил (большую часть) это. (Я не думаю, что кто-то когда-нибудь по-настоящему изучает Haskell.) Это упражнение выглядело немного напрасным, пока один из моих коллег, тестировщик, назначенный в мою группу, не сделал ничего из комментариев, что мой код стало легче тестировать.
Случилось так, что я начал делать свои объекты все более и более неизменными. Классы со сложным изменяемым состоянием начали заменяться классами, которые клонировали себя с изменениями, возвращая новые объекты. Общие объекты начали заменяться объектами, которые имели семантику копирования при записи (таким образом, создавая иллюзию множества клонов объектов без использования памяти). Функции не имели побочных эффектов, за исключением случаев, когда это абсолютно необходимо; Чистое математическое определение «функции» становилось все более и более нормой. Все это начало происходить в моем коде естественным образом - без какой-либо сознательной мысли - когда я исследовал все больше и больше функционального пространства программирования.
Теперь я ставлю целью выучить хотя бы одну новую парадигму программирования каждые два года (даже если это всего лишь парадигма незначительного расширения, например, AOP) и как минимум два новых языка в каждой парадигме (один максимально чистый, еще один гибридный / практический). ). Каждый из них дал мне новые интеллектуальные инструменты для применения ко всем моим программам на любом языке, поэтому время, потраченное на их изучение, по моему мнению, не было даже потрачено впустую.
источник
Я говорил это раньше, и я скажу это снова, изучение функциональных языков определенно улучшило мой C #. Это помогло мне понять лямбды (и помогло мне любить их). Это также заставило меня понять, насколько я предпочитаю функциональное программирование (F #) при работе с асинхронными операциями!
источник
Машинный код - это не что иное, как список побочных эффектов - команд, которые непосредственно выполняются процессором. Побочные эффекты в C разные, вместо обработки регистров и физического оборудования, вы имеете дело с набором абстракций и позволяете компилятору выполнять всю грязную работу. C также позволяет структурировать ваши побочные эффекты в циклах и в операторах if then. C ++ улучшает C, добавляя ООП и некоторые столь необходимые функции в язык. Java и C # добавляют сборщик мусора, а Python добавляет динамическую типизацию.
Даже со всеми этими функциями - динамическая типизация, сборка мусора и т. Д. Программы на этих языках все еще полностью основаны на побочных эффектах. Функциональные языки программирования, такие как Scheme, Clojure, Haskell и ML - это нечто совершенно иное, эти языки ближе к математике, чем к машинному коду. Вместо того, чтобы использовать побочные эффекты, вы передаете значения вокруг функций.
Я рекомендую Scheme , она минимальна и использовалась в старых вводных классах MIT. Другие функциональные языки программирования гораздо сложнее выучить. Clojure сочетает в себе все тонкости Java, ML - сложную систему статических типов, Haskell иногда называют академическим языком - он не идеален для начинающих и так далее. Схема с другой стороны проста в освоении и понимании.
Почти все языки программирования высокого уровня имеют функции и рекурсию - концепции, на которых основано функциональное программирование. Таким образом, ваши знания FP должны быть полезны почти везде, однако, если вы действительно хотите программировать функционально, вам следует использовать язык, который является естественным и эффективным, а не пытаться склонить чужой языковой дизайн по своему вкусу, то есть Вы должны использовать функциональный язык программирования для функционального программирования.
источник