使用反射按声明顺序获取属性 [英] Get properties in order of declaration using reflection

查看:32
本文介绍了使用反射按声明顺序获取属性的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要按照在类中声明的顺序使用反射获取所有属性.根据 MSDN,使用 GetProperties()

I need to get all the properties using reflection in the order in which they are declared in the class. According to MSDN the order can not be guaranteed when using GetProperties()

GetProperties 方法不返回特定的属性顺序,例如字母顺序或声明顺序.

The GetProperties method does not return properties in a particular order, such as alphabetical or declaration order.

但我已经读到通过 MetadataToken 对属性进行排序是一种解决方法.所以我的问题是,那安全吗?我似乎无法在 MSDN 上找到有关它的任何信息.或者有没有其他方法可以解决这个问题?

But I've read that there is a workaround by ordering the properties by the MetadataToken. So my question is, is that safe? I cant seem find any information on MSDN about it. Or is there any other way of solving this problem?

我目前的实现如下:

var props = typeof(T)
   .GetProperties(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic)
   .OrderBy(x => x.MetadataToken);

推荐答案

On .net 4.5 (甚至 vs2012 中的 .net 4.0) 你可以使用带有 [CallerLineNumber] 属性的巧妙技巧通过反射做得更好,让编译器插入为您订购您的物业:

On .net 4.5 (and even .net 4.0 in vs2012) you can do much better with reflection using clever trick with [CallerLineNumber] attribute, letting compiler insert order into your properties for you:

[AttributeUsage(AttributeTargets.Property, Inherited = false, AllowMultiple = false)]
public sealed class OrderAttribute : Attribute
{
    private readonly int order_;
    public OrderAttribute([CallerLineNumber]int order = 0)
    {
        order_ = order;
    }

    public int Order { get { return order_; } }
}


public class Test
{
    //This sets order_ field to current line number
    [Order]
    public int Property2 { get; set; }

    //This sets order_ field to current line number
    [Order]
    public int Property1 { get; set; }
}

然后使用反射:

var properties = from property in typeof(Test).GetProperties()
                 where Attribute.IsDefined(property, typeof(OrderAttribute))
                 orderby ((OrderAttribute)property
                           .GetCustomAttributes(typeof(OrderAttribute), false)
                           .Single()).Order
                 select property;

foreach (var property in properties)
{
   //
}

如果您必须处理部分类,您还可以使用 [CallerFilePath] 对属性进行额外排序.

If you have to deal with partial classes, you can additionaly sort the properties using [CallerFilePath].

这篇关于使用反射按声明顺序获取属性的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆