0

Существует пример на MSDN Deferring the Resolution of ObjectsЕдинство отложив разрешение объектов

// Create a Unity container 
IUnityContainer myContainer = new UnityContainer(); 

// Create an IEnumerable resolver for the IMyClass interface type 
var resolver = myContainer.Resolve<Func<IEnumerable<IMyClass>>>(); 

// ... other code here... 

// Register mappings for the IMyClass interface to appropriate concrete types 
myContainer.RegisterType<IMyClass, FirstClass>("First"); 
myContainer.RegisterType<IMyClass, SecondClass>("Second"); 
myContainer.RegisterType<IMyClass, ThidClass>("Third"); 

// Resolve a collection of the mapped target objects 
IEnumerable<IMyClass> myClassInstances = resolver(); 

Я вдохновил немного и пытается сделать что-то, как показано ниже.

Мой интерфейс и конкретные классы:

public interface IImplementMe 
{ 
    void DoSomething(); 
} 
public class FirstImplementation : IImplementMe 
{ 
    public void DoSomething() 
    { 
     Console.WriteLine("First"); 
    } 
} 
public class SecondImplementation : IImplementMe 
{ 
    public void DoSomething() 
    { 
     Console.WriteLine("Second"); 
    } 
} 

Мой класс Service, как это:

public class Service 
    { 
     private bool someCondition; 

     Func<Dictionary<string, IImplementMe>> myClassInstances; 
     public Service(Func<Dictionary<string, IImplementMe>> myClassInstances) 
     { 
      this.myClassInstances = myClassInstances; 
     } 


     public void Foo() 
     { 
      if (someCondition) 
      { 
       myClassInstances.Invoke()["First"].DoSomething(); 
      } 
      else 
      { 
       myClassInstances.Invoke()["Second"].DoSomething(); 
      } 
     } 
    } 

Как вы можете понять, что я пытаюсь зарегистрировать несколько экземпляров интерфейса и должен использовать правильный по времени работы по требованию.

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

Я знаю, что могу зарегистрировать их, используя aliasses и разрешить их, предоставив aliasses. Но я не хочу давать ссылку на Unity в моем классе обслуживания.

Возможно, существует более мудрый способ сделать это.

ответ

1

Эта документация предназначена для Unity2. Если вы используете Unity3.x, вы должны использовать Lazy<T> вместо Func<T>, как описано here. Я бы поставил под вопрос, почему вам нужно использовать отложенное разрешение, поскольку построение объектов должно быть практически незначительным для производительности (если это не так, то это запах кода для слишком большой работы, выполняемой в ваших конструкторах).

Без ссылки на Unity, ваш разрешенный экземпляр Foo не будет знать имена регистрации элементов коллекции. Но вы можете отличать предметы коллекции другими способами. Вы можете создать свойство Name на языке IImplementMe. Или вы можете получить тип разрешенного элемента.

+0

Вы правы, я не должен использовать отложенное разрешение. Мое приложение находится на .Net 4.0, поэтому я должен использовать Unity2. На самом деле я пытаюсь зарегистрировать несколько экземпляров интерфейса. В Unity3 вы можете сделать это с помощью «container.RegisterTypes», но этот метод расширения не существует в Unity2. – fkucuk

0

В конце концов, я мог бы выяснить что-то.

Спасибо, Тайлер ..

public enum MyType 
    { 
     First, 
     Second 
    } 

    public interface IImplementMe 
    { 
     MyType TypeOfClass { get; } 
     void DoSomething(); 
    } 
    public class FirstImplementation : IImplementMe 
    { 
     public void DoSomething() 
     { 
      Console.WriteLine("First"); 
     } 

     public MyType TypeOfClass 
     { 
      get 
      { 
       return MyType.First; 
      } 
     } 
    } 
    public class SecondImplementation : IImplementMe 
    { 
     public void DoSomething() 
     { 
      Console.WriteLine("Second"); 
     } 

     public MyType TypeOfClass 
     { 
      get 
      { 
       return MyType.Second; 
      } 
     } 
    } 


    public interface IService { } 
    public class Service : IService 
    { 
     private bool someCondition = true; 

     private IImplementMe first; 
     private IImplementMe second; 
     IEnumerable<IImplementMe> hebele; 

     public Service(IEnumerable<IImplementMe> hebele) 
     { 
      this.hebele = hebele; 
      foreach (var item in hebele) 
      { 
       switch (item.TypeOfClass) 
       { 
        case MyType.First: 
         first = item; 
         break; 
        case MyType.Second: 
         second = item; 
         break; 
        default: 
         break; 
       } 
      } 
     } 


     public void Foo() 
     { 
      if (someCondition) 
      { 
       first.DoSomething(); 
      } 
      else 
      { 
       second.DoSomething(); 
      } 
     } 
    } 




class Program 
    { 
     static void Main(string[] args) 
     { 
      IUnityContainer myContainer = new UnityContainer(); 


      myContainer.RegisterType<IImplementMe, FirstImplementation>("First"); 
      myContainer.RegisterType<IImplementMe, SecondImplementation>("Second"); 
      myContainer.RegisterType<IEnumerable<IImplementMe>, IImplementMe[]>(); 


      myContainer.RegisterType<IService, Service>(); 


      var srv = myContainer.Resolve<Service>(); 
      srv.Foo(); 
     } 
    }