c++和c#传递字符串问题

alexsun6 2016-10-12 09:37:12
我要把c++的一个dll中的字符串通过参数传递给c#主程序。
c++接口定义:
extern "C" __declspec(dllexport)bool __stdcall GetError(char** sErrorStr, ERROR_ENUM* nError);

其中sErrorStr就是我要的字符串。

c#接口定义:

[DllImport(DllName)]
public extern static bool GetError(ref string sErrorStr, ref ERROR_ENUM nError);

但是调用此函数时程序崩溃,错误信息:尝试读取或写入受保护的内存。

是这两个接口转换定义有问题吗?
...全文
883 10 打赏 收藏 转发到动态 举报
写回复
用AI写文章
10 条回复
切换为时间正序
请发表友善的回复…
发表回复
Forty2 2016-10-12
  • 打赏
  • 举报
回复 1
引用 6 楼 alexsun6 的回复:
... 我是要C++传递string给c#使用,不是c#发参数给c++。
C++里,字符串要占用内存的。 C++创建字符串,并传给C#,就会造成内存泄露(因为C#不知道C++如何创建,也就不知道如何销毁)。 因此,通常的做法(甚至是C++互相调用的惯例),是 1、调用者(这里是C#)准备好一段内存缓冲区(这里是StringBuilder); 2、被调用者C++把字符串内容,填充到指定缓冲区去; 3、调用者从缓冲区能得到结果,也知道如何清理缓冲(C#自己会用垃圾回收),没有内存泄露问题。
alexsun6 2016-10-12
  • 打赏
  • 举报
回复
引用 7 楼 Libby1984 的回复:
[quote=引用 4 楼 alexsun6 的回复:] [quote=引用 3 楼 Libby1984 的回复:] 不需要ref,因为字符串本来就是引用传递,还有c++中的字符串应该是char* 类型的,不是char** ,你那是指针的指针,一个*就够了。
用char**因为下面还有一层,是从那一层传递的值,ref是因为string是从c++传递给c#,不是c#发参数下去。[/quote] 不明白你说的上一层是什么,但是你C#代码中用的是ref string sErrorStr,那么与之对应的就赢是char* sErrorStr,否则数据的类型就不对。cahr**是指向一个地址,也就是一个整数,而非一个字符串。[/quote] 我要是用char**崩溃,但是崩溃时的参数值是我要的,如果用char*,上层根本得不到这个传递的string。
alexsun6 2016-10-12
  • 打赏
  • 举报
回复
忘记说一点, public extern static bool GetError(ref string sErrorStr, ref ERROR_ENUM nError); 传递的字符串sErrorStr是c++传递给c#使用,并不是c#发送参数给c++。
  • 打赏
  • 举报
回复
引用 4 楼 alexsun6 的回复:
[quote=引用 3 楼 Libby1984 的回复:] 不需要ref,因为字符串本来就是引用传递,还有c++中的字符串应该是char* 类型的,不是char** ,你那是指针的指针,一个*就够了。
用char**因为下面还有一层,是从那一层传递的值,ref是因为string是从c++传递给c#,不是c#发参数下去。[/quote] 不明白你说的上一层是什么,但是你C#代码中用的是ref string sErrorStr,那么与之对应的就赢是char* sErrorStr,否则数据的类型就不对。cahr**是指向一个地址,也就是一个整数,而非一个字符串。
alexsun6 2016-10-12
  • 打赏
  • 举报
回复
引用 2 楼 Forty2 的回复:
改成: ERROR_ENUM GetError(char* sErrorStr, int& sErrorStrLength); [DllImport(DllName)] public extern static ERROR_ENUM GetError(StringBuilder, ref int sbLength);
我是要C++传递string给c#使用,不是c#发参数给c++。
alexsun6 2016-10-12
  • 打赏
  • 举报
回复
引用 1 楼 stherix 的回复:
传递字符串 c dll里面用 char* c#用StringBuilder来引用 不需要ref
我要c++传递string给c#,不是c#发参数给c++。
alexsun6 2016-10-12
  • 打赏
  • 举报
回复
引用 3 楼 Libby1984 的回复:
不需要ref,因为字符串本来就是引用传递,还有c++中的字符串应该是char* 类型的,不是char** ,你那是指针的指针,一个*就够了。
用char**因为下面还有一层,是从那一层传递的值,ref是因为string是从c++传递给c#,不是c#发参数下去。
  • 打赏
  • 举报
回复
不需要ref,因为字符串本来就是引用传递,还有c++中的字符串应该是char* 类型的,不是char** ,你那是指针的指针,一个*就够了。
Forty2 2016-10-12
  • 打赏
  • 举报
回复
改成: ERROR_ENUM GetError(char* sErrorStr, int& sErrorStrLength); [DllImport(DllName)] public extern static ERROR_ENUM GetError(StringBuilder, ref int sbLength);
stherix 2016-10-12
  • 打赏
  • 举报
回复
传递字符串 c dll里面用 char* c#用StringBuilder来引用 不需要ref

111,129

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Creator Browser
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧