Öncelikle, ben sadece web geliştirme için bu soruyu sınırlamak istiyor. Yani bu dil, web geliştirme için kullanılan ediliyor sürece agnostik dilidir. Şahsen, ben PHP bir arka plan bu da geliyorum.
Çoğu zaman birden fazla kapsamları bir nesne kullanmanız gerekir. Örneğin, bir kontrolör sınıftan da daha sonra normal kapsamı bir veritabanı sınıfını kullanabilirsiniz ama gerekebilir. Biz, normal kapsamında bir veritabanı nesnesi oluşturmak Eğer biz denetleyici sınıf içinde onu erişemez. Biz farklı kapsamlarda iki veritabanı nesneleri oluşturma önlemek isteyen ve bu yüzden ne olursa olsun kapsam veritabanı sınıfını yeniden bir yol gerekir. Bunu yapmak için, biz iki seçeneğiniz var:
- Her yerden erişilebilir, böylece veritabanı nesne küresel olun.
- Örneğin, şeklinde kontrolör sınıfa denetleyicisinin kurucusuna bir parametre veritabanı sınıfını geçmek. Bu bağımlılık, enjeksiyon (Di) olarak da bilinir.
Sorun birçok farklı kapsamlarda talep eden tüm nesneleri dahil birçok sınıfları vardır daha karmaşık hale gelir. Her iki çözümlerinde küresel bizim nesnelerin her birini yaparsanız, biz küresel kapsam içine çok fazla gürültü koyarak, çünkü bu sorunlu olur ve biz bir sınıfa çok fazla parametre geçmesi halinde, sınıf çok daha zor yönetmek olur.
Bu nedenle, her iki durumda da, sık sık bir kayıt kullanımını görüyoruz. Küresel durumda, küresel yapılmış ve o herhangi bir nesne onları kullanılabilir hale ancak küresel kapsam içine tek bir değişken, kayıt koyarak bizim nesneleri ve tüm değişkenler eklemek bir kayıt nesnesi var. DI durumda, parametre sayısını 1 azaltarak her sınıfa kayıt nesnesini iletin.
Şahsen, ben çünkü küresellerle kullanarak üzerinde onu savunan birçok makale ikinci bir yaklaşım kullanın ama iki sorunla karşılaşmadım. Öncelikle, kayıt defteri sınıf özyineleme büyük miktarlarda içerir. Örneğin, kayıt defteri sınıf veritabanı sınıfının ihtiyaç duyduğu veritabanı oturum değişkenleri içerir. Bu nedenle, veritabanına kayıt sınıfını enjekte gerekir. Ancak, veritabanı birçok diğer sınıflar tarafından ihtiyaç duyulacak ve böylece veritabanı kayıt defterine eklenecek gerekir, bir döngü yarattı. Modern diller, bu tamam işlemek veya bu neden büyük bir performans sorunları olduğunu miyim? O şey içine geçmedi gibi küresel kayıt bu muzdarip değil dikkat edin.
İkincisi, ona ihtiyacım yok nesnelere büyük miktarda veri geçen başlayacaktır. Benim veritabanı benim yönlendirici önemsemiyor ama yönlendirici veritabanı bağlantısı detayları ile birlikte veritabanına aktarılabilir alacak. Yönlendirici kayıt varsa, bu kayıt defteri veritabanı ve kayıt defteri vardır ve kayıt (yani I {yapabileceğini veritabanı, daha sonra veritabanı yönlendirici üzerinden kendisine geçirilen elde ettiğini geçirilen çünkü bu özyineleme sorunu üzerinden kötü yapılır [(0)]} veritabanı sınıfının içinden `).
Ayrıca, ben DI fazla karmaşıklık dışında bana veriyor ne görmüyorum. Ben her nesnenin içine ekstra bir değişken geçmek zorunda ve ben $this->registry->object->method()
yerine $registry->object->method()
ile kayıt nesneleri kullanmak zorunda. Şimdi bu tabii ki büyük bir sorun değil ama bana küresel yaklaşım üzerinde hiçbir şey vermeyeceğim eğer gereksiz görünüyor.
Ben bir kayıt olmadan DI kullanabilirsiniz ama sonra parametreleri saçma numarası ile sınıf Kurucular sonuçlanan, 'elle' her nesneyi geçmek zorunda Açıkçası, bu sorunlar yoktur.
DI iki sürümleri ile bu sorunlar göz önüne alındığında, küresel kayıt üstün değil mi? Ben DI üzerinden küresel bir kayıt defterini kullanarak ne kaybediyorum?
Globals vs DI tartışırken sık sık söz edilir bir şey globallerinin düzgün programı test etmek yeteneğini inhibe olmasıdır. Tam olarak nasıl globallerinin beni DI olmaz bir programı test engelleyebilir mi? Bu küresel bir yerden değiştirilebilir olmasından dolayı olduğu birçok yerde okumak ve böylece dalga zordur var. Ancak, aynı zamanda enjekte edildiği içine başka bir sınıf içinde değişecek bazı sınıfta bir enjekte nesneyi değiştirerek bu yana, en azından PHP, nesnelerine başvuru tarafından geçirilir gibi geliyor bana.