当前位置: 首页 > 知识库问答 >
问题:

如何将字符串从 JSON 返回到 C 调用方(高浪 CGO)?

曾阳飙
2023-03-14

我正在尝试在Go中开发一个将由C程序调用的例程。Go如下所示:

package main

import (
    "C"
    "encoding/json"
    "log"
)

type keydata struct {
    Key   string `json:"key"`
    Error string `json:"Error"`
}

func lookupKey() string {
//simplified to remove the call to web service
    body := "{\"key\": \"blahblah\", \"Error\": \"\"}"

    k := keydata{}
    err := json.Unmarshal([]byte(body), &k)
    if err != nil {
        log.Fatal(err)
    }

    return k.Key
}

//export GetKey
func GetKey() string {
    theKey := lookupKey()
    return theKey
}

func main() {}

如果我用一些硬编码的值替换return k.Key语句,则一切正常,C或C可以调用导出的GetKey函数。当我尝试从k.Key返回解码的JSON字符串,甚至只是从名为body的变量返回字符串时,我收到一个错误:

运行时错误:cgo结果具有go指针Go routine 17[正在运行,锁定到线程]

我按如下方式构建它:

去构建 -构建模式 =c-归档示例.go

C 的构造如下:

g-pthread测试。cpp就是一个例子。a-o测试

我错过了什么才能在不引发恐慌错误的情况下完成这项工作?我正在四处寻找答案,但尚未解决这个问题。

@吉姆布

我当然可以返回C.CString char数组并使其工作-谢谢!我只是想了解为什么它在返回硬编码字符串时有效,而不是在我发布的示例中。

谢谢你们的时间和解释。

共有2个答案

孔宇
2023-03-14

您需要使用<code>C。CString将Go字符串转换为C字符串的原始指针。注意,C字符串不是垃圾收集的,必须在程序的其他地方释放。

这将使返回类型*C.char,它应该对C可见为char数组。返回缓冲区长度也是您的责任(是否编写单独的函数或C结构取决于您)。

景成和
2023-03-14

不能将 Go 字符串返回到 C 函数。如果需要 C 字符串,可以使用 C.CString 函数创建一个字符串并返回 *C.char

//export GetKey
func GetKey() *C.char {
    theKey := lookupKey()
    return C.CString(theKey)
}

这个函数的返回值必须在C代码中显式释放。

如果释放分配的缓冲区不方便,通常会填充调用者提供的缓冲区:

func GetKey(buff *C.char, n int) int

如果您可以分配内存,但不想处理C字符串,则可以将缓冲区插入指针并返回大小。

func GetKey(buff **C.char) int
 类似资料:
  • 问题内容: 为了使进度报告过程更加可靠,并使它与请求/响应脱钩,我正在Windows Service中执行处理,并将预期的响应持久化到文件中。当客户端开始轮询更新时,其目的是控制器以JSON字符串形式返回文件的内容(无论它们是什么)。 该文件的内容已预序列化为JSON。这是为了确保在响应过程中没有任何阻碍。无需进行任何处理(只需将文件内容读入字符串并返回)即可获得响应。 我最初虽然很简单,但事实并

  • 问题内容: 当我尝试读取add函数的返回值时,它什么也不返回。 而且,当我尝试将消息放入变量并从外部返回时,也给出空值。 问题答案: 简单地说, 您不能 。要从此类函数获取值,必须使用回调: 然后,您将使用如下功能:

  • 本文向大家介绍C#枚举到字符串并返回,包括了C#枚举到字符串并返回的使用技巧和注意事项,需要的朋友参考一下 示例            

  • 问题内容: 在某些情况下,我具有NewtonSoft JSON.NET,在控制器中,我只是从控制器中返回Jobject,一切都很好。 但是我遇到的情况是,我从另一个服务中获取了一些原始JSON,并且需要从我的webAPI中返回它。在这种情况下,我不能使用NewtonSOft,但是如果可以的话,我将根据字符串创建一个JOBJECT(这似乎是不必要的处理开销),并返回该值,这一切对世界都很好。 但是,

  • 在下面的程序中,我将一个字符串值作为参数传递给方法print(string),该方法是静态的,返回string。虽然我没有得到错误,但我没有得到输出。

  • 问题内容: 我正在开发一个使用JSON进行服务器通信的Android应用,当我尝试解析json文件时遇到了一个奇怪的问题。 这是我来自服务器的json 我通过调用地址Json-object 获得City的价值。对于这种情况,我期望为空(这是optString的意思吗?),但实际上它包含字符串“ null”。因此,进一步的null或isEmpty- checks将返回false,因为String包含