Является ли объектно-ориентированное программирование решением проблемы сложности? [закрыто]


18

Как вы думаете, объектно-ориентированное программирование является решением для сложности. Почему? Эта тема может быть немного спорным, но мои намерения знать ответ, почему у специалистов здесь!


15
Трудное задание эссе? ; p
Гленатрон

1
Вопрос не имеет смысла, так как нет сложности. Существуют стратегии борьбы со сложностью (в частности, внутренняя, неснижаемая сложность). Но решений, нет, нет. Это все равно, что искать решение, которое сводит одну физическую милю к нулю.
luis.espinal

1
Объектно-ориентированное программирование - это инструмент для управления сложностью.
Роберт Харви

Вопрос: Можете ли вы программировать сложные проблемы с ООП? - Ответ: Конечно. Если вы используете ООП, это будет сложно.
Mouviciel

«это может быть спорным» делает это предмет для обсуждения, а не технический вопрос ...
jwenting

Ответы:


24

Нет решения для сложности.

В «Мифическом человеко-месяце» Фред Брукс обсуждает разницу между случайной и существенной сложностью в программировании. Случайная сложность вызвана нашими инструментами и методами, такими как необходимость писать и тестировать дополнительный код на языке, потому что мы не можем выразить наши идеи напрямую и тому подобное. Новые методы и методы могут уменьшить случайную сложность. Я могу писать программы быстрее и лучше, чем двадцать пять лет назад, потому что у меня есть лучшие языки и инструменты.

Существенная сложность возникает из-за того, что то, что мы пытаемся делать с программированием, по своей сути сложно, и что существует неснижаемая сложность. «Существенный» в данном контексте означает «относящийся к сути вещи», а не «очень необходимый».

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

Я настоятельно рекомендую вам прочесть его книгу: в частности, я рекомендую издание Silver Anniversary с дополнительным эссе "No Silver Bullet". При этом он рассматривает предложенные решения по сложности и учитывает их влияние. (То, что он считает наиболее эффективным, - это программа для упаковки в термоусадочную пленку - однажды напишите что-нибудь сложное и продайте тысячи или миллионы копий.)

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


3
Издание «20th Anniversary» также содержит «Refired без серебряной пули», в котором он называет ООП «медной пулей» и говорит: «... очень многообещающая концепция».
Джерри Гроб

18

Я ожидаю, что вы получите лучшие ответы в ближайшее время, но вот простой:

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

* Потому что ничто не может «решить» сложность


4
Вот как ООП работает в теории. На практике примеры ООП, такие как собаки, которые лают, утки, которые летают, и грузовики, которые являются транспортными средствами, начинают ломаться, когда вы пишете реальное программное обеспечение, потому что реальные программные объекты всегда более абстрактны, чем эта.
Роберт Харви

8
@ Роберт: Я не утверждаю, что вы на самом деле очень часто моделируете объекты реального мира в ООП - просто что проще думать о большинстве программ в терминах объекта (даже если это объекты сокет-прокси и модель-фасад), потому что именно так мы смотрим на мир собак и уток в реальной жизни.
Fishtoaster

2
Нет, это распространенное заблуждение об ООП. Вы не должны моделировать свою программу на основе реальных объектов. В реальной жизни BufferReader не существует.
hasen

1
@Hasen j: Да, это то, что я сказал, когда пояснил в своем комментарии.
Fishtoaster


15

Я думаю, что текущее основное определение ООП не является хорошим решением для управления сложностью.

Если вы вернетесь к его корням, я полагаю, что Алан Кей сильно повлиял на «шутку».

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

Если вы посмотрите на конец «Лекции 3a: Пример Хендерсона Эшера» SICP , Хэл Абельсон предлагает, чтобы сложность управлялась не разбиванием задачи на более мелкие подзадачи, а созданием слоев абстракции. На высшем уровне вы выражаете решение сложной проблемы в терминах решения нижнего уровня абстракции.

Я думаю, что ООП изначально задумывался как механизм для создания этих слоев абстракций.

К сожалению, в настоящее время ООП (ab) используется для написания спагетти-кода / структур.

Я приведу пример: многопользовательская игра FPS.

На высшем уровне игра работает, когда кучка игроков бегает по карте и стреляет друг в друга из оружия.

На следующем более низком уровне мы должны поговорить о картах, оружии и игроках. Возможно, мы можем говорить о них как о физических объектах, которые взаимодействуют в мире игры.

На следующем более низком уровне мы можем говорить о том, как объекты физически взаимодействуют (движение, столкновения и т. Д.).

И так далее.

Это означает (и я как бы цитирую SICP ..), что на каждом уровне мы решаем не только конкретную конкретную проблему, но и класс проблем, которые как бы попадают в окрестности проблемы, которую мы » пытаемся решить. Поэтому, если в описании проблемы есть небольшие изменения, это, скорее всего, потребует лишь небольших изменений в решении.

Таким образом, разумный способ использования ООП состоит в том, чтобы создавать слои абстракций, на каждом уровне абстракции вы решаете проблему, используя «объекты» с уровня, который находится непосредственно ниже.

Вот цитата, которую я цитировал из лекции: http://www.youtube.com/watch?v=CYtrfncMqHQ


5
Как и многие другие инструменты, ООП очень эффективен, когда используется разумно и вдумчиво, и не так эффективно, когда им злоупотребляют.
Роберт Харви

1
+1 за «слои абстракции» - очень хорошее объяснение. ООП также позволяет вам ограничивать область видимости одним объектом за раз, что упрощает визуализацию дизайна и взаимодействий.
Майкл К

1
Я считаю, что теоретическая концепция, не «искаженная массовым усыновлением», поможет улучшить управление сложностями в реальных проектах ... странно.
Майкл Боргвардт

@MichaelBorgwardt, массовое внедрение развращает полезную идею, потому что многие люди в основном потоке не понимают, в чем суть идеи, поэтому, когда вы пытаетесь найти, что такое ООП, вы видите различные заблуждения разных людей. LISP еще будет использоваться, но только в меньшинстве, так что это менее вероятно , что первоначальные идеи пострадали от коррупции , вызванных заостренными волосистой боссов , не имея понятия , что это все о.
hasen

@hasen j: OTOH соответственно более вероятно, что "оригинальные идеи", которые никогда не видели массового принятия, были вещами башни из слоновой кости, которые не работают в реальном мире. Отсутствие популярности, безусловно, не является четким аргументом в пользу чего-либо.
Майкл Боргвардт

10

Как обычно, я не согласен со всеми. ООП не только предоставляет вам инструменты для управления сложностью, но и создает огромную сложность, потому что это неадекватная и математически поддельная парадигма. Это не смущает программистов, пытающихся моделировать вещи с ООП, которые нельзя смоделировать с помощью ООП.

На мой взгляд, основная работа здесь - это конструирование объектно-ориентированного программного обеспечения Мейера. В нем подробно описан ряд требований, в том числе одно, которое я считаю крайне важным: принцип Open-Closed. Это говорит о том, что вещь должна быть открыта для расширения, но закрыта для использования одновременно.

Мейер начинает выводить объектную ориентацию из этих требований, воплощенных в Eiffel. Инкапсуляция обеспечивает закрытие, открытость наследования, и упомянутая «вещь» - это класс.

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

Ошибка делает класс или тип модульной единицей. Это неправильно и доказуемо так. Даже Мейер осознал проблему (называемую проблемой ковариации), что ООП не может обрабатывать отношения арности выше единицы (то есть ООП отлично работает для свойств, но не работает на бинарных отношениях). В Eiffel эта проблема привела к несостоятельности системы типов!

Решение вполне понятно. Единица модульности должна быть больше, чем один тип. Он должен состоять из нескольких типов и методов, связанных с ними.

Неудивительно, что эта модель абстракции опирается на математическую теорию абстракции, а именно на теорию категорий: типы - это объекты категории, а методы (функции) - стрелки.

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

Стандартный мета-язык (SML) и Ocaml основаны непосредственно на этой модели. Ocaml также имеет классы и ООП: это не бесполезно, потому что ООП дает вам диспетчеризацию свойств, то есть динамическое связывание. Однако большинство проблем реального мира связаны с отношениями, и неудивительно, что в Окамле классы не так часто используются.

Неудивительно, что наследование практически не используется в стандартной библиотеке шаблонов C ++.

Простой факт в том, что ООП не дает вам правильных инструментов для управления сложностью, он даже не дает вам инструментов для решения действительно простых задач, вместо этого он ввел в заблуждение и запутал два поколения программистов. ООП - это не самая злая и плохая вещь, которая случилась с программированием с тех пор, как С, Фортран и Кобол начали уставать.


соблазн создать еще одну учетную запись, чтобы поддержать вас;)
Marco Mariani

Вы делаете ряд утверждений. Возможно, вы можете предоставить аргументы, подтверждающие ваши утверждения, или ссылки на аргументы. Как это, что не совсем поддерживает ваши различные тезисы (в смысле того, что «что-то не так с ОО; это то, что нужно делать»): lucacardelli.name/Papers/BadPropertiesOfOO.pdf
Фрэнк Шиарар

3
Говоря «foo - самая злая и плохая вещь ...», между прочим, активно разъедает любой аргумент, который вы можете попытаться привести.
Фрэнк Ширар

6

У объектно-ориентированного программирования есть корни, которые можно проследить до 1960-х годов. Поскольку аппаратное и программное обеспечение становится все более сложным, управляемость часто становится проблемой. Исследователи изучили способы поддержания качества программного обеспечения и разработали объектно-ориентированное программирование, частично для решения общих проблем, уделяя особое внимание дискретным, многократно используемым элементам логики программирования.

Таким образом, объектно-ориентированная программа может рассматриваться как совокупность взаимодействующих объектов, в отличие от обычной модели, в которой программа рассматривается как список задач (подпрограмм), которые необходимо выполнить. В ООП каждый объект способен принимать сообщения, обрабатывать данные и отправлять сообщения другим объектам. Каждый объект можно рассматривать как независимую «машину» с определенной ролью или ответственностью. Действия (или «методы») над этими объектами тесно связаны с самим объектом.

http://en.wikipedia.org/wiki/Object-oriented_programming

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


2

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

Есть и другие способы управления сложностью программного обеспечения, например, логическое (Prolog) и функциональное (Haskell) программирование.

На уровне выше, чем программирование, нам нужны шаблоны проектирования и принципы для управления ООП. Следовательно, ООП управляет сложностью на низком (кодирующем) уровне, в то время как эти методологии, такие как Шаблоны проектирования и Принципы, направляют разработку решения на более высокий (системный и прикладной) уровень и делают сложность разработки и обработки программного обеспечения более управляемой.

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


3
Я бы очень осторожно сказал, что нам «нужны» шаблоны проектирования. Это естественные артефакты хорошего дизайна ОО - их не следует использовать для управления им. «О, у нас нет шаблона для этого, поэтому мы не можем этого сделать». Они являются средством общения дизайна.
Майкл К

2

Объектно-ориентированное программирование управляет существенной и необязательной сложностью, но также не уменьшает ее.

Я предпочитаю определение, данное Эриком Стивеном Рэймондом в «Искусстве программирования на Unix» , потому что оно разграничивает существенную, необязательную и случайную сложность. http://www.faqs.org/docs/artu/ch13s01.html#id2964646

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


2

Сложные проблемы не могут быть оказаны проще с помощью технологии, они могут быть только удалось с помощью технологии.

ООП - это технология, концепция и способ решения проблемы.

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

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

В конце концов, объектно-ориентированное программирование не может быть решением проблемы сложности; это просто инструмент для управления им. (при правильном использовании)


+1 В конце концов, объектно-ориентированное программирование не может быть решением сложности; это просто инструмент для управления им. (при правильном использовании)
Картик Сринивасан

2

Ориентация на объект (как обычно используется) является полезным инструментом во многих случаях, но не является достаточным решением для сложности.

В частности, это часто добавляет много «дополнительной сложности ». Примерами являются сложность, связанная с наследованием реализации, необходимость предоставления большого количества «стандартных функциональных возможностей» suach as equals (), hashCode () и т. Д. Хорошая презентация Стюарта Хэллоуэя на эту тему: « Простота не легкая »

Объекты в большинстве языков также имеют тенденцию инкапсулировать множество изменяемых состояний, что в параллельном мире все больше начинает казаться плохим дизайнерским решением. Снова интересное видео от Rich Hickey рассказывает о различии между идентичностью объекта и состоянием, а также о том, как может быть ошибкой объединять их.


1

Объектно-ориентированное программирование - это способ представления проблемы, ни больше, ни меньше. Он сам по себе не менее сложен, чем любая другая парадигма программирования. Хорошо спроектированная система ООП управляет и уменьшает сложность, но также очень легко спроектировать систему, которая намного сложнее, чем необходимо, и мешает всему.

Как часто говорят в C ++, ООП дает вам достаточно веревки, чтобы повеситься.


Но это верно для любого мощного языка или парадигмы. Вы хотите, чтобы веревка была слишком короткой, чтобы повеситься? ты никогда не взберешься с горы!
Майкл К

@ Майкл, немного больше, чем другие. Но по сути да. Здесь нет серебряных пуль, всегда есть отступление от того, какой язык или парадигму вы используете.
Доминик Макдоннелл

1

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

Разделяй и властвуй.


1

ООП - это попытка найти решение.

Лучший способ управлять сложностью - создавать абстракции. Если я смогу превратить свои данные в полезные коллекции с узнаваемыми функциями, которые работают с этими коллекциями, я могу начать думать о коллекциях как о «отдельных вещах». Это основа для классов и методов. В этом отношении, правильно спроектированный ООП может помочь управлять сложностью.

Где-то по пути кто-то решил, что мы могли бы использовать ООП, чтобы помочь решить проблему повторного использования кода. Я имею в виду, зачем изобретать велосипед? Если кто-то еще проделал большую часть работы по решению этой проблемы, используйте то, что он сделал, добавьте настройки, которые требуются вашему конкретному проекту, и вуаля! Вы создали мощное, сложное приложение с относительно небольшой работой с вашей стороны. ОО программисты могут быть очень продуктивными программистами.

Конечным результатом является то, что современные программисты OO в конечном итоге становятся «учениками колдуна», где они связывают кучу больших, громоздких библиотек с помощью нескольких строк «клея» и получают что-то, что работает. Сорта. Своего рода. Большую часть времени. Есть ли потенциальные побочные эффекты от использования этой библиотеки с этой? Может быть. Но у кого есть время, чтобы действительно покопаться в коде, содержащемся в этих библиотеках? Особенно, когда библиотеки развиваются. В результате мы получаем раздутые приложения, где программисту нужно было несколько классов и методов из этой библиотеки, но приложение должно нести вес всех ДРУГИХ вещей, которые им не нужны.

Конечным результатом является то, что вы получаете гораздо больше сложности, чем вам нужно.

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

Пока вы не должны поддерживать что-то написанное кем-то другим.

Да, приятно знать, что все функции доступа к данным находятся здесь. Но как их называть?

Этот метод вызывает этот метод в этом классе. Но когда я смотрю на определение класса, нет метода с таким именем. О, это наследуется от чего-то еще на один или два уровня в цепочке наследования. Подожди минуту; этот класс реализовал интерфейс? Сколько разных классов реализуют этот интерфейс? И мы используем какую-то сложную систему времени выполнения (я смотрю на тебя, Spring), чтобы «соединить» экземпляры классов во время выполнения? Где можно использовать ЛЮБОЙ класс, реализующий этот интерфейс?

В результате вы получаете множество маленьких, дискретных методов, которые делают точные вещи. Но этот называет его одним в другом классе. Который называет это один в другом классе. Который называет это один в другом классе. Который называет это, в дополнительном классе. Который возвращает результат определенного типа. На котором вы должны вызвать метод, чтобы сделать определенную вещь. Который возвращает результат другого типа. И т.п.

Для этого есть термин: код спагетти.

В итоге получается очень сложная система, необходимая только для написания кода. Следовательно IDE, такие как Visual Studio, Eclipse и NetBeans. Все из которых имеют значительную кривую обучения. Действительно, многие из них могут инкапсулировать / объединять несколько инструментов, разработанных разными группами, каждая из которых имеет свои собственные кривые обучения.

Это управляет сложностью?

Отладка кода в два раза сложнее, чем его написание. Удачи в отладке некоторых из этих вещей. Особенно, если он использует несколько библиотек, «соединенных вместе» во время выполнения с использованием какой-либо системы внедрения зависимостей.

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

ИМХО, это чистый убыток; это добавляет больше сложности, чем устраняет. Это позволяет вам делать вещи, которые были бы чрезвычайно сложными, возможно, даже невозможными, без него. Но любой крупный проект быстро превращается в неразрешимый беспорядок.

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

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


0

До некоторой степени...

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


0

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

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

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


1
Комментарии удалены; попытаться сохранить их гражданскими.
Fishtoaster

0

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

да, это также решение для сложности, предоставляя модель для вас, чтобы «увидеть» ваш код естественным образом, как объекты, которые имеют свойства и возможные действия

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.