{"id":272,"date":"2025-10-13T21:44:36","date_gmt":"2025-10-13T19:44:36","guid":{"rendered":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/?p=272"},"modified":"2025-10-14T13:33:47","modified_gmt":"2025-10-14T11:33:47","slug":"zasada-odwrocenia-zaleznosci","status":"publish","type":"post","link":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/?p=272","title":{"rendered":"Zasada Odwr\u00f3cenia Zale\u017cno\u015bci"},"content":{"rendered":"\n<hr class=\"wp-block-separator has-css-opacity is-style-default\"\/>\n\n\n\n<hr class=\"wp-block-separator has-css-opacity is-style-default\"\/>\n\n\n\n<div class=\"wp-block-media-text alignwide has-media-on-the-right is-stacked-on-mobile is-vertically-aligned-center has-background\" style=\"background-color:#f1f5c7\"><div class=\"wp-block-media-text__content\">\n<div class=\"wp-block-group is-layout-flow wp-block-group-is-layout-flow\" style=\"padding-top:2em;padding-right:2em;padding-bottom:2em;padding-left:2em\">\n<p style=\"font-size:36px;line-height:1.2\"><strong>Definicja<\/strong><\/p>\n\n\n\n<p class=\"has-extra-small-font-size\">Zasada odwr\u00f3cenia zale\u017cno\u015bci (<em>Dependency Inversion Principle<\/em>, DIP) m\u00f3wi, \u017ce:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote has-normal-font-size is-layout-flow wp-block-quote-is-layout-flow\">\n<p><strong>Modu\u0142y wysokiego poziomu nie powinny zale\u017ce\u0107 od modu\u0142\u00f3w niskiego poziomu. Obydwa powinny zale\u017ce\u0107 od abstrakcji.<\/strong><\/p>\n<\/blockquote>\n\n\n\n<p class=\"has-extra-small-font-size\">W praktyce oznacza to, \u017ce zamiast bezpo\u015brednio tworzy\u0107 i u\u017cywa\u0107 konkretnych klas, powinni\u015bmy opiera\u0107 si\u0119 na <strong>interfejsach lub klasach abstrakcyjnych<\/strong>.<br>Dzi\u0119ki temu kod staje si\u0119 <strong>lu\u017ano powi\u0105zany, elastyczny i \u0142atwy do modyfikacji<\/strong>.<\/p>\n<\/div>\n<\/div><figure class=\"wp-block-media-text__media\"><img data-opt-id=807734801  fetchpriority=\"high\" decoding=\"async\" width=\"1024\" height=\"683\" src=\"https:\/\/mlb55nihrfbl.i.optimole.com\/w:1024\/h:683\/q:mauto\/ig:avif\/http:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/Businessmans-hand-holding-question-mark.jpg\" alt=\"\" class=\"wp-image-240 size-full\" srcset=\"https:\/\/mlb55nihrfbl.i.optimole.com\/w:1024\/h:683\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/Businessmans-hand-holding-question-mark-scaled.jpg 1024w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:300\/h:200\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/Businessmans-hand-holding-question-mark-scaled.jpg 300w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:768\/h:512\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/Businessmans-hand-holding-question-mark-scaled.jpg 768w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:1536\/h:1024\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/Businessmans-hand-holding-question-mark-scaled.jpg 1536w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:1620\/h:1080\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/Businessmans-hand-holding-question-mark-scaled.jpg 2048w\" sizes=\"(max-width: 1000px) 100vw, 1000px\" \/><\/figure><\/div>\n\n\n\n<div class=\"wp-block-media-text alignwide is-stacked-on-mobile is-vertically-aligned-center has-background\" style=\"background-color:#fffdea\"><figure class=\"wp-block-media-text__media\"><img data-opt-id=815507356  fetchpriority=\"high\" decoding=\"async\" width=\"1024\" height=\"614\" src=\"https:\/\/mlb55nihrfbl.i.optimole.com\/w:1024\/h:614\/q:mauto\/ig:avif\/http:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/2002.i126.003_automated-robotic-packing-conveyor.jpg\" alt=\"\" class=\"wp-image-269 size-full\" srcset=\"https:\/\/mlb55nihrfbl.i.optimole.com\/w:1024\/h:614\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/2002.i126.003_automated-robotic-packing-conveyor-scaled.jpg 1024w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:300\/h:180\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/2002.i126.003_automated-robotic-packing-conveyor-scaled.jpg 300w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:768\/h:461\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/2002.i126.003_automated-robotic-packing-conveyor-scaled.jpg 768w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:1536\/h:922\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/2002.i126.003_automated-robotic-packing-conveyor-scaled.jpg 1536w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:1799\/h:1080\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/2002.i126.003_automated-robotic-packing-conveyor-scaled.jpg 2048w\" sizes=\"(max-width: 1000px) 100vw, 1000px\" \/><\/figure><div class=\"wp-block-media-text__content\">\n<div class=\"wp-block-group is-layout-flow wp-block-group-is-layout-flow\" style=\"padding-top:2em;padding-right:2em;padding-bottom:2em;padding-left:2em\">\n<p style=\"font-size:36px;line-height:1.2\"><strong>Przyk\u0142ad z \u017cycia<\/strong><\/p>\n\n\n\n<p class=\"has-extra-small-font-size\">W fabryce prefabrykat\u00f3w \u017celbetowych mamy <strong>system produkcji<\/strong>, kt\u00f3ry koordynuje r\u00f3\u017cne etapy wytwarzania element\u00f3w:<br>zbrojenie, betonowanie, transport i magazynowanie.<\/p>\n\n\n\n<p>Je\u017celi kontroler produkcji (modu\u0142 wysokiego poziomu) <strong>bezpo\u015brednio tworzy obiekty konkretnych maszyn<\/strong>, to w momencie zmiany typu maszyny (np. wymiany na nowy model) \u2013 trzeba modyfikowa\u0107 kod kontrolera.<\/p>\n\n\n\n<p class=\"has-extra-small-font-size\">Zamiast tego \u2013 kontroler powinien komunikowa\u0107 si\u0119 z maszynami <strong>przez interfejs<\/strong> (abstrakcj\u0119),<br>a konkretne implementacje maszyn mo\u017cna \u0142atwo podmienia\u0107 bez ingerencji w logik\u0119 steruj\u0105c\u0105.<\/p>\n<\/div>\n<\/div><\/div>\n\n\n\n<h2 class=\"wp-block-heading\" style=\"font-size:38px;line-height:1.4\"><strong>Przyk\u0142ady przed i po zastosowaniu zasady<\/strong><\/h2>\n\n\n\n<div class=\"wp-block-columns is-layout-flex wp-container-core-columns-is-layout-28f84493 wp-block-columns-is-layout-flex\">\n<div class=\"wp-block-column is-layout-flow wp-block-column-is-layout-flow\">\n<p><strong>PRZED<\/strong><\/p>\n\n\n\n<p style=\"font-size:18px\"><strong>Problem:<\/strong><\/p>\n\n\n\n<p style=\"font-size:18px\">Kod jest ma\u0142o elastyczny i trudny do testowania.<\/p>\n\n\n\n<p><code>ProductionController<\/code> jest <strong>\u015bci\u015ble zale\u017cny<\/strong> od klasy <code>ConcreteMachine<\/code>.<\/p>\n\n\n\n<p>Je\u015bli chcemy doda\u0107 nowy typ maszyny (np. <code>AutomaticConcreteMachine<\/code>), musimy <strong>zmieni\u0107 kod kontrolera<\/strong>.<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: java; title: ; notranslate\" title=\"\">\nclass ConcreteMachine {\n    public void pourConcrete() {\n        System.out.println(&quot;Pouring concrete into the mold...&quot;);\n    }\n}\n\n\n\nclass ProductionController {\n    private ConcreteMachine machine = new ConcreteMachine();\n\n    public void startProduction() {\n        machine.pourConcrete();\n    }\n}\n\n\n\npublic class Main {\n    public static void main(String&#x5B;] args) {\n        ProductionController controller = new ProductionController();\n        controller.startProduction();\n    }\n}\n<\/pre><\/div>\n\n\n<figure class=\"wp-block-image size-large\"><img data-opt-id=1811348755  data-opt-src=\"https:\/\/mlb55nihrfbl.i.optimole.com\/w:683\/h:1024\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/digital-manufacturing-specialist-enhancing-production-efficiency.jpg\"  decoding=\"async\" width=\"683\" height=\"1024\" src=\"data:image/svg+xml,%3Csvg%20viewBox%3D%220%200%20683%201024%22%20width%3D%22683%22%20height%3D%221024%22%20xmlns%3D%22http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%22%3E%3Crect%20width%3D%22683%22%20height%3D%221024%22%20fill%3D%22transparent%22%2F%3E%3C%2Fsvg%3E\" alt=\"\" class=\"wp-image-304\" old-srcset=\"https:\/\/mlb55nihrfbl.i.optimole.com\/w:683\/h:1024\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/digital-manufacturing-specialist-enhancing-production-efficiency-scaled.jpg 683w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:200\/h:300\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/digital-manufacturing-specialist-enhancing-production-efficiency-scaled.jpg 200w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:720\/h:1080\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/digital-manufacturing-specialist-enhancing-production-efficiency-scaled.jpg 768w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:720\/h:1080\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/digital-manufacturing-specialist-enhancing-production-efficiency-scaled.jpg 1024w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:719\/h:1080\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/digital-manufacturing-specialist-enhancing-production-efficiency-scaled.jpg 1365w, https:\/\/mlb55nihrfbl.i.optimole.com\/w:720\/h:1080\/q:mauto\/ig:avif\/https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/wp-content\/uploads\/2025\/10\/digital-manufacturing-specialist-enhancing-production-efficiency-scaled.jpg 1707w\" \/><figcaption class=\"wp-element-caption\">Designed by Freepik<\/figcaption><\/figure>\n<\/div>\n\n\n\n<div class=\"wp-block-column is-layout-flow wp-block-column-is-layout-flow\">\n<p><strong>PO<\/strong><\/p>\n\n\n\n<p>Zastosujmy zasad\u0119 <strong>Dependency Inversion Principle<\/strong>, wprowadzaj\u0105c <strong>interfejs<\/strong> opisuj\u0105cy og\u00f3lne zachowanie maszyny.<br>Kontroler b\u0119dzie zale\u017ce\u0107 od tego interfejsu \u2013 a nie od konkretnej klasy.<\/p>\n\n\n\n<p><strong>Dlaczego teraz dzia\u0142a lepiej:<\/strong><\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><code>ProductionController<\/code> nie zale\u017cy od konkretnej klasy (<code>ManualConcreteMachine<\/code> czy <code>AutomaticConcreteMachine<\/code>).<\/li>\n\n\n\n<li>Zale\u017cno\u015b\u0107 jest <strong>odwr\u00f3cona<\/strong> \u2013 kontroler zna tylko interfejs <code>ConcreteWorker<\/code>.<\/li>\n\n\n\n<li>Mo\u017cna \u0142atwo wprowadzi\u0107 now\u0105 maszyn\u0119, np. <code>SmartConcreteMachine<\/code>, bez modyfikowania kontrolera.<\/li>\n<\/ul>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: java; title: ; notranslate\" title=\"\">\n\/\/ Abstrakcja (interfejs)\ninterface ConcreteWorker {\n    void pourConcrete();\n}\n\n\/\/ Konkretne implementacje\nclass ManualConcreteMachine implements ConcreteWorker {\n    @Override\n    public void pourConcrete() {\n        System.out.println(&quot;Pouring concrete manually...&quot;);\n    }\n}\n\nclass AutomaticConcreteMachine implements ConcreteWorker {\n    @Override\n    public void pourConcrete() {\n        System.out.println(&quot;Pouring concrete automatically with robotic arm...&quot;);\n    }\n}\n\n\/\/ Modu\u0142 wysokiego poziomu (zale\u017cny od abstrakcji, a nie od implementacji)\nclass ProductionController {\n    private ConcreteWorker worker;\n\n    \/\/ Wstrzykni\u0119cie zale\u017cno\u015bci (Dependency Injection)\n    public ProductionController(ConcreteWorker worker) {\n        this.worker = worker;\n    }\n\n    public void startProduction() {\n        System.out.println(&quot;Starting production process...&quot;);\n        worker.pourConcrete();\n    }\n}\n\n\/\/ Klasa g\u0142\u00f3wna \u2013 przyk\u0142ad u\u017cycia\npublic class Main {\n    public static void main(String&#x5B;] args) {\n        \/\/ Mo\u017cemy \u0142atwo wymienia\u0107 implementacje bez zmiany kontrolera\n        ConcreteWorker manual = new ManualConcreteMachine();\n        ConcreteWorker automatic = new AutomaticConcreteMachine();\n\n        ProductionController controller1 = new ProductionController(manual);\n        ProductionController controller2 = new ProductionController(automatic);\n\n        controller1.startProduction();\n        controller2.startProduction();\n    }\n}\n<\/pre><\/div><\/div>\n<\/div>\n\n\n\n<p><\/p>\n\n\n\n<div class=\"wp-block-columns alignwide is-layout-flex wp-container-core-columns-is-layout-d2da2050 wp-block-columns-is-layout-flex\" style=\"margin-bottom:0\">\n<div class=\"wp-block-column has-text-color has-background has-link-color wp-elements-a685da0f548d69545c08acb9e74bddac is-layout-flow wp-block-column-is-layout-flow\" style=\"color:#000000;background-color:#ffe97d;padding-top:2em;padding-right:2em;padding-bottom:2em;padding-left:2em\">\n<p class=\"has-normal-font-size\" style=\"line-height:1.5\"><strong>Kiedy zasada jest wa\u017cna?<\/strong><\/p>\n\n\n\n<hr class=\"wp-block-separator has-text-color has-css-opacity has-background is-style-wide\" style=\"background-color:#000000;color:#000000\"\/>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Gdy system ma si\u0119 rozwija\u0107 (dodawanie nowych urz\u0105dze\u0144, etap\u00f3w produkcji, funkcji).<\/li>\n<\/ul>\n\n\n\n<ul class=\"wp-block-list\">\n<li>W projektach z wieloma warstwami (np. kontrolery, serwisy, dost\u0119p do bazy danych).<\/li>\n<\/ul>\n<\/div>\n\n\n\n<div class=\"wp-block-column has-text-color has-background has-link-color wp-elements-69a25a96c3c1714f8dbc61698e4e2451 is-layout-flow wp-block-column-is-layout-flow\" style=\"color:#000000;background-color:#d1d1e1;padding-top:2em;padding-right:2em;padding-bottom:2em;padding-left:2em\">\n<p class=\"has-normal-font-size\" style=\"line-height:1.5\"><strong>Na co zwraca\u0107 uwag\u0119:<\/strong><\/p>\n\n\n\n<hr class=\"wp-block-separator has-css-opacity is-style-wide\"\/>\n\n\n\n<ul class=\"wp-block-list has-normal-font-size\">\n<li>U\u017cywaj <strong>interfejs\u00f3w lub klas abstrakcyjnych<\/strong> jako punkt\u00f3w zale\u017cno\u015bci.<\/li>\n\n\n\n<li>Stosuj <strong>wstrzykiwanie zale\u017cno\u015bci (Dependency Injection)<\/strong> przez konstruktor lub setter.<\/li>\n<\/ul>\n<\/div>\n\n\n\n<div class=\"wp-block-column has-text-color has-background has-link-color wp-elements-f11519180ef6e2987d46500416164142 is-layout-flow wp-block-column-is-layout-flow\" style=\"color:#000000;background-color:#c0ebf1;padding-top:2em;padding-right:2em;padding-bottom:2em;padding-left:2em\">\n<p class=\"has-normal-font-size\"><strong>Trudno\u015bci:<\/strong><\/p>\n\n\n\n<hr class=\"wp-block-separator has-css-opacity is-style-wide\"\/>\n\n\n\n<ul class=\"wp-block-list has-normal-font-size\">\n<li>Pocz\u0105tkowo kod mo\u017ce wydawa\u0107 si\u0119 bardziej z\u0142o\u017cony (wi\u0119cej klas i interfejs\u00f3w),<\/li>\n\n\n\n<li>Jednak w d\u0142u\u017cszej perspektywie przynosi ogromne korzy\u015bci w utrzymaniu i testowaniu kodu.<\/li>\n<\/ul>\n<\/div>\n<\/div>\n","protected":false},"excerpt":{"rendered":"<p>Przyk\u0142ady przed i po zastosowaniu zasady PRZED Problem: Kod jest ma\u0142o elastyczny i trudny do testowania. ProductionController jest \u015bci\u015ble zale\u017cny od klasy ConcreteMachine. Je\u015bli chcemy doda\u0107 nowy typ maszyny (np. AutomaticConcreteMachine), musimy zmieni\u0107 kod kontrolera. PO Zastosujmy zasad\u0119 Dependency Inversion Principle, wprowadzaj\u0105c interfejs opisuj\u0105cy og\u00f3lne zachowanie maszyny.Kontroler b\u0119dzie zale\u017ce\u0107 od tego interfejsu \u2013 a nie [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":273,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[9],"tags":[],"class_list":["post-272","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-solid"],"_links":{"self":[{"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=\/wp\/v2\/posts\/272","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=272"}],"version-history":[{"count":5,"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=\/wp\/v2\/posts\/272\/revisions"}],"predecessor-version":[{"id":305,"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=\/wp\/v2\/posts\/272\/revisions\/305"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=\/wp\/v2\/media\/273"}],"wp:attachment":[{"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=272"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=272"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/ewelina-beben.profesjonalnyprogramista.pl\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=272"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}