1,Marshal.SizeOf
返回类的非托管大小 (以字节为单位).
- using System;
- using System.Runtime.InteropServices;
- public struct Point
- {
- public int x;
- public int y;
- }
- class Example
- {
- static void Main()
- {
- // Create a point struct.
- Point p;
- p.x = 1;
- p.y = 1;
- Console.WriteLine("The value of first point is" + p.x + "and" + p.y + ".");
- // 先获取 p 的内存大小 再分配内存
- IntPtr pnt = Marshal.AllocHGlobal(Marshal.SizeOf(p));
- try
- {
- // 将数据从托管对象封送到非托管内存块
- //p 是要封送的数据的托管对象
- //pnt 是指向非托管内存块的指针
- Marshal.StructureToPtr(p, pnt, false);
- Point anotherP;
- // 将数据从非托管内存块封送到托管对象
- //pnt 是指向非托管内存块的指针
- // 第二个参数是将数据复制到其中的对象. 这必须是格式化类的实例.
- anotherP = (Point)Marshal.PtrToStructure(pnt, typeof(Point));
- Console.WriteLine("The value of new point is" + anotherP.x + "and" + anotherP.y + ".");
- }
- finally
- {
- // Free the unmanaged memory.
- Marshal.FreeHGlobal(pnt); // 释放内存
- }
- }
- }
- 2,Marshal.AllocHGlobal
从进程的非托管内存中分配内存.
AllocHGlobal(Int32) 通过使用指定的字节数, 从进程的非托管内存中分配内存.
AllocHGlobal(IntPtr) 通过使用指向指定字节数的指针, 从进程的非托管内存中分配内存.
返回值: 指向新分配的内存的指针. 必须使用 FreeHGlobal(IntPtr) 方法释放该内存.
- IntPtr hglobal = Marshal.AllocHGlobal(100);
- Marshal.FreeHGlobal(hglobal);
3,Marshal.SizeOf 和 sizeof 的区别
4,IntPtr 结构: 用于表示指针或句柄的平台特定类型.
示例: 使用托管指针来反转数组中的字符
- using System;
- using System.Runtime.InteropServices;
- class NotTooSafeStringReverse
- {
- static public void Main()
- {
- string stringA = "I seem to be turned around!";
- int copylen = stringA.Length;
- // 将 Unicode 字符串作为 ANSI (单字节) 字符复制到非托管内存. 返回 IntPtr 指向非托管字符串的开头的对象.
- IntPtr sptr = Marshal.StringToHGlobalAnsi(stringA);
- // 分配与非托管字符串占用的字节数相同的字节数
- IntPtr dptr = Marshal.AllocHGlobal(copylen + 1);
- // The unsafe section where byte pointers are used.
- unsafe
- {
- // 获取指向字符串的起始地址和非托管内存块的非托管指针, 并将该字符串的长度小于该字符串的长度添加到 ANSI 字符串的起始地址
- // 由于非托管字符串指针现在指向字符串的末尾, 因此复制操作会将字符串末尾的字符复制到内存块的开头
- byte *src = (byte *)sptr.ToPointer();
- byte *dst = (byte *)dptr.ToPointer();
- if (copylen> 0)
- {
- src += copylen - 1;
- // 使用循环将字符串中的每个字符复制到非托管内存块.
- while (copylen--> 0)
- {
- *dst++ = *src--;
- }
- *dst = 0;
- }
- }
- // 将包含复制的 ANSI 字符串的非托管内存块转换为托管的 Unicode String 对象
- string stringB = Marshal.PtrToStringAnsi(dptr);
- Console.WriteLine("Original:\n{0}\n", stringA);
- Console.WriteLine("Reversed:\n{0}", stringB);
- // 释放为非托管 ANSI 字符串和非托管内存块分配的内存
- Marshal.FreeHGlobal(dptr);
- Marshal.FreeHGlobal(sptr);
- }
- }
- //output:
- //
- // Original:
- // I seem to be turned around!
- //
- // Reversed:
- // !dnuora denrut eb ot mees I
来源: http://www.bubuko.com/infodetail-3776872.html