Kontrolün Tersine Dönüşümü ve Bağımlılık Enjeksiyonu


525

Martin Fowler tarafından yazılan makaleye göre , kontrolün ters çevrilmesi, bir programın kontrol akışının ters çevrildiği ilkedir: bir programın akışını kontrol eden programcı yerine, dış kaynaklar (çerçeve, hizmetler, diğer bileşenler) o. Sanki başka bir şeye bir şey takıyoruz. EJB 2.0 hakkında bir örnek verdi:

Örneğin, Oturum Bean arabirimi ejbRemove, ejbPassivate (ikincil depolamaya depolanır) ve ejbActivate'i (pasif durumdan geri yüklenir) tanımlar. Bu yöntemlerin ne zaman çağrıldığını, ne yaptıklarını kontrol edemezsiniz. Konteyner bizi çağırıyor, biz çağırmıyoruz.

Bu, çerçeve ve kütüphane arasındaki farka yol açar:

Denetimi Tersine Çevirme, çerçeveyi kütüphaneden farklı kılan şeyin önemli bir parçasıdır. Bir kütüphane aslında arayabileceğiniz bir dizi işlevdir, bu günlerde genellikle sınıflar halinde düzenlenmiştir. Her çağrı bir iş yapar ve kontrolü istemciye döndürür.

Bence DI'nin IOC olduğu bakış açısı, bir nesnenin bağımlılığının tersine çevrilmesi anlamına gelir: kendi bağımlılıklarını kontrol etmek yerine, yaşam döngüsü ... sizin için başka bir şey yapar. Ancak, bana DI hakkında el ile söylediğin gibi, DI mutlaka IOC değildir. Hala DI olabilir ve IOC olmayabilir.

Bununla birlikte, bu makalede (pococapsule'den, C / C ++ için başka bir IOC Çerçevesi), IOC ve DI nedeniyle, IOC kapları ve DI çerçevelerinin J2EE'den çok daha üstündür, çünkü J2EE çerçeve kodunu bileşenlere karıştırır böylece Düz Eski Java / C ++ Nesnesi (POJO / POCO) yapmaz.

Bağımlılık Enjeksiyon kalıbı dışındaki Kontrol Kaplarının Ters Çevrilmesi (Arşiv bağlantısı)

Yukarıdaki ikinci makaleye götüren eski Bileşen Tabanlı Geliştirme Çerçevesinde sorunun ne olduğunu anlamak için ek okuma: Neden ve ne Denetimi Ters Çevirme (Arşiv bağlantısı)

Sorum : IOC ve DI tam olarak nedir? Kafam karıştı. Pococapsule'a dayanan IOC, nesneler veya programcılar ve çerçeveler arasındaki kontrolün ters çevrilmesinden daha önemli bir şeydir.


2
İşte konu hakkında iyi bir yazı, IoC vs DI (Dependency Inject) vs SL (Servis Bulucu): tinyurl.com/kk4be58 - Url'den alıntı : IoC vs DI (Dependency Injection)? IoC akışının kontrolü genel bir kavramdır Ters çerçeveye istemci kodu, “müşteri için mu şey” den. SL (Servis Bulucu) ve DI (Bağımlılık Enjeksiyonu) IoC'den çıkan iki tasarım modelidir.
Swab.Jat

İki sentimi eklemek için, bir bağımlılık enjeksiyonunun bir kahve dükkanı temasında nasıl yardımcı olabileceği ile ilgileniyorsanız, bunun hakkında bir makale yazdım: digigene.com/design-patterns/dependency-injection-coffeeshop
Ali Nem


Bağımlılığın tersine çevrilmesi: Somutlaşmalara değil, soyutlamalara bağlıdır. Kontrolün ters çevrilmesi: Ana ve Soyutlamanın karşılaştırılması ve Ana'nın sistemlerin tutkalı olması. Bunlar bunun hakkında konuşan iyi mesajlardır: coderstower.com/2019/03/26/… coderstower.com/2019/04/02/… coderstower.com/2019/04/09/…
Daniel Andres Pelaez Lopez

bu derin hakkında okuyun, tüm martinfowler.com/articles/…
Dushman

Yanıtlar:


644

IoC , uygulamanın yöntemleri bir çerçevede çağırmasını sağlamak yerine genel bir terimdir; çerçeve, uygulama tarafından sağlanan uygulamaları çağırır.

DI , uygulamaların bir nesneye yapıcıları / ayarlayıcıları / servis aramaları yoluyla aktarıldığı ve nesnenin doğru davranması için 'bağımlı' olacağı bir IoC biçimidir.

Örneğin DI kullanılmadan IoC , Şablon kalıbı olur çünkü uygulama yalnızca alt sınıflandırma yoluyla değiştirilebilir.

DI Çerçeveleri DI'den faydalanmak için tasarlanmıştır ve uygulamaların aktarılmasını kolaylaştırmak için arayüzleri (veya Java'daki Ek Açıklamaları) tanımlayabilir.

IoC Kapsayıcılar programlama dilinin dışında çalışabilen DI çerçeveleridir. Bazılarında, meta veri dosyalarında (ör. XML) daha az invaziv olan hangi uygulamaların kullanılacağını yapılandırabilirsiniz. Bazılarıyla normalde imkansız olan IoC'yi nokta kesimlerde bir uygulama enjekte etmek gibi yapabilirsiniz .

Ayrıca bu Martin Fowler'in makalesine bakın .


2
Cevap için teşekkürler. Ancak diğer makale, IOC ile IOC konteynerlerinin EJB'den çok daha üstün olduğunu öne sürerken, Martin Fowler EJB'nin tipik bir IOC örneği olduğunu öne sürüyor.
Amumu

5
EJB yönetimi gerçekten IoC'nin tipik bir örneğidir. Bir EJB'nin yaşam döngüsünün programcı tarafından değil, konteyner tarafından yönetildiği gerçeğinden görebilirsiniz. Denetim sunucuya devredildiği için programcı bir EJB örneği oluşturmaz veya yok etmez . IoC kavramı budur: harici kod, kodunuzun ne zaman çağrıldığını kontrol eder, bu genellikle çoğu zaman yaptığı şeyin tersidir .
brandizzi

2
IoC, uygulamanın yöntemleri bir çerçevede çağırmasını sağlamak yerine genel bir terimdir; çerçeve, uygulama tarafından sağlanan uygulamaları çağırır. Bununla ilgili daha fazla açıklayabilir misiniz?
Imad Alazani

21
Aka Hollywood prensibi , 'bizi arama, seni arayacağız'. Çağrıyı uygulamadan ziyade çerçeveye bırakır.
Garrett Hall

@ImadAlazani, Garrett'ın eklediği makaleyi okumanız iyi olur, bu da kontrolü uygulama kodundan çerçeveye çevirmek hakkında ayrıntılı bir tartışmadır.
MengT

210

Kısacası, IoC, DI'yi içeren ancak bunlarla sınırlı olmayan çok daha geniş bir terimdir.

Inversion of Control (IoC) terimi aslında genel bir çerçevenin veya çalışma süresinin program akışını kontrol ettiği her türlü programlama stili anlamına geliyordu

DI bir isme sahip olmadan önce insanlar Bağımlılıkları Kontrol Kapsayıcılarını Ters Çevirme olarak yöneten çerçevelere atıfta bulunmaya başladılar ve yakında IoC'nin anlamı yavaş yavaş bu özel anlama doğru yöneldi: Bağımlılıklar Üzerindeki Kontrolün Tersine Dönmesi.

Kontrolü Tersine Çevirme (IoC), nesnelerin işlerini yapmak için güvendikleri başka nesneler oluşturmadığı anlamına gelir. Bunun yerine, ihtiyaç duydukları nesneleri bir dış kaynaktan alırlar (örneğin, bir xml yapılandırma dosyası).

Bağımlılık Enjeksiyonu (DI), bunun nesne müdahalesi olmadan, genellikle yapıcı parametrelerini geçen ve özellikleri ayarlayan bir çerçeve bileşeni tarafından yapıldığı anlamına gelir.


1
Görünüşe göre IoC, Depresyon İnversiyonu prensibi için başka bir terim, değil mi?
Todd Vance

@ToddVance - Evet, bence IoC ve DIP aynı şey. DIP ve DI aynı şey değildir. IoC, DI olmadan yapılabilir, ancak DI, IoC olmadan yapılamaz.
Eljay

2
@ToddVance - Hayır, DIP ve IoC eş anlamlı değildir ve ilgili değildir.
TSmith

3
Ha, bu yüzden bu iş parçacığındayım ... "İnversiyon Kontrol ve Bağımlılık Enjeksiyonu"
Todd Vance

50

resim açıklamasını buraya girin
kaynak

IoC ( Ben nSürüm o f C ontrol): - O genel bir terimdir ve birkaç şekilde (etkinlikler, delegeler vs.) uygulanan bu.

DI ( D ependency I njection) - DI IOC bir alt türü olup tarafından uygulanan yapıcı enjeksiyon, ayarlayıcı enjeksiyon veya Arayüz enjeksiyon .

Ancak, Spring yalnızca aşağıdaki iki türü destekler:

  • Setter Enjeksiyonu
    • Setter tabanlı DI, fasulyesini somutlaştırmak için argüman oluşturucu olmayan veya argüman içermeyen statik fabrika yöntemini çağırdıktan sonra kullanıcının fasulyeleri üzerinde setter yöntemleri çağrılarak gerçekleştirilir.
  • Yapıcı Enjeksiyonu
    • Yapıcı tabanlı DI, her biri bir işbirlikçiyi temsil eden bir dizi argümana sahip bir yapıcıyı çağırarak gerçekleştirilir. uygulama başlarken biz olsun NullPointerException: bean does not exist. Yapıcı enjeksiyonu bağımlılıkları enjekte etmek için en iyi uygulamadır.

1
Spring'in mülk enjeksiyonunu desteklemediğini belirtmek doğru değildir. Öyle. Ve bu kötü bir uygulama, katılıyorum.
kekko12

Bahar @Autowired açıklama Bence mülkiyet enjeksiyon yoludur
Sajith

49

DI, IoC'nin bir alt kümesidir

  • IoC , nesnelerin işlerini yapmak için güvendikleri başka nesneler oluşturmadığı anlamına gelir. Bunun yerine, ihtiyaç duydukları nesneleri bir dış hizmetten (örneğin, xml dosyası veya tek uygulama hizmeti) alırlar. Kullandığım 2 IoC uygulaması DI ve ServiceLocator.
  • DI , IoC'nin bağımlı nesneyi elde etme prensibinin somut nesneler değil soyutlamalar (arayüzler) kullanılmadan yapıldığı anlamına gelir. Bu, tüm bileşenleri zincir test edilebilir hale getirir, çünkü daha yüksek seviye bileşen daha düşük seviye bileşene bağlı değildir, sadece arayüzden. Alaycılar bu arayüzleri uygularlar.

İşte IoC'ye ulaşmak için başka teknikler .


IoC'nin nesne yaratmamak anlamına geldiğini söylemem. Sınıf yöntemini doğrudan değil, arabirim yöntemini çağırdığınızda - bu denetimin ters çevrilmesidir (bu durumda arayanın arama koduna bağlı olmadığı gibi) ve nesne oluşturma ile hiç ilgili değildir.
IoC'ye bir

19

Tüm cevaplar teoriyi vurguladığından, örnek bir ilk yaklaşımla göstermek istiyorum:

Sipariş gönderildikten sonra SMS onay mesajları gönderme özelliği içeren bir uygulama oluşturduğumuzu varsayalım. İki sınıfımız olacak, biri SMS (SMSService) göndermekten sorumlu, diğeri kullanıcı girişlerini (UIHandler) yakalamaktan sorumlu, kodumuz aşağıdaki gibi görünecek:

public class SMSService
{
    public void SendSMS(string mobileNumber, string body)
    {
        SendSMSUsingGateway(mobileNumber, body);
    }

    private void SendSMSUsingGateway(string mobileNumber, string body)
    {
        /*implementation for sending SMS using gateway*/
    }
}

public class UIHandler
{
    public void SendConfirmationMsg(string mobileNumber)
    {
        SMSService _SMSService = new SMSService();
        _SMSService.SendSMS(mobileNumber, "Your order has been shipped successfully!");
    }
}

Yukarıdaki uygulama yanlış değildir, ancak birkaç sorun vardır:
-) Varsayalım Geliştirme ortamında, bunu başarmak için SMS ağ geçidi kullanmak yerine bir metin dosyasına gönderilen SMS'leri kaydetmek istiyorsunuz; (SMSService) 'in somut uygulamasını başka bir uygulamayla değiştireceğiz, esnekliği kaybediyoruz ve bu durumda kodu yeniden yazmak zorunda kalıyoruz.
-) Sınıfların sorumluluklarını karıştıracağız, (UIHandler) (SMSService) 'in somut uygulaması hakkında hiçbir zaman bilgi sahibi olmamalı, bu “Arayüzler” kullanan sınıfların dışında yapılmalıdır. Bu uygulandığında, aynı arabirimi uygulayan başka bir sahte hizmetle kullanılan (SMSService) değiştirerek sistemin davranışını değiştirme yeteneğini verecektir, bu hizmet SMS'leri mobileNumber'a göndermek yerine bir metin dosyasına kaydedecektir.

Yukarıdaki sorunları düzeltmek için (SMSService) ve yeni (MockSMSService) tarafından uygulanacak Arayüzler kullanıyoruz, temel olarak yeni Arayüz (ISMSService) her iki hizmetin de aşağıdaki kodlarla aynı davranışlarını ortaya koyacaktır:

public interface ISMSService
{
    void SendSMS(string phoneNumber, string body);
}

Ardından (SMSService) uygulamamızı (ISMSService) arayüzünü uygulamak için değiştireceğiz:

public class SMSService : ISMSService
{
    public void SendSMS(string mobileNumber, string body)
    {
        SendSMSUsingGateway(mobileNumber, body);
    }

    private void SendSMSUsingGateway(string mobileNumber, string body)
    {
        /*implementation for sending SMS using gateway*/
        Console.WriteLine("Sending SMS using gateway to mobile: 
        {0}. SMS body: {1}", mobileNumber, body);
    }
}

Şimdi, aynı arayüzü kullanarak tamamen farklı bir uygulama ile yeni mock up hizmeti (MockSMSService) oluşturabileceğiz:

public class MockSMSService :ISMSService
{
    public void SendSMS(string phoneNumber, string body)
    {
        SaveSMSToFile(phoneNumber,body);
    }

    private void SaveSMSToFile(string mobileNumber, string body)
    {
        /*implementation for saving SMS to a file*/
        Console.WriteLine("Mocking SMS using file to mobile: 
        {0}. SMS body: {1}", mobileNumber, body);
    }
}

Bu noktada, hizmetin somut uygulamasını (MockSMSService) kullanmak için (UIHandler) içindeki kodu aşağıdaki gibi kolayca değiştirebiliriz:

public class UIHandler
{
    public void SendConfirmationMsg(string mobileNumber)
    {
        ISMSService _SMSService = new MockSMSService();
        _SMSService.SendSMS(mobileNumber, "Your order has been shipped successfully!");
    }
}

Çok fazla esneklik sağladık ve kodumuzdaki endişelerin ayrılmasını sağladık, ancak yine de iki SMS Hizmeti arasında geçiş yapmak için kod tabanında bir değişiklik yapmamız gerekiyor. Bu yüzden Bağımlılık Enjeksiyonu uygulamamız gerekiyor .

Bunu başarmak için, (UIHandler) sınıf yapıcımızda bağımlılığı içinden geçirmek için bir değişiklik uygulamamız gerekir, bunu yaparak (UIHandler) kullanan kod (ISMSService) 'in hangi somut uygulamasını kullanacağını belirleyebilir:

public class UIHandler
{
    private readonly ISMSService _SMSService;

    public UIHandler(ISMSService SMSService)
    {
        _SMSService = SMSService;
    }

    public void SendConfirmationMsg(string mobileNumber)
    {
        _SMSService.SendSMS(mobileNumber, "Your order has been shipped successfully!");
    }
}

Artık sınıfla (UIHandler) konuşacak olan UI formu, hangi arabirim uygulamasının (ISMSService) tüketileceğini iletmekten sorumludur. Bu, kontrolü tersine çevirdiğimiz anlamına gelir, (UIHandler) artık hangi uygulamanın kullanılacağına karar vermekten sorumlu değildir, arama kodu yapar. DI'nin bir türü olduğu Kontrolün Tersinmesi prensibini uyguladık .

UI form kodu aşağıdaki gibi olacaktır:

class Program
{
    static void Main(string[] args)
    {
        ISMSService _SMSService = new MockSMSService(); // dependency

        UIHandler _UIHandler = new UIHandler(_SMSService);
        _UIHandler.SendConfirmationMsg("96279544480");

        Console.ReadLine();
    }
}

Great
description

19

IOC (Kontrolün Ters Çevrilmesi) : Nesnenin bir örneğini almak için konteynere kontrol vermek Denetimi Ters Çevirme olarak adlandırılır, bunun yerine yeni operatörü kullanarak bir nesne oluşturduğunuz anlamına gelir, konteynerin bunu sizin için yapmasına izin verin.

DI (Bağımlılık Enjeksiyonu) : Bir nesneye özellik enjekte etme yoluna Bağımlılık Enjeksiyonu denir .

Üç tip Bağımlılık Enjeksiyonumuz var :

  1. Yapıcı Enjeksiyonu
  2. Setter / Getter Enjeksiyonu
  3. Arayüz Enjeksiyonu

Yay sadece Yapıcı Enjeksiyonu ve Setter / Getter Enjeksiyonunu destekler .


5

Ancak bahar belgeleri aynı olduklarını söylüyor.

http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#beans-introduction

İlk satırda " IoC, bağımlılık enjeksiyonu (DI) olarak da bilinir ".


1
Sanırım ele almaya çalıştıkları şey, DIC'nin, IoC tasarım modelinin çok kolay kullanılan bir lezzeti olması ve belgelerin aksini gösteren herhangi bir açık referansı olmadıkça neredeyse IoC aka DI olarak adlandırılabileceğidir.
ha9u63ar

5
"IoC aynı zamanda bağımlılık enjeksiyonu (DI)" olarak da bilinir.
MikeM

5

IoC - Kontrolün ters çevrilmesi , dilden bağımsız olarak genel bir terimdir, aslında nesneleri yaratmaz, hangi moda nesnesinin yaratıldığını tanımlar.

DI - Bağımlılık Enjeksiyonu, farklı enjeksiyon teknikleri kullanılarak nesnenin çalışma zamanında bağımlılıklarını sağladığımız somut bir terimdir. Setter Enjeksiyonu, Yapıcı Enjeksiyonu veya Arayüz Enjeksiyonu ile.


4

Kontrolün ters çevrilmesi, uygulamanızın hedeflenen bileşenlerine, işi yapanlara daha fazla kontrol sağlamak amacıyla bir tasarım paradigmasıdır.
Bağımlılık enjeksiyonu, derleme zamanında hangi işlevselliğin sağlanması için hangi sınıfın kullanılacağını bilmeden diğer nesnelerin güvendiği nesnelerin örneklerini oluşturmak için kullanılan bir modeldir.

Kontrolün ters çevrilmesini uygulamak için birkaç temel teknik vardır. Bunlar:

  • Fabrika kalıbı kullanma
  • Bir servis bulucu kalıbı kullanma
  • Aşağıdaki tipte herhangi bir bağımlılık enjeksiyonunun kullanılması:

    1). Bir yapıcı enjeksiyonu
    2). Bir ayarlayıcı enjeksiyonu
    3). Bir arayüz enjeksiyonu

4

DI ve IOC , temel olarak bileşenler arasında gevşek kuplaj sağlamaya odaklanan veya nesneler arasındaki konvansiyonel bağımlılık ilişkilerini, nesnelerin birbirine sıkı olmaması için ayırdığımız bir yol olan iki tasarım modelidir .

Aşağıdaki örneklerle, her iki kavramı da açıklamaya çalışıyorum.

Daha önce böyle bir kod yazıyoruz

Public MyClass{
 DependentClass dependentObject
 /*
  At somewhere in our code we need to instantiate 
  the object with new operator  inorder to use it or perform some method.
  */ 
  dependentObject= new DependentClass();
  dependentObject.someMethod();
}

Bağımlılık enjeksiyonu ile, bağımlılık enjektörü nesnelerin somutlaştırılmasına dikkat edecektir.

Public MyClass{
 /* Dependency injector will instantiate object*/
 DependentClass dependentObject

 /*
  At somewhere in our code we perform some method. 
  The process of  instantiation will be handled by the dependency injector
 */ 

  dependentObject.someMethod();
}

Başlatma ve enjeksiyon için kontrolü başka bir kişiye (örneğin konteynere) verme işlemi, Konversiyon Kontrolü olarak adlandırılabilir ve IOC konteynerinin bizim için bağımlılığı enjekte etme işlemi, bağımlılık enjeksiyonu olarak adlandırılabilir.

IOC, bir programın kontrol akışının ters çevrildiği ilkedir: bir programın akışını kontrol eden programcı yerine , program yükü programcıya azaltarak akışı kontrol eder. Ve program tarafından bağımlılığı enjekte etmek için kullanılan işlem şu şekilde adlandırılır: DI

İki kavram birlikte çalışarak bize çok daha esnek, yeniden kullanılabilir ve kapsüllenmiş kod yazmanın bir yolunu sunarak onları nesne yönelimli çözümler tasarlarken önemli kavramlar haline getirir.

Ayrıca okumak için tavsiye.

Bağımlılık enjeksiyonu nedir?

Benzer cevabımdan birini buradan da kontrol edebilirsiniz

Kontrolün İnversiyonu ile Bağımlılık Enjeksiyonu Arasındaki Fark


3

Inversion of Control, bakımı kolay yeniden kullanılabilir, modüler yazılım çerçeveleri oluşturmaya yardımcı olan yazılım mimarisinin genel bir tasarım ilkesidir.

Kontrol Akışının genel olarak yazılmış kitaplıktan veya yeniden kullanılabilir koddan "alındığı" bir tasarım ilkesidir.

Daha iyi anlamak için kodlamanın önceki günlerinde nasıl kod yazdığımızı görelim. Prosedürel / geleneksel dillerde, iş mantığı genellikle uygulamanın akışını kontrol eder ve genel veya yeniden kullanılabilir kodu / fonksiyonları "Aratır". Örneğin, basit bir Konsol uygulamasında, kontrol akışım, programın genel yeniden kullanılabilir işlevlere yapılan çağrıları içerebilen talimatları tarafından kontrol edilir.

print ("Please enter your name:");
scan (&name);
print ("Please enter your DOB:");
scan (&dob);

//More print and scan statements
<Do Something Interesting>

//Call a Library function to find the age (common code)
print Age

Buna karşılık, IoC ile, Çerçeveler iş mantığını "Çağıran" yeniden kullanılabilir koddur.

Örneğin, Windows tabanlı bir sistemde, düğmeler, menüler, pencereler ve iletişim kutuları gibi UI öğeleri oluşturmak için bir çerçeve zaten mevcut olacaktır. Uygulamamın iş mantığını yazdığımda, iş mantığı kodumu (bir olay tetiklendiğinde) çağıracak ve bunun tersi değil, çerçevenin olayları olurdu.

Çerçevenin kodu iş mantığımın farkında olmasa da, yine de kodumu nasıl arayacağımı bilecek. Bu, olaylar / delegeler, geri aramalar vb. Kullanılarak gerçekleştirilir. Burada Akış Kontrolü "Tersine çevrilir".

Dolayısıyla, kontrol akışını statik olarak bağlı nesneler yerine, genel nesne grafiğine ve farklı nesneler arasındaki ilişkilere bağlıdır.

Bağımlılık Enjeksiyonu, nesnelerin bağımlılıklarını çözmek için IoC prensibini uygulayan bir tasarım modelidir.

Daha basit bir deyişle, kod yazmaya çalıştığınızda, farklı sınıflar oluşturacak ve kullanacaksınız. Bir sınıf (Sınıf A) diğer sınıfları (Sınıf B ve / veya D) kullanabilir. Yani, B ve D Sınıfları A sınıfının bağımlılıklarıdır.

Basit bir benzetme bir sınıf Araba olacaktır. Bir araba, Motor, Lastikler ve diğer sınıflara bağlı olabilir.

Bağımlılık Enjeksiyonu, bağımlılıklarını (Sınıf Motoru ve sınıf Lastiği) oluşturmak için Bağımlı sınıflar (burada Sınıf Arabası) yerine, sınıfın bağımlılığın somut örneği ile enjekte edilmesi gerektiğini önermektedir.

Daha pratik bir örnekle anlayalım. Kendi TextEditor'unuzu yazdığınızı düşünün. Diğer şeylerin yanı sıra, kullanıcıya metnindeki yazım hatalarını kontrol etme olanağı sağlayan bir yazım denetleyicisine sahip olabilirsiniz. Böyle bir kodun basit bir uygulaması şunlar olabilir:

Class TextEditor
{

    //Lot of rocket science to create the Editor goes here

    EnglishSpellChecker objSpellCheck;
    String text;

    public void TextEditor()

    {   

        objSpellCheck = new EnglishSpellChecker();

    }

    public ArrayList <typos> CheckSpellings()
    {

        //return Typos;

    }

}

İlk bakışta, hepsi pembe görünüyor. Kullanıcı bir metin yazacaktır. Geliştirici metni yakalar ve CheckSpellings işlevini çağırır ve Kullanıcıya göstereceği Yazım hatalarının bir listesini bulur.

Bir kullanıcının Editör'de Fransızca yazmaya başladığı güzel bir güne kadar her şey harika çalışıyor gibi görünüyor.

Daha fazla dil için destek sağlamak için daha fazla Yazım Denetleyici'ye ihtiyacımız var. Muhtemelen Fransız, Alman, İspanyol vb.

Burada, "English" SpellChecker ile TextEditor sınıfımıza sıkı sıkıya bağlı bir kod oluşturduk; bu da TextEditor sınıfımızın EnglishSpellChecker'a veya başka bir deyişle EnglishSpellCheker'ın TextEditor'a bağımlı olduğu anlamına gelir. Bu bağımlılığı ortadan kaldırmalıyız. Ayrıca, Metin Düzenleyicimiz, geliştiricinin çalışma zamanında takdirine bağlı olarak herhangi bir Yazım Denetleyicisinin somut referansını tutmanın bir yoluna ihtiyaç duyar.

Bu nedenle, DI'nin girişinde gördüğümüz gibi, sınıfın bağımlılıklarına enjekte edilmesi gerektiğini düşündürmektedir. Bu nedenle, çağrılan sınıfa / koda bağımlılıkları enjekte etmek çağrı kodunun sorumluluğunda olmalıdır. Böylece kodumuzu

interface ISpellChecker
{

    Arraylist<typos> CheckSpelling(string Text);

}

Class EnglishSpellChecker : ISpellChecker

{

    public override Arraylist<typos> CheckSpelling(string Text)

    {

        //All Magic goes here.

    }

}



Class FrenchSpellChecker : ISpellChecker

{

    public override Arraylist<typos> CheckSpelling(string Text)

    {

        //All Magic goes here.

    }

}

Örneğimizde, TextEditor sınıfı ISpellChecker türünün somut örneğini almalıdır.

Şimdi, bağımlılık Yapıcı, Kamusal Mülk veya yöntemle enjekte edilebilir.

Yapıcı DI kullanarak sınıfımızı değiştirmeye çalışalım. Değiştirilen TextEditor sınıfı şuna benzer:

Class TextEditor

{

    ISpellChecker objSpellChecker;

    string Text;



    public void TextEditor(ISpellChecker objSC)

    {

        objSpellChecker = objSC;

    }



    public ArrayList <typos> CheckSpellings()

    {

        return objSpellChecker.CheckSpelling();

    }

}

Böylece arama kodu, metin düzenleyiciyi oluştururken TextEditor örneğine uygun SpellChecker Türünü enjekte edebilir.

Sen tam makalemizi okuyabilirsiniz burada


3

IOC (Kontrolün Ters Çevrilmesi): Nesnenin örneğini almak için konteynere kontrol vermek Kontrolün Ters Çevrilmesi olarak adlandırılır. Bu, yeni işleç kullanarak nesne oluşturmak yerine , kapsayıcıyı sizin için yapsın.

DI (Bağımlılık Enjeksiyonu): Gerekli parametrelerin (özelliklerin) XML'den bir nesneye (POJO CLASS'ta) geçirilmesine Bağımlılık enjeksiyonu denir.


2

IOC , bir uygulamanın sınıflarını yöneten harici sınıfların ve harici sınıfların, bir kapsayıcı, uygulama sınıfı arasındaki bağımlılığı yönettiği anlamına gelir. IOC'nin temel konsepti, programcının nesnelerinizi oluşturmasına gerek olmaması, nasıl yaratılması gerektiğini tanımlamasıdır.

IoC kapsayıcısı tarafından gerçekleştirilen ana görevler şunlardır: uygulama sınıfını örneklemek. nesneyi yapılandırmak için. nesneler arasındaki bağımlılıkları birleştirmek.

DI , ayarlayıcı enjeksiyonu veya yapıcı enjeksiyonu kullanılarak bir nesnenin çalışma zamanında bağımlılıklarını sağlama işlemidir.


2

IOC (Kontrolün Ters Çevirilmesi) temel olarak bağımlılıkları ortadan kaldırmak ve akışları doğrusal olmayan hale getirmek için ayırmaktır ve konteynerin / veya başka bir varlığın bağımlılıkların sağlanmasını yönetmesine izin verir. Aslında Hollywood'un “Bizi arama, sizi arayacağız” prensibini takip ediyor. Farklılıkları özetleyelim.

Kontrolün ters çevrilmesi: - Bağımlılıkları birbirinden ayırmak ve provizyonlarını devretmek için kullanılan genel bir terimdir ve bu birkaç şekilde uygulanabilir (etkinlikler, delegeler vb.).

Bağımlılık enjeksiyonu: - DI, IOC'nin bir alt türüdür ve yapıcı enjeksiyonu, ayarlayıcı enjeksiyonu veya yöntem enjeksiyonu ile uygulanır.

Aşağıdaki makale bunu çok düzgün bir şekilde açıklamaktadır.

https://www.codeproject.com/Articles/592372/Dependency-Injection-DI-vs-Inversion-of-Control-IO


1

Bence fikir, fikri karıştırıyor gibi görünen Nesne Odaklı yabani otlara girmeden açıkça gösterilebilir.

// dependency injection
function doSomething(dependency) {
    // do something with your dependency
}

// in contrast to creating your dependencies yourself
function doSomething() {
    dependency = getDependencySomehow()
}

// inversion of control
application = makeApp(authenticate, handleRequest, sendResponse)
application.run(getRequest())

// in contrast to direct control or a "library" style
application = makeApp()
request = application.getRequest()

if (application.authenticate(request.creds)) {
    response = application.handleRequest(request)
    application.sendResponse(response)
}

Başınızı eğerek ve gözlerinizi kısarsanız, DI'nin IoC'nin belirli endişeleri olan özel bir uygulaması olduğunu göreceksiniz. Modelleri ve davranışları bir uygulama çerçevesine veya daha üst düzey bir işleme enjekte etmek yerine, bir işleve veya nesneye değişkenler enjekte edersiniz.


0

SOLID'den D ile başlayalım ve Scott Millett'in "Profesyonel ASP.NET Tasarım Desenleri" kitabından DI ve IoC'ye bakalım:

Bağımlılık Ters Çevirme İlkesi (DIP)

DIP beton uygulamalarından sizin sınıfları izole ve onları soyut sınıflar veya arayüzler bağlıdır sahip ilgili. Bir uygulamadan ziyade bir arayüze kodlama mantrasını teşvik eder, bu da bir uygulamaya sıkıca bağlı olmadığınızdan emin olarak sistem içindeki esnekliği artırır.

Bağımlılık Enjeksiyonu (DI) ve Kontrolün İnversiyonu (IoC)

DIP ile yakından bağlantılı olan DI prensibi ve IoC prensibidir. DI , bir yapıcı, yöntem veya özellik aracılığıyla düşük seviyeli veya bağımlı bir sınıf sağlama eylemidir. DI ile birlikte kullanıldığında, bu bağımlı sınıflar, son derece test edilebilir ve değiştirilmesi kolay gevşek bağlı sistemlere yol açacak arabirimlere veya soyut sınıflara dönüştürülebilir.

In IoC , kontrol sistemin akış prosedürel programlama kıyasla tersine çevrilir. Bunun bir örneği , somut uygulamayı belirten müşteri koduna sahip olmadan hizmetleri müşteri koduna enjekte etmek olan bir IoC kapsayıcısıdır . Bu durumda ters çevrilen denetim, hizmeti alan istemcinin eylemidir.

Millett, C (2010). Profesyonel ASP.NET Tasarım Desenleri. Wiley Yayıncılık. 7-8.


0

// ICO, DI, 10 yıl önce, bu şekilde oldu:

public class  AuditDAOImpl implements Audit{

    //dependency
    AuditDAO auditDAO = null;
        //Control of the AuditDAO is with AuditDAOImpl because its creating the object
    public AuditDAOImpl () {
        this.auditDAO = new AuditDAO ();
    }
}

Şimdi Bahar 3,4 veya en son aşağıdaki gibi

public class  AuditDAOImpl implements Audit{

    //dependency

     //Now control is shifted to Spring. Container find the object and provide it. 
    @Autowired
    AuditDAO auditDAO = null;

}

Genel olarak kontrol, eski birleştirilmiş kod kavramından, Spring gibi nesneyi kullanılabilir kılan çerçevelere dönüştürülür. Bu, bildiğim kadarıyla IOC ve Bağımlı nesneyi Yapıcı veya ayarlayıcılar kullanarak başka bir nesneye enjekte ettiğimizde bildiğiniz gibi Bağımlılık enjeksiyonu. Enjekte etmek, onu bir argüman olarak geçirmek anlamına gelir. İlkbaharda, fasulye nesnesini tanımladığımız ve bağımlı nesneyi Oluşturucu veya ayarlayıcı enjeksiyon stiliyle geçirdiğimiz XML ve ek açıklama tabanlı yapılandırmaya sahibiz.


0

Dzone.com'da IOC ve DI arasındaki gerçek farklılığı anlamaya gerçekten yardımcı olan en iyi örneği buldum

“IoC, sizin için başka nesneler yarattığınız zamandır.” Bu nedenle, kodunuza "yeni" anahtar kelime (Örneğin, MyCode c = new MyCode ()) yazmak yerine, nesne başka biri tarafından oluşturulur. Bu 'başkası' normalde IoC konteyneri olarak adlandırılır. Bu, nesnenin örneğini almak için kontrole rsponsibility'yi (kontrole devredeceğimiz anlamına gelir. Inversion of Control.), Yeni bir operatör kullanarak nesne oluşturmak yerine konteynerin bunu sizin için yapmasına izin verin.

   DI(Dependency Injection):  Way of injecting properties to an object is 
   called 
  Dependency injection.
   We have three types of Dependency injection
    1)  Constructor Injection
    2)  Setter/Getter Injection
    3)  Interface Injection
   Spring will support only Constructor Injection and Setter/Getter Injection.

Makalenin tamamını oku IOC ve Makaleyi oku DI


0

1) DI Child-> obj ebeveyn-obj'e bağlıdır. Fiil bağlıdır önemlidir. 2) IOC bir platform altında Child-> obj icradır. platform okul, kolej, dans dersi olabilir. Burada gerçekleştirme, herhangi bir platform sağlayıcısı altında farklı imalara sahip bir etkinliktir.

pratik örnek:

//DI
child.getSchool();
//IOC
child.perform()// is a stub implemented by dance-school
child.flourish()// is a stub implemented by dance-school/school/

'

-AB


0

Bu soruya gelince, wiki'nin ayrıntılı ve kolay anlaşılır açıklamalar sağladığını söyleyebilirim. Burada en önemlilerini alıntılayacağım.

IoC Uygulaması

Nesne yönelimli programlamada, kontrolün ters çevrilmesini uygulamak için birkaç temel teknik vardır. Bunlar:

  1. Bir servis bulucu deseninin kullanılması Bağımlılık enjeksiyonunun kullanılması, örneğin Yapıcı enjeksiyonu Parametre enjeksiyonu Setter enjeksiyonu Arayüz enjeksiyonu;
  2. Bağlamsallaştırılmış bir arama kullanma;
  3. Şablon yöntem tasarım desenini kullanarak;
  4. Strateji tasarım modelini kullanma

Gelince Dependency Injection

bağımlılık enjeksiyonu, bir nesnenin (veya statik yöntemin) başka bir nesnenin bağımlılıklarını sağladığı bir tekniktir. Bağımlılık kullanılabilecek bir nesnedir (bir hizmet). Enjeksiyon, bağımlılığın, onu kullanacak bağımlı bir nesneye (bir istemciye) geçmesidir.


0

IoC kavramı başlangıçta prosedürel programlama döneminde duyuldu. Bu nedenle, tarihsel bir bağlamdan IoC , kontrol akışının sahipliğinin tersine çevrilmesi hakkında konuştu; yani, işlevleri ister istedikleri sırayla çağırmakla yükümlüdür - işlevlerin kendileri olsun ya da bir dış varlığa çevirmeniz gerekip gerekmediği.

Ancak OOP ortaya çıktığında, insanlar OOP bağlamında IoC hakkında, uygulamaların kontrol akışı dışında nesnelerin oluşturulması ve ilişkileri ile ilgili olduğu yerlerde konuşmaya başladılar. Bu tür uygulamalar , nesne oluşturma (kontrol akışı yerine) sahipliğini tersine çevirmek istedi ve uygulama nesnelerinin nesne oluşturma, nesne yaşam döngüsü ve enjekte etme bağımlılıklarından sorumlu olan ve böylece uygulama nesnelerinin diğer somut nesneler oluşturmasını önleyen bir kap gerektiriyordu.

Bu anlamda DI, Io C ile aynı değildir , çünkü kontrol akışı ile ilgili değildir, ancak bir tür Io * , yani nesne yaratma sahipliğinin tersine çevrilmesi.

DI ve IoC'yi açıklama şeklimde yanlış olan ne?


0

IoC, yani Kontrolün Tersine Çevirilmesi, Spring konteyneri tarafından yapılan örnekleri oluşturma kontrolünü ifade eder. Nesneleri oluşturma ve oluşturma kontrolü konteynır tarafından halledilir. Kap, nesneleri oluşturur ve bunları uygulamamıza enjekte eder.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.