Не совсем понял зачем мешать DDD с ФП. DDD создан для, и хорошо встраивается в, ООП из-за сугубой концептуальной скудности последнего. Область ФП скудностью не страдает, даже наоборот, тут концепций на столетия вперед.
Подскажите, пожалуйста, как обстоят дела с банковскими переводами из-за кордона, ЕС, ЮК. Можно ли комфортно, получать переводы в евро или долларах и хранить их на счетах не переводя в тенге. Спасибо.
Функции почти всегда выходят чистыми и карированными, так что никакого состояния в модулях нет и быть не может. Это ваши оопэшные проблемы, на ФП уровне их просто нет.
Да для описания логики почти одинаково, только отступов больше и конструкторов всяких. Пляски начинаются когда все эти классы нужно использовать, тут или в ручную, или через управление зависимостями. И еще автор не использует нотации типов, и это очень плохо для DDD кармы :) .
Спасибо за перевод, но по мне статья так себе. Имплементации автора, на мой взгляд, через чур избыточны и выглядят как натягивание совы C# на глобус Питона. Сами пилим DDD на питоне и пока никакой нужды в классах не видели, все доменные сущности, сервисы, репозитории, итд, реализованны как модули(файл с функциями) и все просто прекрасно.
Но можно так же сказать, что функция sort_by зависит от cmp.
В плане ООП, нельзя, ведь функция не является экземпляром чего-либо(хотя технически это неверно). Рассматривайте ее как часть статического класса на какой-нибудь Java. cmp это аргумент функции только и всего.
Есть ли у нас такое выше? Нет.
Вот как можно представить sortBy если бы у нас был foldrDefEmpty : sortBy = (foldDefEmpty . insertBy), где F это foldDefEmpty, a insertBy G. Что в результате даст foldDefEmpty(insertBy(cmp))
Мы немного в сторону ушли, цель моего комментария сказать что на Питоне можно писать качественный, тестируемый код прибегая к принципам ФП, которые в свою очередь, по полноте своей, обнуляют хоть какой-то смысл использовать DI. Значит ли это что ФП есть единственный путь - нет. Значит ли это что ФП есть самый удобный путь, ИМХО - да (не буду лукавить на Питоне не всегда). Значит ли это что ФП пропитан принципами DI, нет, я бы сказал наоборот, как и все хорошее что можно найти в ООП.
В первом случае у нас работает принцип инверсии зависимости (функция не знает что она вызовет, но знает абстракцию), во втором случае у нас невозможно повторное использование функции в чуть других условиях.
Секундочку, мы говорим о концепциях ФП в Питоне. Таких концепциях как функциональная композиция, которые являются частью ФП с самого начала и, следовательно, были реализованны например в Lisp аж в 1958г. Принципы DI увидели свет гораздо позже ООП, как средство закрытия бреши самой концепции ООП. Пожалуйста, вот не нужно, принципы инверсии совать туда где их нет и быть не может.
По сортировке, есть функция sort, которая склеена(не вызывает, а именно склеена!) из более мелких функций. Возьмем пример из Haskell:
sort :: (Ord a) => [a] -> [a]
sort = sortBy compare
sortBy :: (a -> a -> Ordering) -> [a] -> [a]
sortBy cmp = foldr (insertBy cmp) []
insertBy :: (a -> a -> Ordering) -> a -> [a] -> [a]
insertBy cmp x [] = [x]
insertBy cmp x ys@(y:ys')
= case cmp x y of
GT -> y : insertBy cmp x ys'
_ -> x : ys
Посмотрите на сигнатуру: (a -> a -> Ordering) -> [a] -> [a], функция sortBy, это каррированя(по нормальному все функции должны быть только такими) функция, которая "разложена" и при получении первого аргумента, функции (a -> a -> Ordering), вернет нам функцию [a] -> [a], которая уже при получении [a], "сработает" и вернет результат. И может показаться что foldr вызывается и возвращает результат, но это не так, foldr здесь встроена и является частью цепочки. В Питоне можно почти так же писать с помощью toolz например.
Погодите. Вот допустим у вас есть функция foo, которая вызывает функцию bar. Вы можете сделать это напрямую или передавать bar как аргумент. Тогда вы можете сделать foo1 = partial(foo, bar) - и вот у вас внедрение зависимости в функциональном стиле.
Нет это не внедрение зависимости в ФП стиле, это костыль. У меня может быть функция moveMoney, которая выполняет сначала валидацию, списывает деньги с одного счета и записывает на другой. Так вот ее определение будет, если упростить: moveMoney: TransferOperation -> bool = validate >> take >> move
В ФП на нижнем уровне я определяю маленькие функции, кирпичики, а на более высоком я их склеиваю с помощью композиции. Все прекрасно тестируется и может мокатся на более высоких уровнях для интеграционных тестов.
На мой вопрос вы так и не ответили: чем DI мешает или не помогает?
DI просто не нужен, это анахронизм, избыточность. А все что избыточно есть не мера, а антимера.
Концепция универсальная и относится не только к ООП, но и к ФП (даже если называется там по другому)
Если так рефлексировать то можно поставить знак равенства между ООП и ФП, все же ведь программирование в конце концов.
А разговаривая про ФП, я не понимаю вашего противопоставления каррирования и DI, по факту это тот же механизм, но примененный функциям, а не объектам.
А вот и нет, это довольно разные концепции и механизмы.
И все таки раскройте мысль почему внедрение зависимостей в Python не приносить пользы и атипаттерн по вашему мнению.
Питон можно использовать в двух парадигмах. ФП, хоть это и не так удобно и практично как в Haskell, Clojure или F#. Если вы выбираете ФП, то вам и внедрение зависимостей не нужно и выступает как тормоз.
Да и в ООП на Питоне, на мой взгляд, это на любителя.
Расскажите подробнее, почему DI - это антипаттерн.
Будьте любезны, из контекста не выдирайте отдельные слова. Я же говорил:
на мой взгляд, внедрение зависимостей в таких языках как Python или Ruby не приносит ничего полезного, ИМХО, это антипаттерн.
Вот несколько мнений, может ингода пафосных, но доходчивых почему при смене парадигмы, DI превращается в костыль:
- Про Haskell - Про F# (более детальная рефлексия)
В ФП нет классов, есть только функции, и механизмы работы с ними, каррирование, композиция, partial application, итд. Все это с лихвой и более заменяет DI на Python, Ruby, TypeScript, etc.
Спасибо.
Не подскажете, когда там планируют от Type Erasure избавиться и завести поддержку обобщений на уровне байт-кода?
Мне одному показалось или IE оказался самым "неломаемым" браузером?
Интересно, а могут ли данные системы противодействовать дронам камикадзе(или даже nlaw/javelin) и если да, то на каком расстоянии.
Это платное расширение?
Не совсем понял зачем мешать DDD с ФП. DDD создан для, и хорошо встраивается в, ООП из-за сугубой концептуальной скудности последнего. Область ФП скудностью не страдает, даже наоборот, тут концепций на столетия вперед.
Вас понял, спасибо. Подскажите, нужно ли при выставлении счета указывать банк корреспондент или через прямой IBAN все проходит?
Подскажите, пожалуйста, как обстоят дела с банковскими переводами из-за кордона, ЕС, ЮК. Можно ли комфортно, получать переводы в евро или долларах и хранить их на счетах не переводя в тенге. Спасибо.
2.8Гб Ram в 2022, нет спасибо, я лучше продолжу с Xubuntu и ее 0.6Гб Ram.
Функции почти всегда выходят чистыми и карированными, так что никакого состояния в модулях нет и быть не может. Это ваши оопэшные проблемы, на ФП уровне их просто нет.
Да для описания логики почти одинаково, только отступов больше и конструкторов всяких. Пляски начинаются когда все эти классы нужно использовать, тут или в ручную, или через управление зависимостями. И еще автор не использует нотации типов, и это очень плохо для DDD кармы :) .
Простите, но когда вижу советы от нетфликса сразу вспоминаю:
Колобок
Спасибо за перевод, но по мне статья так себе. Имплементации автора, на мой взгляд, через чур избыточны и выглядят как натягивание совы C# на глобус Питона. Сами пилим DDD на питоне и пока никакой нужды в классах не видели, все доменные сущности, сервисы, репозитории, итд, реализованны как модули(файл с функциями) и все просто прекрасно.
А помните как это было без обобщений и с каким энтузиазмом мы приветствовали .net 2.0 ? Как летит время.
У нас есть и то и то. Pydantic на самом верху в связке с FastAPI, а вот все что бузинес и ниже все на attrs, ибо pydantic просто адски громоздкий.
От себя могу добавить что dataclasses это хорошо, а вот attrs это намного лучше, и по объективным причинам, он никогда не станет частью Питон.
В плане ООП, нельзя, ведь функция не является экземпляром чего-либо(хотя технически это неверно). Рассматривайте ее как часть статического класса на какой-нибудь Java. cmp это аргумент функции только и всего.
Вот как можно представить sortBy если бы у нас был foldrDefEmpty : sortBy = (foldDefEmpty . insertBy), где F это foldDefEmpty, a insertBy G. Что в результате даст foldDefEmpty(insertBy(cmp))
Мы немного в сторону ушли, цель моего комментария сказать что на Питоне можно писать качественный, тестируемый код прибегая к принципам ФП, которые в свою очередь, по полноте своей, обнуляют хоть какой-то смысл использовать DI. Значит ли это что ФП есть единственный путь - нет. Значит ли это что ФП есть самый удобный путь, ИМХО - да (не буду лукавить на Питоне не всегда). Значит ли это что ФП пропитан принципами DI, нет, я бы сказал наоборот, как и все хорошее что можно найти в ООП.
Секундочку, мы говорим о концепциях ФП в Питоне. Таких концепциях как функциональная композиция, которые являются частью ФП с самого начала и, следовательно, были реализованны например в Lisp аж в 1958г. Принципы DI увидели свет гораздо позже ООП, как средство закрытия бреши самой концепции ООП. Пожалуйста, вот не нужно, принципы инверсии совать туда где их нет и быть не может.
По сортировке, есть функция sort, которая склеена(не вызывает, а именно склеена!) из более мелких функций. Возьмем пример из Haskell:
Посмотрите на сигнатуру: (a -> a -> Ordering) -> [a] -> [a], функция sortBy, это каррированя(по нормальному все функции должны быть только такими) функция, которая "разложена" и при получении первого аргумента, функции (a -> a -> Ordering), вернет нам функцию [a] -> [a], которая уже при получении [a], "сработает" и вернет результат. И может показаться что foldr вызывается и возвращает результат, но это не так, foldr здесь встроена и является частью цепочки. В Питоне можно почти так же писать с помощью toolz например.
Нет это не внедрение зависимости в ФП стиле, это костыль.
У меня может быть функция moveMoney, которая выполняет сначала валидацию, списывает деньги с одного счета и записывает на другой. Так вот ее определение будет, если упростить:
moveMoney: TransferOperation -> bool = validate >> take >> move
В ФП на нижнем уровне я определяю маленькие функции, кирпичики, а на более высоком я их склеиваю с помощью композиции. Все прекрасно тестируется и может мокатся на более высоких уровнях для интеграционных тестов.
DI просто не нужен, это анахронизм, избыточность. А все что избыточно есть не мера, а антимера.
Если так рефлексировать то можно поставить знак равенства между ООП и ФП, все же ведь программирование в конце концов.
А вот и нет, это довольно разные концепции и механизмы.
Питон можно использовать в двух парадигмах. ФП, хоть это и не так удобно и практично как в Haskell, Clojure или F#. Если вы выбираете ФП, то вам и внедрение зависимостей не нужно и выступает как тормоз.
Да и в ООП на Питоне, на мой взгляд, это на любителя.
Будьте любезны, из контекста не выдирайте отдельные слова. Я же говорил:
Вот несколько мнений, может ингода пафосных, но доходчивых почему при смене парадигмы, DI превращается в костыль:
- Про Haskell
- Про F# (более детальная рефлексия)
В ФП нет классов, есть только функции, и механизмы работы с ними, каррирование, композиция, partial application, итд. Все это с лихвой и более заменяет DI на Python, Ruby, TypeScript, etc.