Принципы SOLID | На примере Python
HTML-код
- Опубликовано: 3 июн 2024
- В этом видео мы обсудим пять принципов SOLID на примере языка Python и посмотрим, как переписать программный код с использованием этих принципов.
Таймкоды:
00:00 Введение
00:45 Кто придумал SOLID?
01:40 Принцип Single responsibility (SRP)
05:10 Принцип Open-closed (OCP)
09:13 Принцип Liskov substitution (LSP)
14:35 Принцип Interface segregation (ISP)
18:29 Принцип Dependency inversion (DIP)
23:25 Заключение
Станьте спонсором канала, и вы получите доступ к эксклюзивным бонусам: / @ilyabodrovkrukowski
Аккаунт Ethereum (ETH): 0x719C2d2bcC155c85190f20E1Cc3710F90FAFDa16
Boosty: boosty.to/bodrovis
Patreon: / bodrovis
DonationAlerts: www.donationalerts.com/r/bodr...
Исходный код: github.com/bodrovis-learning/...
Канал Telegram: t.me/dev_in_ruby_colors
Наш чат в Telegram: t.me/joinchat/MxYT6-01eeA1NTYy
Мой сайт: bodrovis.tech
Музыкальный сюрприз: • Dog & Butterfly - Hear...
Друзья, в код закралась довольно глупая ошибка. Она никак не мешает пониманию принципов SOLID (то есть сами объяснения остаются прежними), но баг весьма досадный. Вот небольшой коммит, в котором сделаны нужные исправления (суть в том, что иначе просто будет печататься одно и то же время, хотя в ряде случаев вам может потребоваться печатать именно одинаковое время, если произошло сразу много событий в один момент) github.com/bodrovis-learning/Python-SOLID-video/commit/2f98a12d55f10252aa6fa46bac8e75dc1fdb1878 Спасибо коллеге Rebbit13 за внимательность! Кстати, разделитель можно тоже хранить в формате: github.com/bodrovis-learning/Python-SOLID-video/commit/220bf6d872033d77ca19698d3608886c3475e3a6
Большое - Спасибо , отлично объяснили
Eto bojestvenno, osobenno posle kursow posmotret mnenie i primeri drugogo prepod. Laik i podpiska!
Спасибо большое!
Очень круто, спасибо! Когда уходишь от абстрактных размышлений к реальной реализации на любимом языке сразу всё становится понятным
Безусловно :)
@@IlyaBodrovKrukowski имеет ли место использовать оператор super(), ведь в классах нового стиля он может нарушить логику программы при подмешивании классов и множественном наследовании ромбовидной формы ?
как вы считаете не лучше ли явно задавать родительские классы ?
@@koshakpoc2876 Особо проблем в этом не вижу, если честно. Если логика выстроено корректно, то всё должно быть ок
Самое понятное объяснение из всех мной увиденных, спасибо
На здоровье!
Спасибо Вам большое. У Вас очень здорово получилось объяснить все и на практике и в теории, таким образом, что все сразу становится понятно. Редко где такое встретишь. Успехов Вам!
Благодарю
Лучшее видео про SOLID на примере python! Кратко и понятно! Спасибо, освежил знания перед собеседованием.
Благодарю! Удачного собеседования :)
Лучшее объяснение что я видел, огромное спасибо
На здоровье
Круто! Спасибо
Спасибо. Полезный материал.
Очень приятное объяснение, спасибо большое за видео!
Отличное видео, большое спасибо
С такими примерами, понимание неизбежно)
На здоровье!
Большое спасибо. Самое понятное и не растянутое пояснение по SOLID на простых примерах да еще на Python. Лайк, подписка, как говорится )
Спасибо большое!
Спасибо огромное за Ваш труд, очень полезное видео! За приятный голос и понятные примеры отдельная благодарность)
На здоровье
Одно из лучших объяснений на ютубе. Спасибо
На здоровье!
Каждый раз когда вы переписывали код я получал тот самый программистерский кайф от чистоты и в общем крутости кода. Примеры очень хорошие, создаётся понимание где это можно использовать. Самое главное что все очень понятно. Благодарю за хорошее видео
Благодарю! Да, в этом и правда есть свой кайф
Илья, спасибо! Самое понятное и наглядное объяснение солида! Спасибо за труды!!! Побольше бы таких видосов. За исходники - отдельная благодарность.
На здоровье
@@IlyaBodrovKrukowski Илья, Вы могли бы сделать, в таком же стиле, ещё одно видео про популярные паттерны с использованием питона? Я думаю, что общественность будет безгранично рада такому контенту. Спасибо за внимание.
@@goodevening2144 Можно подумать в эту сторону, но тут надо понять, какие из них "популярные"
Шикарное видео, спасибо большое!
Огромное спасибо! Отличное объяснение!
Thank you so much
Спасибо за урок!
на здоровье!
The best!!!!!
Боже мой, ну наконец-то кто-то понятно объяснил за вменяемое время. Мартин пишет про Java, и как это всё применить к Python, надо додумывать самому. А так как это две разные планеты, никогда не знаешь, правильно ты додумал или неправильно. И проверить свои догадки до этого видео было негде. Особенно на понимание DI кучу времени потратил, потому что в Python такое гибкое наследование, что из Java-примеров непонятно, нужен ли DI в Python вообще в принципе (нужен, конечно).
Рад, что теперь ситуация прояснилась
Респект за видео! Очень качественный контент
отличное видео, спасибо
На здоровье!
Спасибо тебе огромное!!! Просто невероятное спасибо! Просто спас мой мозг) Пытался смотреть другие источники, но там на других языках и постоянно пытался понять, как это реализуется на Python просто улетел в далекий космос к далеким друзьям) респект за прекрасную интерпретацию на моем языке)
На здоровье
Спасибо!
Спасибо тебе большое за такие понятные примеры, уже смотрел очень много видео и читал не одну статью по солид, понимал только первые 2 принципа SRP и OCP, но вот остальные 3 вообще непонятны и только после просмотра этого видео до меня наконец доперли все принципы! Спасибо тебе огромное еще раз. п.с. огромная проблема многих объяснений и видео в каких-то совсем абстрактных примерах, которые только больше запутывают и демотивируют(
На здоровье
Спасибо за видео!
4:30. Для больших проектов это безусловно так, но для среднего проекта я бы в случае необходимости создал 2-ой класс, который имеет свою комбинацию "формат", "текст" и т.п.
По фактту это будет паттерн "фабрика" или service layer (не уверен), но зато весь процесс, данные и логика в 1-м месте.
Вообще прочитав "Чистую архитектуру" я понял, что большинство советов годятся только для компилируемых языков, а пайтон... он изначально вышел хорошо)).
Очень много оверхеда в пропорции к пейлоду у пайтона получается если досконально следовать SOLID.
Не без этого, поэтому я и упоминаю, что следовать принципам до буквы не стоит :) Спасибо за подробный комментарий!
Именно поэтому я начал изучать Java, но потом понял, что Python лучше. Как говори автор "не стоит полностью следовать правилам, это вредно"
Спасибо
На здоровье :)
Несколько дней не мог понять эту инверсию зависимостей, скачал примеры из видео и вроде понял. Как-то все подозрительно просто получается :)
Ну, там не сильно-то и сложно это. В прниципе, на YT есть ролики, где объясняются эти вопросы с теоретической точки зрения, тоже имеет смысл глянуть
Ne prosto kogda probuesh pochinit kod po principam. Sovetuyu poprobovat)
Лайк, подписка, колокольчик, коммит )
Спасибо!
А как лучше всего следовать второму принципу:
1. В __init__ захардкодить префикс и сделать новый класс с наследованием первого (как в примере из видео)
или же
2. в __init__ префикс брать из параметра при инициализации класса, т.е. при инициализации класса передавать нужный префикс?
Предполагаю, что вариант 1 более наглядный, простой и потенциально меньше ошибок в себе скрывает, но хотелось бы уточнить у более опытных разработчиков
Книга: "Чистая архитектура", там Роберт Мартин говорит о SOLID. Возможно и в "Чистый код" Роберт Мартин говорит о SOLID, но, признаюсь, я её пока не читал
14:22 . с этим префиксом " _ " amout будет ломатся - если будут передаваться именные, а не позиционные параметры
На позиционные всегда расчитывать - опасная затея
в последем примере можно будет создать единый интерфейс Printer который будет реализовывать метод write. и наследуясь от принтера, классы Fileprinter и TerminalPrinter обязаны будут реализовывать метод write
Я б его, наверное, назвал Notifier )
Привет, спасибо большое
Скажи пожалуйста, как ты сделал так, чтобы у тебя подставлялось self в метод класса автоматически?
Что за плагин в vscode? Или настройка какая-то?
Спасибо
На здоровье! Да у меня ничего такого не установлено, кроме pylance и python для VS Code, так что думаю, это их проделки
Я начинающий, есть вопрос. 9:12 Непонятно зачем в методе init класса CustomerLogger нужен super() , если и без него все также работает, по крайней мере вывод такой же. Зачем делегировать родителю инициализацию атрибута format, если следующей строчкой мы все ровно этот атрибут переопределяем.
class CustomerLogger(Logger):
def __init__(self):
# super().__init__()
self.format = '%Y-%b-%d ::'
Для сохранения цепочки наследования - в будущем родитель может делать какие-то дополнительные манипуляции
@@IlyaBodrovKrukowski Спасибо, очень полезная инфа.
На 22:41 не понял, что значит инстанцировать? Ведь под notifier как бы понимается экземпляр класса FilePrinter, TerminalPrinter или другого, который передается в качестве аргумента. И у этого экземпляра вызывается метод write().
В общем notifier().write(...) наверно и правильно, но до конца я не понял почему. Потому что notifier - это не потенциальный экземпляр одного из вышеобъявленных классов, а экземпляр класса type?
notifier - это просто аргумент функции. Мы в него можем засунуть что угодно. Чтобы получить экземпляр класса, у которого есть метод write(), нам нужно сам класс передать как параметр в notifier, а затем в методе log создать его экземпляр с помощью ().
А что плохого в одном но унивресальном классе, вместо десяти маленьких?
ОРУ, спасибо, очень смешной рофл
Solid - это как метод 5S, все принципы известны до них, и использовалось ещё с машинных кодов или логика взята из оптимизации СУБД подходящих для sql, просто один очень... Человек якобы это структурировать и сказал, что то он всё придумал...
На самом деле, как и 5S - Solid в своей разработке может быть избыточна очень часто и в пустую тратит ресурсы. ( или например задачу должен выполнять специалист, но не должен напрягать этим руководителя или иного специалиста...
И не создавать другим дополнительную работу.
Вы должны, если на этапе тестирования или использования создать такой экземпляр наследуемого класса, что сам другой специалист в процессе объявления его будет создавать требования но в автоматическом режиме, в виде принимаемых входных полей.
Есть ещё одно правило, что касается - Солид, но его туда не включили, потому, что человек не обладал не знанием и не опытом в этой области или считал это избыточным.
Например - 3 правило противоречит (хотя например тот же sql говорит что всё должно быть максимально оптимизировано), но даже есть исключения...
3 правило нарушает правило - программа или процедура должна быть максимальна собрана и продумана в своей многозадачности - а пытаться обращаться например к различным потомкам одиночным образом, что бы получить один результат - это извините, надуманная глупость.
Потом на 3 наследовании окажется, что забыли указать тип покрытия животного, - чешуя, шерсть или волосы... И опять начнется?
Дальше я на стал пока смотреть (4 и 5)
по поводу single responsibility не понял одного: зачем нам класс с единственным методом, если можно просто написать обычную функцию?
Можно, в принципе. Просто раз уж мы говорим об ООП, то и используем везде классы. В более сложных случаях это был бы класс побольше, но главное тут то, что он должен решать определённую задачу, а не много задач сразу - суть в этом. Но если можно что-то сделать проще, то переусложнять код, конечно, не стоит
@@IlyaBodrovKrukowski спасибо вам за ответ и ваш труд
@@dmitriynekrasov3098
SOLID SNAKE получается... MGS референс
LSP нарушится если вызывать dog.eat(amount=3). Параметры у методов нельзя делать с разными именами!
Первый не очень пример, зачем делать класс с один методом минимум 3 я думаю нужно, максимум 4)) ну или 6 если нельзя поделить логично
Мне одному кажется, что solid плодит кучу сущностей? Может это и полезно в проектах с 1000000 строк кода, но имхо для более малых проектов большинство этих принципов бесполезны
Вы правы, как я и говорил в видео (хотя, может и не в этом ) не стоит просто следовать правил для того, чтобы им следовать. Нужно понимать, зачем это нужно. Так что да, если это маленький проект, то в целом применять весь арсенал solid часто смысла нет. Но иметь его ввиду стоит
Спасибо!
:D