Подтвердить что ты не робот

Что отличает между собой и цель MEF и Unity?

Я только начинаю изучение DI (я работаю над WPF/Silverlight, но у меня есть план перехода на ASP.NET). После того, как я прочитал некоторые статьи из Интернета, есть две рамки, которые меня интересуют, MEF и Unity. Я хочу знать, что между ними реальный мир, и что хорошо делать.

4b9b3361

Ответ 1

Основное отличие состоит в том, что с единицей вы будете явно регистрировать каждый класс, который хотите использовать в композиции:

var container = new UnityContainer();
container.RegisterType<IFoo,Foo>();
container.RegisterType<IBar,Bar>();
...
var program = container.Resolve<Program>();
program.Run();

В MEF, с другой стороны, вы отмечаете классы с атрибутами, а не регистрируете их где-то еще:

[Export(typeof(IFoo))]
public Foo
{
   ...
}

На первый взгляд это выглядит как незначительная синтаксическая разница, но на самом деле это более важно. MEF предназначен для динамического обнаружения деталей. Например, с помощью DirectoryCatalog вы можете проектировать свое приложение таким образом, чтобы его можно было расширить, просто отбросив новые библиотеки DLL в папке приложения.

В этом примере MEF найдет и создаст экземпляр всех классов с атрибутом [Export(typeof(IPlugin))] в данном каталоге и передаст эти экземпляры конструктору Program:

[Export]
public class Program
{
    private readonly IEnumerable<IPlugin> plugins;

    [ImportingConstructor]
    public Program(
       [ImportMany(typeof(IPlugin))] IEnumerable<IPlugin> plugins)
    {
        this.plugins = plugins;
    }

    public void Run()
    {
        // ...
    }
}

Точка входа:

public static void Main()
{
    using (var catalog = new DirectoryCatalog(".","*"))
    using (var container = new CompositionContainer(catalog))
    {
        var program = container.GetExportedValue<Program>();
        program.Run();
    }
}

Для размещения таких сценариев динамической компоновки, MEF имеет концепцию "стабильной композиции", а это означает, что когда она попадает в пропавшую зависимость где-то, она просто будет отмечать эту часть как недоступную и будет продолжать композицию в любом случае.

Стабильная композиция может быть весьма полезной, но она также делает очень трудно отладить неудачную композицию. Поэтому, если вам не требуется динамическое обнаружение деталей и "стабильная композиция", я бы использовал обычный контейнер DI вместо MEF. В отличие от MEF, регулярные контейнеры DI выдают четкие сообщения об ошибках, когда отсутствует зависимость.

Также возможно получить лучшее из обоих миров, используя контейнер DI, который интегрируется с MEF, например Autofac. Используйте Autofac для составления основного приложения и MEF для частей, которые должны быть динамически расширяемыми.

Ответ 2

Есть много вариантов для выполнения DI. Прежде всего, вы должны понимать, что DI - это не инструменты, а скорее шаблоны и принципы. Вы можете использовать DI просто отлично без инструмента. Если вы это сделаете, мы назовем его Бедный человек DI.

Однако, существует много контейнеров DI, доступных для .NET. Единство - это лишь один из них.

MEF очень похож на контейнер DI, но в настоящее время решает другую проблему - проблему расширяемости. Вместо внешней конфигурации компонентов (которые используются все контейнеры DI) он использует механизм обнаружения на основе атрибутов.