2013-08-23 53 views
1

是否有可能使用帶有表達式的枚舉來反映枚舉值?考慮這個假設常規:使用Enum作爲/與表達式?

public enum Fruit 
{ 
    Apple, 
    Pear 
} 

public void Foo(Fruit fruit) 
{ 
    Foo<Fruit>(() => fruit); 
} 

public void Foo<T>(Expression<Func<T>> expression) 
{ 
    //... example: work with Fruit.Pear and reflect on it 
} 

Bar()會給我有關枚舉的信息,但我想用實際值繼續工作。

背景:我一直在添加一些幫助器方法來返回類型的CustomAttribute信息,並想知道是否有類似的例程可以用於枚舉。

我完全知道你可以使用枚舉類型來獲得CustomAttributes。

更新:

我在MVC使用了類似的概念,幫助擴展:

public class HtmlHelper<TModel> : System.Web.Mvc.HtmlHelper<TModel> 
{ 
    public void BeginLabelFor<TProperty>(Expression<Func<TModel, TProperty>> expression) 
    { 
     string name = ExpressionHelper.GetExpressionText(expression); 
    } 
} 

在這個例子中name將是模型的成員名稱。我想用枚舉做類似的事情,所以名字就是枚舉的'成員'。這甚至有可能嗎?

更新了例:

public enum Fruit 
{ 
    [Description("I am a pear")] 
    Pear 
} 

public void ARoutine(Fruit fruit) 
{ 
    GetEnumDescription(() => fruit); // returns "I am a pear" 
} 

public string GetEnumDescription<T>(/* what would this be in a form of expression? Expression<T>? */) 
{ 
    MemberInfo memberInfo; 
    // a routine to get the MemberInfo(?) 'Pear' from Fruit - is this even possible? 

    if (memberInfo != null) 
    { 
    return memberInfo.GetCustomAttribute<DescriptionAttribute>().Description; 
    } 

    return null; // not found or no description 
} 
+8

你的意思是讓Foo打電話給酒吧?你爲什麼在這裏使用表達式樹?你究竟在努力實現什麼?你的問題目前非常模糊。 –

+0

@JonSkeet很抱歉,發佈前發生變更的情況。我已經更新了它,並且還爲Mvc添加了一個例程,其中爲屬性標籤提取了屬性的名稱。 –

+2

目前還不清楚爲什麼你不只是調用'ToString()',它會給你與該值相關聯的名稱。 –

回答

4

你不需要Expression S表示這一點。所有你需要知道的是,enum s爲他們的每個值都有一個字段。這意味着你可以這樣做:

public string GetEnumDescription<T>(T enumValue) where T : struct 
{ 
    if (!typeof(T).IsEnum) 
     throw new ArgumentException("T has to be an enum"); 

    FieldInfo field = typeof(T).GetField(enumValue.ToString()); 

    if (field != null) 
    { 
     var attribute = field.GetCustomAttribute<DescriptionAttribute>(); 

     if (attribute != null) 
      return attribute.Description; 
    } 

    return null; // not found or no description 
}