2014-06-25 62 views
2

我已經無休止地搜索了一個指定了我的問題的線程,但找不到它。將類屬性的名稱設置爲字符串

我想要一個類屬性,只是把它作爲一個字符串!

public class Foo 
{ 
    public Foo() 
    { 
    } 
    public int MyProperty { get; set; } 
} 

然後我想在結束的字符串「myProperty的」,這樣的事情:

Foo f = new Foo(); 
string s = Helperfunction(f.MyProperty); 

string Helperfunction( X ) 
{ 
    string MyString; 
    //do something with X 
    return MyString; 
} 

多大的困難會變成這樣實現只是也許helperfunction? 所以輸出應該是「MyProperty」

因爲我不想硬編碼它,並且只要我重構屬性名稱,它仍然可以在不編輯硬編碼字符串的情況下工作!

+3

Whar你真的試圖解決?如果人們總是反思,我認爲他們應該嘗試尋找不同的方法。 –

+0

如果您在代碼中寫入屬性名稱,爲什麼不將它作爲字符串傳遞? – Gusman

+0

@Gusman因爲重命名屬性時重構工具可能不會選擇它。正如OP所說的那樣,「只要我重構屬性名稱,它就會在沒有編輯硬編碼字符串的情況下工作......!」 – dcastro

回答

5

您可以使用反射來獲得名稱,這裏是我使用的幫手類:

public static class MemberName 
{ 
    /// <summary> 
    /// *** WARNING - Uses reflection - use responsibly *** 
    /// </summary> 
    /// <param name="instance"></param> 
    /// <param name="expression"></param> 
    /// <typeparam name="T"></typeparam> 
    /// <returns></returns> 
    public static string GetMemberName<T>(this T instance, Expression<Func<T, object>> expression) 
    { 
     return GetMemberName(expression); 
    } 

    /// <summary> 
    /// *** WARNING - Uses reflection - use responsibly *** 
    /// </summary> 
    /// <param name="expression"></param> 
    /// <typeparam name="T"></typeparam> 
    /// <returns></returns> 
    /// <exception cref="ArgumentException"></exception> 
    public static string GetMemberName<T>(Expression<Func<T, object>> expression) 
    { 
     if (expression == null) 
     { 
      throw new ArgumentException("The expression cannot be null."); 
     } 

     return GetMemberName(expression.Body); 
    } 

    /// <summary> 
    /// *** WARNING - Uses reflection - use responsibly *** 
    /// </summary> 
    /// <param name="instance"></param> 
    /// <param name="expression"></param> 
    /// <typeparam name="T"></typeparam> 
    /// <returns></returns> 
    public static string GetMemberName<T>(this T instance, Expression<Action<T>> expression) 
    { 
     return GetMemberName(expression); 
    } 

    /// <summary> 
    /// *** WARNING - Uses reflection - use responsibly *** 
    /// </summary> 
    /// <param name="expression"></param> 
    /// <typeparam name="T"></typeparam> 
    /// <returns></returns> 
    /// <exception cref="ArgumentException"></exception> 
    public static string GetMemberName<T>(Expression<Action<T>> expression) 
    { 
     if (expression == null) 
     { 
      throw new ArgumentException("The expression cannot be null."); 
     } 

     return GetMemberName(expression.Body); 
    } 

    private static string GetMemberName(Expression expression) 
    { 
     if (expression == null) 
     { 
      throw new ArgumentException("The expression cannot be null."); 
     } 

     if (expression is MemberExpression) 
     { 
      // Reference type property or field 
      var memberExpression = (MemberExpression)expression; 
      return memberExpression.Member.Name; 
     } 

     if (expression is MethodCallExpression) 
     { 
      // Reference type method 
      var methodCallExpression = (MethodCallExpression)expression; 
      return methodCallExpression.Method.Name; 
     } 

     if (expression is UnaryExpression) 
     { 
      // Property, field of method returning value type 
      var unaryExpression = (UnaryExpression)expression; 
      return GetMemberName(unaryExpression); 
     } 

     throw new ArgumentException("Invalid expression"); 
    } 

    private static string GetMemberName(UnaryExpression unaryExpression) 
    { 
     if (unaryExpression.Operand is MethodCallExpression) 
     { 
      var methodExpression = (MethodCallExpression)unaryExpression.Operand; 
      return methodExpression.Method.Name; 
     } 

     return ((MemberExpression)unaryExpression.Operand).Member.Name; 
    } 
} 

並且示例用法:

string propName = MemberName.GetMemberName<Foo>(x => x.MyProperty); 
+0

只需要將class.MyProperty轉換爲「MyProperty」就可以完成整個類的學習? –

+0

只有一種方法還有另一個答案,但它看起來像被刪除了。沒有整個班級是不需要的,我相信你可以用一種方法做到這一點。加入全班同學需要注意什麼? –

+0

沒有演唱會,我只是驚訝,它仍然不是很簡單..! 確實像其他答案,但另一個不工作,所以..! 我會用你的,生病讓你知道在一秒鐘內 –

4

我不太明白這個問題,但是如果你想用屬性名做些什麼,你可以看看CallerMemberName屬性。

string Helperfunction([CallerMemberName]string X = null ) 
{ 

    return "PropertyName: " + X; 

} 

如果你調用一個屬性的getter內這種方法,則輸出屬性的名稱:

public class Foo 
{ 
    public string Foo { get { Trace.WriteLine (SomeFunction()); } } 
} 

輸出「myProperty的」

+3

注意:.net 4.5+ – ken2k

+0

或者在.NET 4上安裝此更新http://support.microsoft.com/kb/2468871/en –

+0

確實無法正常工作......無論如何感謝幫助! –

相關問題