有没有一种方法可以获取传递到函数中的值的属性名称?
您是在询问这是否有可能吗?
public void PrintPropertyName(int value) {
Console.WriteLine(someMagicCodeThatPrintsThePropertyName);
}
// x is SomeClass having a property named SomeNumber
PrintInteger(x => x.SomeNumber);
你是否认为控制台将输出"SomeNumber"?
如果是这样,那不对。这显然是不可能的(提示:在PrintPropertyName(5)
时会发生什么?)。但你可以这样做:
public static string GetPropertyName<TSource, TProperty>(this Expression<Func<TSource, TProperty>> expression) {
Contract.Requires<ArgumentNullException>(expression != null);
Contract.Ensures(Contract.Result<string>() != null);
PropertyInfo propertyInfo = GetPropertyInfo(expression);
return propertyInfo.Name;
}
public static PropertyInfo GetPropertyInfo<TSource, TProperty>(this Expression<Func<TSource, TProperty>> expression) {
Contract.Requires<ArgumentNullException>(expression != null);
Contract.Ensures(Contract.Result<PropertyInfo>() != null);
var memberExpression = expression.Body as MemberExpression;
Guard.Against<ArgumentException>(memberExpression == null, "Expression does not represent a member expression.");
var propertyInfo = memberExpression.Member as PropertyInfo;
Guard.Against<ArgumentException>(propertyInfo == null, "Expression does not represent a property expression.");
Type type = typeof(TSource);
Guard.Against<ArgumentException>(type != propertyInfo.ReflectedType && type.IsSubclassOf(propertyInfo.ReflectedType));
return propertyInfo;
}
使用方法:
string s = GetPropertyName((SomeClass x) => x.SomeNumber);
Console.WriteLine(s);
现在,"SomeNumber" 将被打印到控制台上。
只有当你使用lambda函数时,也就是
SomeMethod(()=>someObj.PropName);
(使用一个具有类型表达式树的方法而不仅仅是一个值)
然而,这仍然需要相当多的处理来解决,并涉及反射和表达式。除非绝对必要,否则我会避免使用它。学习表达式仅为此并不值得。
不会。属性将在函数调用之前进行评估,函数中的实际值将是该值的副本,而不是属性本身。