2014-10-28 2 views
3

현재 다양한 데이터를 생성 할 때 약 20-30 개의 속성이 10,000 번 이상 검사되는 클래스 'ArisingViewModel'이 있습니다.스위치 구문을 사용하는 것보다 속성 사전의 속도가 느리다

처음에 나는의 라인을 따라 XML 문자열에서 발생하는 속성 값을 검색하는 방법이 있었다 :

public object GetArisingPropertyValue(string propertyName) 
    { 
     switch (propertyName) 
     { 
      case "name_1": 
       return Name1; 
      case "another_name": 
       return AnotherName; 

      // etc. 
     } 
    } 

을하지만 이것은 업데이트하기 위해 쉽게 일을하기 위해 속성 사전을 사용하도록했다 프로젝트의 다른 부분과 관련하여보다 쉽게 ​​생활 할 수 있습니다. 그래서 같은 내 재산 사전 설정 :

private static readonly IDictionary<string, string> PropertyMap; 


    static ArisingViewModel() 
    { 
     PropertyMap = new Dictionary<string, string>(); 

     var myType = typeof(ArisingViewModel); 

     foreach (var propertyInfo in myType.GetProperties(BindingFlags.Instance | BindingFlags.Public)) 
     { 
      if (propertyInfo.GetGetMethod() != null) 
      { 
       var attr = propertyInfo.GetCustomAttribute<FieldNameAttribute>(); 

       if (attr == null) 
        continue; 

       PropertyMap.Add(attr.FieldName, propertyInfo.Name); 
      } 
     } 
    } 

난과 같이 모든 관련 propertys에 속성을 적용

[FieldName("name_1")] 
    public string Name1 
    { 
     get 
     { 
      return _arisingRecord.Name1; 
     } 
    } 

그리고 다음과 같은 방법을 사용하여 속성 이름/값을 찾을 :

public static string GetPropertyMap(string groupingField) 
    { 
     string propName; 
     PropertyMap.TryGetValue(groupingField, out propName); 
     return propName; //will return null in case map not found. 
    } 

    public static object GetPropertyValue(object obj, string propertyName) 
    { 
     return obj.GetType().GetProperty(propertyName).GetValue(obj, null); 
    } 

내 문제는 이전 switch 문을 사용하여 처리 속도가 매우 빨라 졌음을 발견했습니다 (매우 간단한 타이머 클래스를 사용하여 시스템이 얼마나 오래 걸리는지 측정합니다 ~ 20 se 약 25 초).

누구나 내가 잘못하고있는 것을 제안하거나 현재 코드를 개선 할 수있는 방법을 제안 할 수 있습니까?

+0

* 속성 이름 *을 사전에 넣지 마십시오. –

+3

Reflection **은 느립니다 ** (여기서도 속성 검색은 각 액세스마다 반복됩니다). 이 경우 문제가있는 경우 속성 이름 대신 대리자 사전을 작성하면됩니다. Dictionary . 위임 호출은 첫 번째 메소드 (속성 수가 많지 않은 경우)보다 느리지 만 눈에 띄는 것은 없습니다. Expressions and Reflection.Emit로 실험 할 수도 있지만 ... 먼저 측정하십시오! –

+0

고마워, 그건 나에게 의미가있다. Dictionary 솔루션을 살펴보고 그 방법이 얼마나 빠르는지 살펴보고 느린 경우 다시 스위치로 돌아갑니다! – jimbo

답변

1

StringTemplate 4 (BSD 3 절 라이센스)의 C# 포트에서 ObjectModelAdaptor과 유사한 클래스를 구현하는 것이 좋습니다. 이 기능은 템플릿 렌더링 파이프 라인의 성능이 중요한 섹션에서 많이 사용되며 프로파일 링은 현재 구현이 매우 잘 수행되었음을 나타냅니다.

이 클래스는 합리적으로 효율적인 캐싱 및 디스패치 메커니즘을 사용하지만 ConcurrentDictionary을 사용하고 lock 문을 제거하면 .NET 4 이상의 사용자를 위해 향상 될 수 있습니다.

속성이있는 속성에 특정한 로직을 구현하려면 FindMember 구현을 변경하는 것이 좋습니다.

관련 문제