我想要获取特定属性的 PropertyInfo。我可以使用:
foreach(PropertyInfo p in typeof(MyObject).GetProperties())
{
if ( p.Name == "MyProperty") { return p }
}
但肯定有一种类似于这样的方式
typeof(MyProperty) as PropertyInfo
有吗?还是我只能使用不安全的类型字符串比较?
谢谢。
我想要获取特定属性的 PropertyInfo。我可以使用:
foreach(PropertyInfo p in typeof(MyObject).GetProperties())
{
if ( p.Name == "MyProperty") { return p }
}
但肯定有一种类似于这样的方式
typeof(MyProperty) as PropertyInfo
有吗?还是我只能使用不安全的类型字符串比较?
谢谢。
有一种使用lambda/Expression
的.NET 3.5方法,不需要使用字符串...
using System;
using System.Linq.Expressions;
using System.Reflection;
class Foo
{
public string Bar { get; set; }
}
static class Program
{
static void Main()
{
PropertyInfo prop = PropertyHelper<Foo>.GetProperty(x => x.Bar);
}
}
public static class PropertyHelper<T>
{
public static PropertyInfo GetProperty<TValue>(
Expression<Func<T, TValue>> selector)
{
Expression body = selector;
if (body is LambdaExpression)
{
body = ((LambdaExpression)body).Body;
}
switch (body.NodeType)
{
case ExpressionType.MemberAccess:
return (PropertyInfo)((MemberExpression)body).Member;
default:
throw new InvalidOperationException();
}
}
}
你可以使用 C# 6 中的新 nameof()
操作符,它可在 Visual Studio 2015 中使用。更多信息请参见此处。
对于您的示例,您将使用:
PropertyInfo result = typeof(MyObject).GetProperty(nameof(MyObject.MyProperty)) ?? throw new Exception();
编译器将会把nameof(MyObject.MyProperty)
转换成字符串 "MyProperty",但是你可以享受到能够重构属性名称的好处,而不必记得要改变字符串,因为Visual Studio、ReSharper等工具知道如何重构nameof()
的值。PropertyInfo result =
开始而不是 var result =
,那么它可能会更清晰一些。 - DavidRR?? throw new Exception()
,因为编译器仍然认为它可能返回 null
。 - Jon Hallintypeof(MyObject).GetProperty("MyProperty")
然而,由于C#没有"符号"类型,因此没有任何东西能够帮助你避免使用字符串。顺便问一句,为什么你称它为"不安全的类型"?
public static class TypeExtensions
{
public static PropertyInfo? GetProperty<T, TValue>(this T type, Expression<Func<T, TValue>> selector) where T : class
{
Expression expression = selector.Body;
return expression.NodeType == ExpressionType.MemberAccess ? (PropertyInfo)((MemberExpression)expression).Member : null;
}
}
使用方法:
myObject.GetProperty(opt => opt.PropertyName);
反射用于运行时类型评估。因此,您的字符串常量无法在编译时进行验证。
Expression
起作用的现有代码。 - Marc GravellPropertyHelper<Derived>.GetProperty(x => x.BaseProperty);
的情况下,您将无法获取正确的属性信息。请参见https://dev59.com/HGw15IYBdhLWcg3wYKmo。 - nawfal