如果GetFields()不保证顺序,LayoutKind.Sequential如何工作

时间:2011-11-09 15:41:54

标签: c# reflection marshalling

我需要在声明顺序的保证顺序中获取fieldinfo。现在我正在使用属性来指定顺序。

有更自动的方法吗?

是否有人知道LayoutKind.Sequential如何运作,以及我是否可以应用其技术。

除非有一些添加属性的预编译器代码,否则我看不到LayoutKind.Sequential是如何工作的。

3 个答案:

答案 0 :(得分:15)

如果您希望Type.GetFields返回的字段的顺序稳定,请尝试按MetadataToken属性进行排序。

Type myType = ...
BindingFlags flags = ...
IEnumerable<FieldInfo> orderedFields = myType.GetFields(flags)
                                             .OrderBy(field => field.MetadataToken);

根据经验,已经发现以这种方式排序字段为return them in declaration order虽然没有记录

顺便说一下,问的问题并不完全有意义;没有任何理由相信反射API与运行时如何在内存中放置对象有关。

答案 1 :(得分:3)

问题是陈旧但不是那么老......我正在处理同样的问题。而且我更喜欢按照声明的顺序获取字段。以下调用应适用于值类型或格式化引用类型。

var fields = type.GetFields().OrderBy(f => Marshal.OffsetOf(type, f.Name).ToInt32());

享受!

答案 2 :(得分:0)

LayoutKind.Sequential指定类型的字段应按照在源代码中声明的顺序在内存中布局。

如果没有该属性,CLR可以通过重新排列字段来自由优化内存使用。

因此该属性只是添加元数据,告诉CLR不要在内存优化中做任何会弄乱字段顺序的内容。