[MEF] 6. Lazy Exports

Managed Extensibility Framework 2009. 4. 13. 00:38 Posted by POWERUMC
일반적인 Exports
 
Composable Part 를 구성하는 동안 특정 Part 에 대한 요청으로 객체 내부의 객체가 필요할 때가 있습니다. 만약 객체가 이런 연관 관계가 있을 경우 객체 내부에 ImportAttribute 을 선언하여 외부 Part 를 Import 할 수 있습니다. 이런 경우는 객체 내부에 Export 간의 Related 관계를 갖게 됨으로써 자동적으로 객체를 초기화할 수 있게 됩니다. ([MEF] 3. Export 선언 참조)
 
일반적인 Export 를 통해 객체 내부에 Import 를 선언하는 방법입니다.
 
class Program
{
        static void Main(string[] args)
        {
               Program p = new Program();
               p.Run();
        }
 
        void Run()
        {
               var catalog = new AggregateCatalog(new AssemblyCatalog(Assembly.GetExecutingAssembly()));
 
               var container = new CompositionContainer(catalog);
               var batch = new CompositionBatch();
               batch.AddPart(this);
 
               container.Compose(batch);
 
               var obj = container.GetExportedObject<EmailMessageSender>();
               obj.Sender.Say();
        }
}
 
[Export]
public class MessageSender
{
        public void Say()
        {
               Console.WriteLine("Say Method");
        }
}
 
[Export]
public class EmailMessageSender
{
        [Import]
        public MessageSender Sender { get; set; }
}
 
 
Lazy Exports
 
하지만 비용이 비싼 객체를 생성할 경우 위의 [일반적인 Exports] 는 매우 비효율적일 수 있습니다. 객체 내부의 Import Object 를 사용하지 않을 가능성이 크거나, 객체의 생성 비용이 클 경우는 Lazy Export 를 고려해야 합니다. 그리고 내부 객체가 동기적(Synchronicity)이 아닌 비동기성(Asynchronism) 성격의 객체일 경우에도 반드시 필요한 기법입니다.
 
이런 경우 내부 객체의 생성을 선택적, 수동적으로 제어하여, 게으른 초기화(Lazy Initialization) 를 할 필요가 있습니다.
 
아래의 굵은 표시의 코드가 Lazy Export 로 제어하는 코드입니다.
 
class Program
{
        static void Main(string[] args)
        {
               Program p = new Program();
               p.Run();
        }
 
        void Run()
        {
               var catalog = new AggregateCatalog(new AssemblyCatalog(Assembly.GetExecutingAssembly()));
 
               var container = new CompositionContainer(catalog);
               var batch = new CompositionBatch();
               batch.AddPart(this);
 
               container.Compose(batch);
 
               var obj = container.GetExportedObject<EmailMessageSender>();
               obj.Sender.Say();
 
               var lazyObj = container.GetExportedObject<EmailMessageSenderByLazyExport>();
               lazyObj.Sender.GetExportedObject().Say();
        }
}
 
[Export]
public class MessageSender
{
        public void Say()
        {
               Console.WriteLine("Say Method");
        }
}
 
[Export]
public class EmailMessageSender
{
        [Import]
        public MessageSender Sender { get; set; }
}
 
[Export]
public class EmailMessageSenderByLazyExport
{
        [Import]
        public Export<MessageSender> Sender { get; set; }
}
 
ImportAttribute 의 프로퍼티를 Export<T> 타입으로 변경하면 내부 객체를 GetExportedObject() 메서드를 이용하여 지연하여 객체를 생성할 수 있습니다.

'Managed Extensibility Framework' 카테고리의 다른 글

[MEF] 8. Strongly Typed Metadata  (0) 2009.04.16
[MEF] 7. Exports and Metadata  (0) 2009.04.16
[MEF] 5. Catalog 사용  (0) 2009.04.09
[MEF] 4. Import 선언  (0) 2009.04.07
[MEF] 3. Export 선언  (0) 2009.03.29