一个客户要使用C#调用我们用C++开发的一个动态链接库,本来我没有C#的开发经验,就随便写了一个例程。以为很简单就可以搞定,没想到客户开发的过程中遇到了不少问题,最困难的就是用C#调用C++接口中的自定义数据类型的数组作为参数的情况了,解决完问题,总结如下。

DLL接口定义如下:

这里pDinCanInfo是有3个DINCAN_INFO元素数组的指针,其中ReadDinCanInfo中的pDinCanInfo需要作为out参数,WriteDinCanInfo需要作为In参数,这两种使用形式在C#中的调用方法也不太一样。

C#调用ReadDinCanInfo关键代码如下:

DINCAN_INFO DinInfo = new DINCAN_INFO();

int size = Marshal.SizeOf(typeof(DINCAN_INFO)) * 3;

byte[] bytes = new byte[size];

IntPtr pBuff = Marshal.AllocHGlobal(size);

DINCAN_INFO[] pDInfo = new DINCAN_INFO[3];

if (ReadDinCanInfo(1811422176, pBuff)) //参数一为卡内码

{

for (int i = 0; i < 3; ++i)

{

IntPtr pPonitor = new IntPtr(pBuff.ToInt64() + Marshal.SizeOf(typeof(DINCAN_INFO)) * i);

pDInfo[i] = (DINCAN_INFO)Marshal.PtrToStructure(pPonitor, typeof(DINCAN_INFO));

MessageBox.Show("订餐日期:" + pDInfo[i].iYear + "-"+ pDInfo[i].iMonth + "-"+ pDInfo[i].iDay);

MessageBox.Show("订餐餐次:" + pDInfo[i].iMeal);

MessageBox.Show("是否取餐:" + pDInfo[i].bTaked);

}

Marshal.FreeHGlobal(pBuff);

MessageBox.Show("读取订餐信息成功");

}

C#调用WriteDinCanInfo关键代码如下:

DINCAN_INFO DinInfo = new DINCAN_INFO();

DinInfo.iYear =Convert.ToUInt32( DateTime.Now.Year);

DinInfo.iMonth = Convert.ToUInt32( DateTime.Now.Month);

DinInfo.iDay = Convert.ToUInt32( DateTime.Now.Day);

DinInfo.iType = 1;

DinInfo.iMeal = 1;

DinInfo.bTaked = false;

int size = Marshal.SizeOf(typeof(DINCAN_INFO)) * 3;

byte[] bytes = new byte[size];

IntPtr pBuff = Marshal.AllocHGlobal(size);

DINCAN_INFO[] pDInfo = new DINCAN_INFO[3];

long ptr = pBuff.ToInt64();

for (int i = 0; i < 3; ++i )

{

IntPtr RPtr = new IntPtr(ptr);

pDInfo[i] = new DINCAN_INFO();

pDInfo[i].iYear = Convert.ToUInt32(DateTime.Now.Year);

pDInfo[i].iMonth = Convert.ToUInt32(DateTime.Now.Month);

pDInfo[i].iDay = Convert.ToUInt32(DateTime.Now.Day);

pDInfo[i].iType = Convert.ToUInt32(i);

pDInfo[i].iMeal = Convert.ToUInt32(i);

pDInfo[i].bTaked = false;

Marshal.StructureToPtr(pDInfo[i], RPtr, false);

ptr += Marshal.SizeOf(typeof(DINCAN_INFO));

}

if (WriteDinCanInfo(1811422176, pBuff)) // 参数一为卡内码

{

MessageBox.Show("写入订餐信息成功");

}

代码看起来比较麻烦,要参考的抄以上代码了,主要思想就是申请一块内存,在申请的这块内存中构建数组对象,然后将这个内存地址作为pDinCanInfo进行调用。两个函数的区别就是如何将内存按定义的数据结构进行解析的区别。

C#调用C、C++结构体数组的方法总结的更多相关文章

  1. C#调用c++Dll 结构体数组指针的问题

    参考文章http://blog.csdn.net/jadeflute/article/details/5684687 但是这里面第一个方案我没有测试成功,第二个方案我感觉有点复杂. 然后自己写啦一个: ...

  2. C#调用C/C++动态库 封送结构体,结构体数组

    一. 结构体的传递 #define JNAAPI extern "C" __declspec(dllexport) // C方式导出函数 typedef struct { int ...

  3. C#调用C++DLL传递结构体数组的终极解决方案

    在项目开发时,要调用C++封装的DLL,普通的类型C#上一般都对应,只要用DllImport传入从DLL中引入函数就可以了.但是当传递的是结构体.结构体数组或者结构体指针的时候,就会发现C#上没有类型 ...

  4. 绝对好文C#调用C++DLL传递结构体数组的终极解决方案

    C#调用C++DLL传递结构体数组的终极解决方案 时间 2013-09-17 18:40:56 CSDN博客相似文章 (0) 原文  http://blog.csdn.net/xxdddail/art ...

  5. C#调用C/C++动态库 封送结构体,结构体数组

    因为实验室图像处理的算法都是在OpenCV下写的,还有就是导航的算法也是用C++写的,然后界面部分要求在C#下写,所以不管是Socket通信,还是调用OpenCV的DLL模块,都设计到了C#和C++数 ...

  6. C语言 结构体数组保存到二进制文件中

    在项目中我定义了一个结构体数组,头文件如下: C/C++ code   ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 ...

  7. NumPy-快速处理数据--ndarray对象--多维数组的存取、结构体数组存取、内存对齐、Numpy内存结构

    本文摘自<用Python做科学计算>,版权归原作者所有. 上一篇讲到:NumPy-快速处理数据--ndarray对象--数组的创建和存取 接下来接着介绍多维数组的存取.结构体数组存取.内存 ...

  8. C语言 结构体(嵌套结构体--结构体数组)

    //结构体--嵌套结构体和结构体数组 #define _CRT_SECURE_NO_WARNINGS #include <stdio.h> #include <stdlib.h> ...

  9. C#引用c++DLL结构体数组注意事项(数据发送与接收时)

    本文转载自:http://blog.csdn.net/lhs198541/article/details/7593045 最近做的项目,需要在C# 中调用C++ 写的DLL,因为C# 默认的编码方式是 ...

随机推荐

  1. MHA参数 转

    http://blog.csdn.net/wulantian/article/details/12503473 http://blog.csdn.net/wulantian/article/categ ...

  2. Google 推出全新的两步验证机制

    近日 Google 在官方的 Apps Updates 博客公布了全新的两步验证功能--Google 提示,新的功能通过与 Google App 联动,进一步将验证确认工作缩减到仅有两步,同时支持 A ...

  3. 关于在Android设置全局变量随时获取context

    最实在的办法就是继承Application,在里面设置全局变量,因为Application是android的应用入口,并且运行周期贯穿整个程序运行. import android.app.Applic ...

  4. #maven解决乱码问题

    <build>        <plugins>        <plugin>        <groupId>org.apache.maven.pl ...

  5. js兼容性问题

    javscript 浏览器兼容性问题: scrollTop = document.documentElement.scrollTop || document.body.scrollTop; scrol ...

  6. 【Android Api 翻译1】Android Texting(2)Testing Fundamentals 测试基础篇

    Testing Fundamentals The Android testing framework, an integral part of the development environment, ...

  7. iOS 下拉刷新 上拉加载实现原理

    1.下拉刷新 实现原理 if (scrollView.contentOffset.y < -100) { [UIView animateWithDuration:1.0 animations:^ ...

  8. Android下拉刷新-SwipeRefreshLayout,RecyclerView完全解析之下拉刷新与上拉加载SwipeRefreshLayout)

    SwipeRefrshLayout是Google官方更新的一个Widget,可以实现下拉刷新的效果.该控件集成自ViewGroup在support-v4兼容包下,不过我们需要升级supportlibr ...

  9. StdRandom.java

    /************************************************************************* * Compilation: javac StdR ...

  10. codeforces 613B B. Skills(枚举+二分+贪心)

    题目链接: B. Skills time limit per test 2 seconds memory limit per test 256 megabytes input standard inp ...