在线时间:8:00-16:00
迪恩网络APP
随时随地掌握行业动态
扫描二维码
关注迪恩网络微信公众号
1、Array in stack struct Point2D
{ [MarshalAs(UnmanagedType.ByValArray, SizeConst=2)] public int[] XY; } 现在可以这么写(不过得用unsafe上下文): unsafe struct Point2D
{ public fixed int XY[2]; } public static Delegate GetDelegateForFunctionPointer (
IntPtr ptr, Type t ); public static IntPtr GetFunctionPointerForDelegate ( Delegate d ); 3、Marshal过程支持更多的类型 typedef struct { Point2D XYZ[3]; } Point2DX3;
对应到C#,你也许会这样写: struct Point2D
{ [MarshalAs(UnmanagedType.ByValArray, SizeConst=2)] public int[] XY; } struct Point2DX3 { [MarshalAs(UnmanagedType.ByValArray, SizeConst=3)] public Point2D[] XYZ; } 事实上这是不可行的。在.NET 1.x,结构体内嵌定长数组的类型必须是primitive类型,否则不能进行marshal过程。事实上调用Marshal.SizeOf时,会弹出异常说“无法得到大小”云云 unsafe class BinarySerializer
和.NET内置的序列化机制相比,这个方案效率要高得多。和.NET内置的序列化机制相似,这里需要对象或结构体内部的所有成员都能使用
Marshal.SizeOf得到其大小,对应于“对象或结构体内部的所有成员都带有[Serializable]特性或者实现了
ISerializable接口”。 { public static byte[] Struct2Bytes<T>(T obj) { int size = Marshal.SizeOf(obj); byte[] bytes = new byte[size]; fixed (byte* pb = &bytes[0]) { Marshal.StructureToPtr(obj, (IntPtr)pb, true); } return bytes; } public static T Bytes2Struct<T>(byte[] bytes) { fixed (byte* pb = &bytes[0]) { return (T)Marshal.PtrToStructure((IntPtr)pb, typeof(T)); } } } PS. 这个序列化方案效率虽高,但不如.NET内置的方案可靠。.NET的编译器可以检查一个 类型能否支持序列化,而这个方案得由程序员判断Marshal.SizeOf能否工作(比如Marshal.SizeOf绝对不会知道string类型实 际占用多少内存,也就是说类型实例的大小必须是固定的才行)。 |
请发表评论