Func <domainobject,object>如何将对象名称返回为字符串</domainobject,object>

时间:2013-12-12 20:05:07

标签: c# delegates func

我有这样的静态方法:

    public static string MyMethod(Func<Student, object> func)
    {            
        return ??? ;
    }

我用它如下:

    var s1 = MyMethod(student => student.ID); // Return "ID" ???
    var s2 = MyMethod(student => student.Age); // Return "Age" ???
    var s3 = MyMethod(student => student.Name); // Return "Name" ???

如何返回以下结果的write方法?

  • s1:“ID”
  • s2:“年龄”
  • s3:“姓名”

* 在=&gt;之后返回每个属性的名称作为字符串

3 个答案:

答案 0 :(得分:1)

您可以更改方法的签名 从

  public static string MyMethod(Func<Student, object> func)

将其更改为

  public static string MyMethod(Expression<Func<Student, object>> func) {
     return GetMemeberName(func)
  } 

  public static string GetMemberName(Expression expression)
    {            
        if (expression is LambdaExpression)
        {
            var lambdaExpression = (LambdaExpression)expression;
            return GetMemberName(lambdaExpression.Body);                              
        }

        if (expression is MemberExpression)
        {
            var memberExpression = (MemberExpression)expression;
            if (memberExpression.Expression.NodeType == ExpressionType.MemberAccess)
            {
                return GetMemberName(memberExpression.Expression)+ "."+ memberExpression.Member.Name;
            }
            return memberExpression.Member.Name;
        }

        if (expression is UnaryExpression)
        {
            var unaryExpression = (UnaryExpression)expression;
           if (unaryExpression.NodeType != ExpressionType.Convert)
                throw new Exception(string.Format(
                    "Cannot interpret member from {0}",
                    expression));
            return GetMemberName(unaryExpression.Operand);
        }
        throw new Exception(string.Format("Could not determine member from {0}",expression));
    }  

答案 1 :(得分:0)

签名必须包含表达式树而不是func才能检查它。幸运的是,你的调用不会改变,因为编译器会从你的lambda中创建表达式。

这个版本可能是最短版本,它不涉及递归,但仅适用于简单的属性访问lambdas。

public static string MyFunc( Expression<Func<Student, object>> Property )
{
     if ( Property != null && Property.Body != null )
         if ( Property.Body.NodeType == ExpressionType.MemberAccess )
         {
             MemberExpression memberExpression = 
                (MemberExpression)Property.Body;

             if ( !string.IsNullOrEmpty( memberExpression.Member.Name ) )
                 return memberExpression.Member.Name;

         }

     return string.Empty;
 }

答案 2 :(得分:0)

another SO question开始,这可能是您正在寻找的内容:

public static string GetPropertyName<T>(Expression<Func<T>> propertyExpression)
{
    return (propertyExpression.Body as MemberExpression).Member.Name;
}

要使用它,你会写这样的东西:

var propertyName = GetPropertyName(
    () => myObject.AProperty); // returns "AProperty"