Загрузка...
скачать
Реферат на тему:

Внедрение зависимости



План:

    Введение
  • 1 Примеры кода
  • 2 Существующие фреймворки
  • 3 Внешние ссылки

Введение

Внедрение зависимости (англ. Dependency injection) обозначает процесс предоставления внешней зависимости программному компоненту и является специфичной формой «обращения контроля (англ. Inversion of control)», где изменение порядка связи является путём получения необходимой зависимости.

Условно, если объекту нужно получить доступ к определенному сервису, объект берет на себя ответственность за доступ к этому сервису: он или получает прямую ссылку на местонахождение сервиса, или обращается к известному «сервис-локатору» и запрашивает ссылку на реализацию определенного типа сервиса. Используя же внедрение зависимости, объект просто предоставляет свойство, которое в состоянии хранить ссылку на нужный тип сервиса; и когда объект создается, ссылка на реализацию нужного типа сервиса автоматически вставляется в это свойство (поле), используя средства среды. Внедрение зависимости более гибко, потому как становится легче создавать альтернативные реализации данного типа сервиса, а потом указывать, какая именно реализация должна быть использована в, например, конфигурационном файле, без изменений в объектах, которые этот сервис используют. Это особенно полезно в юнит-тестировании, потому как вставить реализацию «заглушки» сервиса в тестируемый объект очень просто. С другой стороны, излишнее использование внедрения зависимостей может сделать приложения более сложными и трудными в сопровождении: так как для понимания поведения программы программисту необходимо смотреть не только в исходный код, а еще и в конфигурацию, а конфигурация, как правило, невидима для IDE, которые поддерживают анализ ссылок и рефакторинг, если явно не указана поддержка фреймворков с внедрениями зависимостей.


1. Примеры кода

Представим, что IFoo это общий класс, определяющий свой интерфейс:

  class IFoo(Interface):
        def do_bar(self):
            "perform bar"
        def do_baz(self):
            "perform baz"

Также есть несколько реализаций, которые реализуют IFoo по-разному:

  class DatabaseFoo(object):
        interface.implements(IFoo)
        def do_bar(self):
            db.select_bar().execute() # Использовать базу данных, чтобы сделать bar
        def do_baz(self):
            db.select_baz().run() # Использовать базу данных, чтобы сделать baz
 
  class PixieDustFoo(object):
        interface.implements(IFoo)
        def do_bar(self):
            cast_spell("bar") # Магия...
        def do_baz(self):
            cast_spell("baz") # ...и волшебство
 
  class EnterpriseFoo(object):
        interface.implements(IFoo)
        def do_bar(self):
            bar = EnterpriseFactoryObserverFactoryCreator("bar")
            bar.creatify()
            bar.preparify()
            bar.configurise()
            bar.make_award_winning()
            bar.opportunities.leverage()
        def do_baz(self):
            baz = EnterpriseFactoryObserverFactoryCreator("baz")
            baz.creatify()
            baz.preparify()
            baz.configurise()
            baz.make_award_winning()
            baz.opportunities.leverage()

IFoo определяет только операции, которые доступны в интерфейсе, но не предоставляет никакой их реализации, позволяя другим классам реализовывать методы, в нем определенные (на то он и интерфейс). Поэтому пользователь, желающий использовать функционал IFoo, может использовать любую реализацию, не имея никакого понятия о том, как оно работает, кроме того, что они соответствуют спецификации интерфейса Foo.

  class ImportantClass(object):
        def __init__(self):
            self.foo = EnterpriseFoo()
        def do_really_important_stuff(self):
            self.foo.do_bar() # оно ничего не делает!

Хотя, это подрывает весь смысл использования интерфейсов вместо конечных реализаций. Чтобы исправить ситуацию, достаточно предоставить вызывающей стороне возможность указывать ту реализацию IFoo, которую она посчитает нужным:

        def __init__(self, foo):
            self.foo = foo

При использовании внедрения зависимостей, как правило, существует конфигурационный механизм или архитектура, которая определяет целесообразность выбора той или иной реализации в зависимости от поставленных целей.


2. Существующие фреймворки

Реализация внедрения зависимостей существует для различных платформ и языков, включая:

ActionScript

  • di-as3
  • Parsley
  • Prana Framework
  • Syringe
  • Swiz
  • SpringActionscript

C++

  • Autumn Framework
  • PocoCapsule/C++ IoC and DSM Framework
  • QtIocContainer

ColdFusion

  • ColdSpring Framework

Java

  • Butterfly Container
  • iPOJO
  • Google Guice
  • HiveMind
  • JBoss Microcontainer
  • PicoContainer
  • Openxava
  • Seasar
  • Spring Framework
  • J2EE 5 / EJB 3
  • Naked objects
  • miocc — Microscopic Inversion of Control Container

.NET

  • Autofac
  • Castle MicroKernel/Windsor
  • ObjectBuilder
  • PicoContainer.NET
  • Puzzle.NFactory
  • Spring.NET
  • StructureMap
  • Ninject
  • Unity
  • Managed Extensibility Framework

PHP4

  • drip

PHP5

  • DiContainer
  • Garden
  • Xyster Framework
  • Lion Framework
  • Symfony Dependency Injection

Perl

  • The IOC Module

Python

  • Zope Component Architecture
  • Spring Python
  • PyContainer

Ruby

  • Copland
  • Needle

3. Внешние ссылки

  • Inversion of Control Containers and the Dependency Injection pattern — Martin Fowler.
  • Dependency Injection & Testable Objects: Designing loosely coupled and testable objects — Jeremy Weiskotten; Dr. Dobb's Journal, May 2006.
  • Design Patterns: Dependency Injection — MSDN Magazine, September 2005
  • Writing More Testable Code with Dependency Injection — Developer.com, October 2006
  • Domain Specific Modeling (DSM) in IoC frameworks
  • Does Dependency Injection pay off? — InfoQ
  • Dependency Injection — Dhanji R. Prasanna; Manning Publications, 2008.
скачать

Данный реферат составлен на основе статьи из русской Википедии. Синхронизация выполнена 14.07.11 20:03:32

Похожие рефераты: SQL injection, Dependency Walker, Gasoline Direct Injection, Dependency Inversion Principle.

Категории: Шаблоны проектирования, Архитектура ПО.

Текст доступен по лицензии Creative Commons Attribution-ShareAlike.