考虑像 System.Drawing.Point 这样的结构 - 一个具有 LayoutKind.Sequential 且仅包含原始成员的结构。我有一个此类结构的 C# 数组。
我通过 P/Invoke 将它传递给一个(非托管的)C++ 函数。在 C++ 方面,有相应的结构定义(例如 struct Point { int x, y; };
)。该函数采用 Point*
参数。
我的问题是,在什么情况下 CLR 会复制数据,在什么情况下它只是固定数据?变量包括:
- 数组类型:一维或矩形
- 函数的 C# 定义 - 使用
Point*
或Point[]
/Point[,]
- 是否使用
fixed(Point* pointer = array)
我想避免复制,因为它很慢。
最佳答案
我在固定方面没有太多经验,但是,根据我对 MSDN 的阅读,您的结构应该固定而不是复制。相关引用:
- Marshalling data with PInvoke
- Copying and pinning
- Blittable and non-blittable types
- Default marshalling for value types
来自#2:
Formatted blittable classes have fixed layout (formatted) and common data representation in both managed and unmanaged memory. When these types require marshaling, a pointer to the object in the heap is passed to the callee directly.
并且您的 Point 结构在#3 中作为示例给出,因此它符合 blittable 类型的条件。
我注意到固定对象有一些开销 here ,但那是针对 fixed byte[]
的,它可能与您的 Point[]
不同。
关于c# - 将结构数组从 .NET 编码到 C++ : when does it do copying?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8529389/