【问题标题】:Reflection: Get All properties that implements an interface in a parameter Object反射:获取参数Object中实现接口的所有属性
【发布时间】:2018-07-24 23:31:49
【问题描述】:

我有一个类有很多其他类的对象:

public class Rootobject
{
    public USD USD { get; set; }
    public CAD CAD { get; set; }
    public EUR EUR { get; set; }
    public AED AED { get; set; }
    public AFN AFN { get; set; }
    public ALL ALL { get; set; }
}

这些类中的每一个都实现了一个名为ICurrency 的接口; ICurrency 接口有一个名为“symbol”的字符串属性,如下所示:

public class EUR : ICurrency 
{/*code logic*/}

最后我有一个方法,它以RootObject 实例为参数;

public object Add22(Rootobject rootobject)
{}

我需要获取rootobject 变量中传递的所有实例的“符号”属性的所有值。

我认为这可以通过反射轻松完成,方法是创建一个 ICurrency 列表并在其中添加所有对象,然后循环遍历它。

我说的对吗?如果是的话;那么如何制作呢?还是有更好的方法?

【问题讨论】:

    标签: c# reflection


    【解决方案1】:

    您可以使用Type.GetProperties 获取类型的属性,使用Type.IsAssignableFrom 查找是否可以将属性分配给ICurrency 变量。您可以使用 LINQ 查询检索所有匹配的属性:

    var currencyProps=typeof(Rootobject).GetProperties()                                   
                       .Where(pi=>typeof(ICurrency).IsAssignableFrom(pi.PropertyType))
                       .ToArray();
    

    var currencyProps=( from pi in typeof(Rootobject).GetProperties()                                   
                        where typeof(ICurrency).IsAssignableFrom(pi.PropertyType)
                      ).ToArray();
    

    您可以将currencyProps 数组缓存在静态字段中,并将其用于任何对象:

    static PropertyInfo[] _currencyProps;
    
    static void InitializeCurrencyProps()
    {
        var currencyProps=( from pi in typeof(RootObject).GetProperties()                                   
                            where typeof(ICurrency).IsAssignableFrom(pi.PropertyType)
                            select pi);
        _currencyProps=currencyProps.ToArray();
    }
    

    一旦你拥有了所有你想要的 PropertyInfo 对象,你就可以使用PropertyInfo.GetValue 从一个特定的实例中读取一个属性值,例如:

    _currencyProps[0].GetValue(rootObject);
    

    要查找所有具有值的属性,即不是 noll,您可以使用另一个查询:

    var values=_currencyProps.Select(pi=>new {pi.Name,Value=pi.GetValue(rootobject)})
                            .Where(val=>val.Value!=null)
                            .ToArray();
    

    var values = ( from pi in _currencyProps
                   let value=pi.GetValue(rootobject)
                   where value !=null
                   select new {pi.Name,value}
                 ).ToArray();
    

    您可以使用ToDictionary() 创建字典而不是数组:

    var values = ( from pi in _currencyProps
                   let value=pi.GetValue(rootobject)
                   where value !=null
                   select new {pi.Name,Value=value}
                 ).ToDictionary(pair=>pair.Name,pair=>pair.Value);
    
    var usd=values["USD"];
    

    【讨论】:

    • 非常感谢;在获取 Values 数组以挖掘所需的属性后,我使用了这一部分: foreach (var x in values) { ICurrency iCurrency = (ICurrency)x.value; //剩下的代码 }
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-09-21
    • 1970-01-01
    • 2011-10-12
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多