如何解决CGO:将 Go 字节数组转换为 C char* 并返回,字节数组中出现空终止符
简要背景:
我正在尝试为我的公司从 uint64->[]byte 创建一个 cgo 缓存。由于 []byte 被视为指针,Golang 的 map[uint64][]byte
由于垃圾收集器而导致相当大的延迟。因此,我想尝试使用 CGO 来避免这个问题。我目前正在实施一个 C++ unordered_map<unsigned long long,char*>
来处理这个问题。我设法让 C++ 包装器工作,但我面临一个主要问题。
目前,我正在使用
转换我的 Go 字节数组b := []byte{1,3,32,2,2}
str := C.String(b)
bb := []byte(C.GoString(str))
然而,事实证明我的 bb 是 []byte{1}
。字节数组中的 0 被视为 '/0'
,因此缩短了字符串。此外,当我使用
delete (map->find(key))->second
。我怀疑这是因为第一个 '/0'
之后的字符没有被释放。
我不知道如何做到这一点。就我个人而言,我是 CGO 的新手,所以在此项目之前我从未使用过它,因此我们将不胜感激。
解决方法
有两个问题:
-
使用
C.CBytes
,而不是C.CString
。在使用
cgo
之前,请完整阅读 this。 -
分配(
C.C*
和C.CString
这样做)的C.CBytes
函数在内部从malloc()
库中的链接调用libc
以获取目标内存块,并且您应该最终对它们调用C.Free()
(它调用libc
的free()
),如文档所述。AFAIK,C++编译器绝对没有义务使用
libc
的{{1}}和malloc()
来实现free()
和new
,所以调用{{ 1}} 在delete
函数的结果上肯定会导致灾难。解决这个问题的最简单方法,IMO,是从 C++ 端导出一个“构造函数”函数:类似
delete
...这将 1) 使用最适合 C++ 的任何方法分配长度为
C.C*
的内存块; 2) 将extern "C" { char* clone(char *src,size_t len); }
字节从len
复制到它; 3) 退货。然后您可以从 Go 端调用它 - 作为
len
并称它为一天:C++ 端可以自由地对结果调用src
。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。