2010-05-19 1 views
0

내 프로그램은 Win32API 함수를 통해 운영 체제와 많은 상호 작용을합니다. 이제 Linux (No wine)에서 Mono로 프로그램을 이전하려고합니다. 운영 체제와의 상호 작용에 다른 구현이 필요합니다.플랫폼 별 구현을위한 C#의 단일성

다른 플랫폼에 대해 서로 다른 구현을 할 수있는 코드를 설계하기 시작했으며 새로운 플랫폼으로 확장 할 수 있습니다.

  1. 나는 PlatformSpecificAttribute을 가지고 ISomeInterface의 구현을 강제 할 수 없습니다

    public interface ISomeInterface 
    { 
        void SomePlatformSpecificOperation(); 
    } 
    
    [PlatformSpecific(PlatformID.Unix)] 
    public class SomeImplementation : ISomeInterface 
    { 
        #region ISomeInterface Members 
    
        public void SomePlatformSpecificOperation() 
        { 
         Console.WriteLine("From SomeImplementation"); 
        } 
    
        #endregion 
    } 
    
    public class PlatformSpecificAttribute : Attribute 
    { 
        private PlatformID _platform; 
    
        public PlatformSpecificAttribute(PlatformID platform) 
        { 
         _platform = platform; 
        } 
    
        public PlatformID Platform 
        { 
         get { return _platform; } 
        } 
    } 
    
    public static class PlatformSpecificUtils 
    { 
        public static IEnumerable<Type> GetImplementationTypes<T>() 
        { 
         foreach (Assembly assembly in AppDomain.CurrentDomain.GetAssemblies()) 
         { 
          foreach (Type type in assembly.GetTypes()) 
          { 
           if (typeof(T).IsAssignableFrom(type) && type != typeof(T) && IsPlatformMatch(type)) 
           { 
            yield return type; 
           } 
          } 
         } 
        } 
    
        private static bool IsPlatformMatch(Type type) 
        { 
         return GetPlatforms(type).Any(platform => platform == Environment.OSVersion.Platform); 
        } 
    
        private static IEnumerable<PlatformID> GetPlatforms(Type type) 
        { 
         return type.GetCustomAttributes(typeof(PlatformSpecificAttribute), false) 
          .Select(obj => ((PlatformSpecificAttribute)obj).Platform); 
        } 
    } 
    
    class Program 
    { 
        static void Main(string[] args) 
        { 
         Type first = PlatformSpecificUtils.GetImplementationTypes<ISomeInterface>().FirstOrDefault(); 
        } 
    } 
    

    나는이 디자인 두 가지 문제를 참조하십시오.

  2. 여러 구현을 동일한 PlatformID으로 표시 할 수 있으며 주에서 사용할 항목을 모릅니다. 첫 번째를 사용하는 것은 ummm 추한 것입니다.

어떻게 이러한 문제를 해결할 수 있습니까? 다른 디자인을 제안 해 주시겠습니까?

답변

0

두 개 이상의 app.config 파일을 준비하고 각각에 따라 플랫폼 종속 구현을 삽입 할 수 있다고 생각합니다.

마지막으로 Windows에서 app.config의 Windows 버전을 사용하는 경우 Unix의 Unix 버전이 사용되는 동안 플랫폼 의존적 인 설치 또는 다른 배포 방법으로 많은 작업을 남겨 둡니다.

addin 아키텍처 또는 다른 복잡한 솔루션을 사용하여 다른 유용한 기능을 사용할 수 있습니다.

0

당신은 유니티 (Unity)에 대해 언급하고 있습니다. 당신은 Dependency Injection container를 사용 해본 적이 있습니까? Castle Windsor, StructureMap과 ninject는 모두 Mono를 어느 정도 지원할 수 있다고 생각합니다.

+0

여기에 맞지 않습니다. 거의 모든 인기있는 DI 컨테이너가 MoMA 테스트를 통과하지 못했습니다. Unity는 모든 MoMA 테스트를 통과하지 못하지만 일부 시나리오에서는 Mono에서 제대로 실행됩니다. –

2

반시의 출처를 살펴보십시오. 그들은 플랫폼에 따라 다른 구현을 연결하는 깔끔한 방법을 가지고 있습니다.