這是一個建立於 的文章,其中的資訊可能已經有所發展或是發生改變。
1. 在Go中引用C代碼很簡單, 在 import "C"前用注釋引入標準的C代碼, 然後使用C.xxx的偽包引用C代碼空間的標識符即可. 需要注意, import"C"是偽package,不能與其他package一塊定義為import (..."C"...)
2. 在Go中引用C代碼必須手工釋放C代碼對象. 釋放方法為C.free(unsafe.Pointer(xxx)), 這也要求C程式碼封裝含#include <stdlib.h>
3. 必須深入理解下述:
(1) Cgo recognizes this comment above import "C" statement.
(2) Any lines starting with #cgo followed by a space character are removed; these become directives for cgo.
(3) The remaining lines are used as a header when compiling the C parts of the package.
------------------------------------
通俗記憶:
(1)cgo能夠識別import "C" 語句的注釋.
(2)#cgo行用作cgo指令
(3)其他行用作C標頭檔
第(2)點很關鍵! 容易導致重複定義.
實踐問題:
程式碼片段1:
-------------------------------
package main
/*
#include <stdlib.h>
#include "prints.h"
*/
import "C"
import (
"fmt"
"unsafe"
)
func main() {
msg := "this is a test for"
cmsg := C.CString(msg)
defer C.free(unsafe.Pointer(cmsg))
C.prints(cmsg)
fmt.Println("done...")
}
//在main包中引入C代碼, 使用go run xxx.go會報錯. 先go build-->再執行, 無錯誤.
-------------------------------------
上面解決辦法,是定義wrapper把C代碼封裝起來. 例如:
package myc
/*
#include <stdlib.h>
#include "prints.h"
*/
import "C"
import "unsafe"
func Cprints(msg string) {
cmsg := C.CString(msg)
defer C.free(unsafe.Pointer(cmsg))
C.prints(cmsg)
}
-------------------------------------------------