我想在 C# 中为 boolean 数组实例化内存,并使用互操作将其传递给 C 库函数。然后 C 函数应该用数据(结果)填充数组,以便数据可以传回 C# 并在那里使用。由于数组是引用类型,并且我为数组显式设置了 [In, Out] 编码属性,所以我认为这很容易。但显然不是。 :-( 下面是一些说明问题的测试代码(尽可能简单)。
在 C 中,我会这样调用:
extern "C" __declspec(dllexport) int __stdcall TestFillArray(bool *resultMaterials, int materialLength);
__declspec(dllexport) int __stdcall TestFillArray(bool *resultMaterials, int materialLength)
{
resultMaterials[0] = true;
resultMaterials[1] = true;
return materialLength;
}
我使用以下声明从 C# 调用此函数:
[DllImport("FrontAuction2.dll", CharSet = CharSet.Auto, SetLastError = true, CallingConvention = CallingConvention.StdCall)]
public static extern int TestFillArray([MarshalAs(UnmanagedType.LPArray, SizeConst = 2), In, Out] bool[] resultMaterial, int materialLength);
然后在我的 C# 测试方法中我有:
var resultMaterials = new bool[2];
var res = TestFillArray(resultMaterials, 2);
当我检查结果时,我得到 res=2 和 resultMaterials[0] = true,以及 resultMaterials[1] = false。 IE。 res 值和第一个数组元素都是正确的,但第二个不是。所以看起来 boolean 数据没有正确编码(除非我遗漏了一些明显的东西)。
我猜也可以声明一个 IntPtr 而不是一个数组,并成功地将这两个元素编码为正确的结果。但是,由于我希望在 C# 中将数组分配到内存中,所以我不确定该怎么做。
非常感谢这方面的帮助。我有点被困在这里。 :(
更新:我猜这是因为 boolean 值只有 1 个字节长,而 C# 代码没有获取此信息。那么如何指定呢?
最佳答案
使用
[MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.I1, SizeConst = 2), In, Out]
应该告诉框架将数组混搭为 1 字节 bool
的数组。另一种选择是改用 4 字节 BOOL
。有关详细信息,请参阅 UnmanagedType
enum .
关于c# - 如何在 C# 互操作调用中从 C# 实例化数组中的 C 取回数据?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6599324/