IntPtr 到三维数组
IntPtr to three dimensional array
我正在我的 C# 项目中使用 C++ dll。使用 pInvoke(平台调用)。
我的 C++ 代码 returns 一个 double***,C# 函数 returns 一个 IntPtr。
我有矩阵两边的维度,只是它们不是常量。
在 C# 方面我有:
[DllImport("mylib.dll")]
public static extern IntPtr GetMatrix(int width, int height, int depth);
在 C++ 方面我有:
extern "C" {
__declspec(dllexport) double*** GetMatrix(int width, int height, int depth) {
// do stuff
return matrix;
}
}
现在我需要将这个 IntPtr 转换为 double[],但是,我不知道该怎么做。
基本上我需要this question答案的反义词。
我从来没有用这些类型的数组尝试过,但是第一个解决方案可能有效,我被 this MSDN article:
引导相信
(请注意,这仅在您可以在 C# 端更改函数定义时才有效)在您的 C# 函数中,将 IntPtr
参数更改为 double[,,]
参数并将此 MarshalAs 属性添加到它, 类似于上面 MSDN 文章的做法。
[DllImport("FooBar.dll")]
extern void Foo([MarshalAs(UnmanagedType.LPArray, SizeConst=**YOUR ARRAY SIZE HERE**)] double[,,] bar);
这还假设您有一个固定大小的数组,我不确定这将如何与 3d 数组一起工作,但是如果您想进一步研究这种类型的解决方案,这里是完整的MarshalAsAttribute.
的文档
另一个解决方案与另一个问题的相反答案非常相似。您可以将 double[,,]
初始化为您需要的任何大小,然后开始使用 Marshal.Copy
(this overload) 填充行。您还可以编组具有相同功能的单个双精度数。像这样:
double[,,] arr = new double[25, 25, 200];
int il = arr.GetLength(0), jl = arr.GetLength(1), kl = arr.GetLength(2);
IntPtr values = DllFoo();
for (int i = 0; i < il; i++)
{
for (int j = 0; j < jl; j++)
{
for (int k = 0; k < kl; k++)
{
double[] temp = new double[1];
arr[i,j,k] = Marshal.Copy(values, temp, 1, k + j * jl + k * jl * kl);
}
}
}
您绝对可以从该代码段中获得更多性能,但它应该仍然有效。
我正在我的 C# 项目中使用 C++ dll。使用 pInvoke(平台调用)。
我的 C++ 代码 returns 一个 double***,C# 函数 returns 一个 IntPtr。
我有矩阵两边的维度,只是它们不是常量。
在 C# 方面我有:
[DllImport("mylib.dll")]
public static extern IntPtr GetMatrix(int width, int height, int depth);
在 C++ 方面我有:
extern "C" {
__declspec(dllexport) double*** GetMatrix(int width, int height, int depth) {
// do stuff
return matrix;
}
}
现在我需要将这个 IntPtr 转换为 double[],但是,我不知道该怎么做。
基本上我需要this question答案的反义词。
我从来没有用这些类型的数组尝试过,但是第一个解决方案可能有效,我被 this MSDN article:
引导相信(请注意,这仅在您可以在 C# 端更改函数定义时才有效)在您的 C# 函数中,将 IntPtr
参数更改为 double[,,]
参数并将此 MarshalAs 属性添加到它, 类似于上面 MSDN 文章的做法。
[DllImport("FooBar.dll")]
extern void Foo([MarshalAs(UnmanagedType.LPArray, SizeConst=**YOUR ARRAY SIZE HERE**)] double[,,] bar);
这还假设您有一个固定大小的数组,我不确定这将如何与 3d 数组一起工作,但是如果您想进一步研究这种类型的解决方案,这里是完整的MarshalAsAttribute.
的文档另一个解决方案与另一个问题的相反答案非常相似。您可以将 double[,,]
初始化为您需要的任何大小,然后开始使用 Marshal.Copy
(this overload) 填充行。您还可以编组具有相同功能的单个双精度数。像这样:
double[,,] arr = new double[25, 25, 200];
int il = arr.GetLength(0), jl = arr.GetLength(1), kl = arr.GetLength(2);
IntPtr values = DllFoo();
for (int i = 0; i < il; i++)
{
for (int j = 0; j < jl; j++)
{
for (int k = 0; k < kl; k++)
{
double[] temp = new double[1];
arr[i,j,k] = Marshal.Copy(values, temp, 1, k + j * jl + k * jl * kl);
}
}
}
您绝对可以从该代码段中获得更多性能,但它应该仍然有效。