Какая практика лучше? Передача ссылок на объекты или ссылок на методы объекта в Python

Я пишу небольшой фрагмент кода на Python, и мне любопытно, что другие люди думают об этом.

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

def do_something(self, x, y, manipulator):
    self.my_value = manipulator.process(x, y)

или это

def do_the_same_thing_but_differently(self, x, y, manipulation):
    self.my_value = manipulation(x, y)

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

РЕДАКТИРОВАНИЕ: я удалил формулировку ООП, потому что она явно расстраивала. В основном я имел в виду слабую связанность и высокую сплоченность.


person Corey D    schedule 09.01.2011    source источник
comment
Сильнее ООП? Что вы измеряете для силы ООП? Я никогда не видел этого раньше. У вас есть цитата или ссылка?   -  person S.Lott    schedule 09.01.2011
comment
en.wikipedia.org/wiki/Loose_coupling   -  person Corey D    schedule 09.01.2011
comment
Что лучше, зависит от того, чего вы пытаетесь достичь. Если функция заинтересована только в вызове этого метода, передача этого метода дает вам большую гибкость (вы можете дать ей любой вызываемый объект). С другой стороны, если он хочет сделать что-то еще с объектом manipulator или если вы хотите быть уверены, что вызываете только определенный метод, вы должны использовать первый метод.   -  person Thomas K    schedule 09.01.2011
comment
Это сцепление, а не ОО. Мне любопытно, как вы используете фразу Stronger OOP. Меня не интересуют сильная связь и слабая связь.   -  person S.Lott    schedule 09.01.2011
comment
явно расстраивает? Возможно, вы имели в виду путаницу.   -  person S.Lott    schedule 10.01.2011


Ответы (3)


Второе решение может обеспечить более слабую связь, потому что оно более «функционально», а не более «ООП». Преимущество первого решения в том, что оно работает на таких языках, как C++, в которых нет замыканий (хотя можно добиться аналогичного эффекта, используя шаблоны и функции указателя на член); но на таком языке, как Python, ИМХО вторая альтернатива кажется более «естественной».

РЕДАКТИРОВАТЬ: вы найдете очень хорошее обсуждение методов "функционального и объектно-ориентированного" в бесплатной книге "Higher order Perl", доступной здесь:

http://hop.perl.plover.com/

(см. главу 1, часть 6). Хотя это книга по Perl (а не по Python), обсуждение в ней точно соответствует заданному здесь вопросу, и описанные там функциональные приемы могут быть аналогичным образом применены к Python.

person Doc Brown    schedule 09.01.2011
comment
Согласованный. Если единственной целью манипулятора является предоставление функции процесса, то, безусловно, более Pythonic будет передавать саму функцию, а не объект. - person AndreiM; 09.01.2011
comment
Вот вопрос. Соответствует ли более функциональный более строгим критериям ООП? Или более функциональный означает более слабое ООП? Я думаю, что на вопрос - как написано - действительно трудно ответить прямо. - person S.Lott; 09.01.2011
comment
ИМХО Функциональная и объектно-ориентированная - в основном ортогональные парадигмы. Так что более функциональный не означает более или менее ООП и наоборот. - person Doc Brown; 09.01.2011
comment
@Doc Brown: Таким образом, более функциональный не означает... бесконечное количество вещей. Что это означает? Соответствует ли более функциональный более строгим критериям ООП? Или более функциональный означает более слабое ООП? - person S.Lott; 10.01.2011
comment
@С. Лотт: извините, меня не интересуют философские дискуссии. Возможно, вы попробуете заглянуть в первую главу бесплатной книги, на которую я дал ссылку выше, и сформулируете собственную точку зрения. - person Doc Brown; 10.01.2011
comment
@Doc Brown: я пытаюсь понять ваши комментарии. Вы сказали, что функциональная и объектно-ориентированная парадигмы в основном ортогональные. Я могу это разобрать. Похоже, более функциональный менее объектно-ориентирован. Затем вы сказали другие вещи, которые я не могу разобрать. Я пытаюсь понять все, что ты сказал. Можете ли вы дать простое разъяснение вопроса, соответствует ли более функциональный более строгим критериям ООП? Я не могу разобрать некоторые вещи, которые вы сказали. Пожалуйста, поясните ваши комментарии. Моя точка зрения не при чем. Ваши комментарии - это то, что я хочу понять. - person S.Lott; 10.01.2011
comment
@С. Лотт: ортогональный - это другое слово для почти независимого (в качестве метафоры я имел в виду диаграмму с системой координат, где одна ось - это ООП против не-ООП, а другая ось - функциональная против императивной). Может быть, просто неправильное понимание этого слова? - person Doc Brown; 10.01.2011

Я скажу второй подход; потому что это определенно похоже на обратный вызов, который они очень часто используют при использовании голливудский принцип (не звоните нам, мы позвоним вам), парадигма, которая помогает в развитии код с высокой связностью и низкой связанностью [Ссылка 2].

person mouad    schedule 09.01.2011

Я бы определенно пошел со вторым подходом.

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

person Karl Knechtel    schedule 09.01.2011