ООП против Функционального программирования против Процедурного [закрыто]

StackOverflow https://stackoverflow.com/questions/552336

  •  23-08-2019
  •  | 
  •  

Вопрос

Каковы различия между этими парадигмами программирования, и лучше ли они подходят для конкретных задач или какие-либо варианты использования отдают предпочтение одной из них перед другими?

Примеры архитектуры приветствуются!

Это было полезно?

Решение

Все они хороши по-своему - это просто разные подходы к одним и тем же проблемам.

В чисто процедурном стиле данные, как правило, сильно отделены от функций, которые с ними работают.

В объектно-ориентированном стиле данные, как правило, содержат в себе набор функций.

В функциональном стиле данные и функции имеют тенденцию иметь больше общего друг с другом (как в Lisp и Scheme), предлагая при этом большую гибкость с точки зрения того, как функции фактически используются.Алгоритмы, как правило, также определяются в терминах рекурсии и композиции, а не циклов и итераций.

Конечно, сам язык влияет только на то, какой стиль предпочтительнее.Даже на чисто функциональном языке, таком как Haskell, вы можете писать в процедурном стиле (хотя это крайне не рекомендуется), и даже на процедурном языке, таком как C, вы можете программировать в объектно-ориентированном стиле (например, в API GTK + и EFL).

Чтобы было ясно, "преимущество" каждой парадигмы заключается просто в моделировании ваших алгоритмов и структур данных.Если, например, ваш алгоритм включает в себя списки и деревья, функциональный алгоритм может быть наиболее разумным.Или, если, например, ваши данные сильно структурированы, возможно, имеет смысл составить их в виде объектов, если это является родной парадигмой вашего языка, или их можно так же легко записать как функциональную абстракцию монад, которая является родной парадигмой таких языков, как Haskell или ML.

Выбор того, что вы используете, - это просто то, что имеет больше смысла для вашего проекта и абстракций, поддерживаемых вашим языком.

Другие советы

Я думаю, что доступные библиотеки, инструменты, примеры и сообщества в наши дни полностью превосходят парадигму.Например, ML (или что-то еще) может быть идеальным универсальным программированием язык но если вы не можете получить никаких хороших библиотек для того, что вы делаете, вы облажались.

Например, если вы создаете видеоигру, на C ++ есть больше хороших примеров кода и пакетов SDK, так что вам, вероятно, будет лучше с этим.Для небольшого веб-приложения есть несколько отличных фреймворков на Python, PHP и Ruby, которые помогут вам очень быстро начать работу.Java - отличный выбор для более крупных проектов из-за проверки во время компиляции и корпоративных библиотек и платформ.

Раньше было так, что стандартные библиотеки для разных языков были довольно маленькими и легко реплицируемыми - C, C ++, ассемблер, ML, LISP и т.д..поставляется с основами, но имеет тенденцию отказываться, когда дело доходит до стандартизации таких вещей, как сетевые коммуникации, шифрование, графика, форматы файлов данных (включая XML), даже базовые структуры данных, такие как сбалансированные деревья и хэш-таблицы, были опущены!

Современные языки, такие как Python, PHP, Ruby и Java, теперь поставляются с гораздо более приличной стандартной библиотекой и имеют множество хороших сторонних библиотек, которые вы можете легко использовать, во многом благодаря использованию ими пространств имен, предотвращающих столкновение библиотек друг с другом, и сборке мусора для стандартизации схем управления памятью библиотек.

Эти парадигмы не обязательно должны быть взаимоисключающими.Если вы посмотрите на python, он поддерживает функции и классы, но в то же время все является объектом, включая функции.Вы можете смешивать и сочетать функциональный / ооп / процедурный стиль в одном фрагменте кода.

Я имею в виду, что в функциональных языках (по крайней мере, в Haskell, единственном, который я изучал) нет утверждений!функциям разрешено использовать только одно выражение внутри них!!НО функции - это первоклассные граждане, вы можете передавать их в качестве параметров вместе с кучей других возможностей.Они могут делать мощные вещи с помощью нескольких строк кода.

В то время как на процедурном языке, таком как C, единственный способ передачи функций - это использование указателей на функции, и это само по себе не позволяет выполнять многие мощные задачи.

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

То же самое относится и к ООП.Такой язык, как Java, не позволяет вам писать процедуры / функции вне класса.Единственный способ передать функцию по кругу - это обернуть ее в объект, который реализует эту функцию, а затем передать этот объект по кругу.

В Python у вас нет этого ограничения.

Для GUI я бы сказал, что объектно-ориентированная парадигма очень хорошо подходит.Окно - это Объект, текстовые поля - это Объекты, и кнопка "Ок" - это тоже объект.С другой стороны, такие вещи, как обработка строк, могут быть выполнены с гораздо меньшими накладными расходами и, следовательно, более простыми с помощью простой процедурной парадигмы.

Я тоже не думаю, что это вопрос языка.Вы можете писать функциональные, процедурные или объектно-ориентированные тексты практически на любом популярном языке, хотя в некоторых случаях это может потребовать дополнительных усилий.

Чтобы ответить на ваш вопрос, нам нужны два элемента:

  1. Понимание характеристик различных архитектурных стилей / паттернов.
  2. Понимание характеристик различных парадигм программирования.

Список стилей / шаблонов архитектуры программного обеспечения показан на статья об архитектуре программного обеспечения в Википейде.И вы можете легко изучить их в Интернете.

Вкратце и в общих чертах, Процедурный хорош для модели, которая следует процедуре, ООП хорош для дизайна, а функциональный хорош для высокоуровневого программирования.

Я думаю, вам следует попробовать прочитать историю каждой парадигмы и посмотреть, почему люди создают ее, и вы сможете легко их понять.

Поняв их оба, вы можете связать элементы стилей / шаблонов архитектуры с парадигмами программирования.

Я думаю, что они часто не "против", но вы можете их комбинировать.Я также думаю, что часто слова, которые вы упоминаете, - это просто модные словечки.Мало кто на самом деле знает, что означает "объектно-ориентированный", даже если они самые ярые его проповедники.

Один из моих друзей пишет графическое приложение, используя NVIDIA CUDA.Приложение очень хорошо вписывается в парадигму ООП, и проблему можно аккуратно разложить на модули.Однако, чтобы использовать CUDA, вам нужно использовать C, который не поддерживает наследование.Поэтому вам нужно быть умным.

а) Вы разрабатываете умную систему, которая в определенной степени будет имитировать наследование.Это можно сделать!

i) Вы можете использовать крюковая система, который ожидает , что каждый дочерний элемент C родительского элемента P будет иметь определенное переопределение для функции F.Вы можете заставить дочерние элементы регистрировать свои переопределения, которые будут сохранены и вызваны при необходимости.

ii) Вы можете использовать struct выравнивание памяти функция превращения детей в родителей.

Это может быть изящно, но нелегко придумать перспективное и надежное решение.Вы потратите много времени на разработку системы, и нет никакой гарантии, что вы не столкнетесь с проблемами на полпути к завершению проекта.Реализующий множественное наследование это еще сложнее, если не почти невозможно.

б) Вы можете использовать согласованную политику именования и использовать разделяй и властвуй подход к созданию программы.У него не будет никакого наследования, но поскольку ваши функции небольшие, простые для понимания и последовательно отформатированы, вам это не нужно.Объем кода, который вам нужно написать, растет, очень трудно оставаться сосредоточенным и не поддаваться простым решениям (взломам).Однако этот способ кодирования ninja - это способ кодирования C.Поддержание баланса между низкоуровневой свободой и написанием хорошего кода.Хороший способ добиться этого - написать прототипы с использованием функционального языка.Например, Хаскелл чрезвычайно хорош для создания прототипов алгоритмов.

Я склоняюсь к подходу б.Я написал возможное решение, используя подход a, и, честно говоря, использование этого кода казалось очень неестественным.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top