Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/297.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/158.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/316.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
将结构数组从C#传递到C++;使用IntPtr_C#_C++_Pinvoke - Fatal编程技术网

将结构数组从C#传递到C++;使用IntPtr

将结构数组从C#传递到C++;使用IntPtr,c#,c++,pinvoke,C#,C++,Pinvoke,我有一个结构--> 编组必须在“IntPtr[]标记列表”和结构标记列表之间进行 [StructLayout(LayoutKind.Sequential)] internal struct TAG_IN_PARAM { public int vis_cnt; public bool valid; } 它也是一个数组,如=>TAG_IN_PARAM[]TAG_list=new TAG_IN_PARAM[1000] 我想把结构“读者”从C++到C

我有一个结构-->

编组必须在“IntPtr[]标记列表”和结构标记列表之间进行

   [StructLayout(LayoutKind.Sequential)]
   internal struct TAG_IN_PARAM
   {
       public int vis_cnt;
       public bool valid;
   }
它也是一个数组,如=>TAG_IN_PARAM[]TAG_list=new TAG_IN_PARAM[1000]

我想把结构“读者”从C++到C++。然而,我一直在做编组,但DLL端出现了垃圾值

//分配内存 Marshal.StructureToPtr(tag_list[j],Reader.tag_list[j],false)

或者如果我有其他方法可以做到,请转达。 任何帮助都将不胜感激。
谢谢。

< P>你试图匹配的C++类型是根据你的评论:

class Readers 
{
public:
    TAG_IN_PARAM* tag_list;
};
这是指向数组的指针

但是您的C#代码声明了一个内联数组。您的C#代码将与此匹配:

class Readers 
{
public:
    TAG_IN_PARAM tag_list[1000];
};
显然,这不是你想走的路

您需要更改C代码以使其匹配。不幸的是,当数组位于结构内部时,封送器似乎不会将数组封送为指向第一个元素的指针。因为数组是结构中唯一的东西,所以只需将数组作为参数传递即可

或者,如果您确实需要在结构中传递数组,那么我认为您需要手动封送。像这样

public struct readers
{
    public IntPtr tag_list;
};
然后你可以简单地固定你的数组

TAG_IN_PARAM[] tag_list = ...;
GCHandle pinnedArray = GCHandle.Alloc(tag_list, GCHandleType.Pinned);
readers r;
r.tag_list = pinnedArray.AddrOfPinnedObject();
// call function passing r
pinnedArray.Free();
不幸的是,由于C#
bool
是不可闪电攻击的,所以这并不能完全起作用。因此,您可以通过为该字段使用不同的类型来解决此问题。例如:代码>字节或<代码> int >代码>取决于C++的内容。 还有一个选项是每个字段上的
Marshal.StructureToPtr
。运行方式如下:

TAG_IN_PARAM[] tag_list = ...;
int structSize = Marshal.SizeOf(typeof(TAG_IN_PARAM));
r.tag_list = Marshal.AllocHGlobal(tag_list.Length*structSize);
IntPtr ptr = r.tag_list;
for (int i = 0; i < tag_list.Length; i++)
{
    Marshal.StructureToPtr(tag_list[i], ptr, false);
    ptr += structSize;
    // or on older versions of .net without arithmetic support on IntPtr
    // ptr = (IntPtr) (long)ptr + structSize;
}
// call function passing r
Marshal.FreeHGlobal(r.tag_list);
TAG_IN_PARAM[]TAG_list=。。。;
int structSize=Marshal.SizeOf(typeof(TAG_IN_PARAM));
r、 tag_list=Marshal.AllocHGlobal(tag_list.Length*structSize);
IntPtr ptr=r.tag_列表;
对于(int i=0;i
您不需要参数[]标记列表中的
公共标记吗?我不明白你想做什么,我想把结构“读者”从C++到C++。但是,我已经将封送处理作为-->for(int j=0;j<1000;j++){readers.tag_list[j]=marshal.AllocHGlobal(marshal.SizeOf(tag_list[j]);marshal.StructureToPtr(tag_list[j],readers.tag_list[j],false);}另一端的声明是什么样子的呢?它的-->类读取器{public:TAG_IN_PARAM*TAG_list;//数组大小必须是tot_tags};您的
标记列表
字段,是固定大小的数组吗?谢谢David。但是我不需要将参数*标记列表中的标记更改为参数标记列表中的标记[1000]。现在有没有其他可能?就像C端的任何东西一样,让它在参数标签列表中为标签工作。请再次阅读答案。我不是告诉你改变C++代码。我并不是告诉您在参数标记列表[1000]
中更改为标记。我告诉您,您当前的C代码与参数标记列表[1000]中的标记匹配。您需要更改C++代码以匹配C++代码。对不起,我读得很正确。但我尝试了不同的方法,但仍然无法得到正确的值。只有第一个目标是好的。在下一个循环中,它以垃圾的形式出现。两个结构之间似乎存在一些大小问题。对不起,我记不清封送拆收器是如何处理结构内部的数组的。我更新了答案。我希望这有帮助!谢谢大卫提供的信息。我尝试了您的代码,但它引发了一个错误“mscorlib.dll中发生了未处理的'System.ArgumentException'类型的异常附加信息:对象包含非原始或不可删除的数据。”;
TAG_IN_PARAM[] tag_list = ...;
int structSize = Marshal.SizeOf(typeof(TAG_IN_PARAM));
r.tag_list = Marshal.AllocHGlobal(tag_list.Length*structSize);
IntPtr ptr = r.tag_list;
for (int i = 0; i < tag_list.Length; i++)
{
    Marshal.StructureToPtr(tag_list[i], ptr, false);
    ptr += structSize;
    // or on older versions of .net without arithmetic support on IntPtr
    // ptr = (IntPtr) (long)ptr + structSize;
}
// call function passing r
Marshal.FreeHGlobal(r.tag_list);