在以前的認(rèn)識(shí)中,不同語言的相互交流大概只能靠網(wǎng)絡(luò)依靠json來傳遞數(shù)據(jù)。下面來了解一個(gè)新的方法:嵌入式開發(fā)
首先巴拉巴拉一下C++吧
- C++ 是一種靜態(tài)類型的、編譯式的、通用的、大小寫敏感的、不規(guī)則的編程語言,支持過程化編程、面向?qū)ο缶幊毯头盒途幊?/strong>
這是C++簡介上對(duì)C++的定義。(以前一直以為c++是面向過程的語言)
- C++ 被認(rèn)為是一種中級(jí)語言,它綜合了高級(jí)語言和低級(jí)語言的特點(diǎn)。
- C++ 進(jìn)一步擴(kuò)充和完善了 C 語言,最初命名為帶類的C,后來在 1983 年更名為 C++。
- C++ 是 C 的一個(gè)超集,事實(shí)上,任何合法的 C 程序都是合法的 C++ 程序。
- 最重要的是c++沒有自動(dòng)垃圾回收機(jī)制
golang調(diào)用C++
1.給電腦安裝MinGW(即gcc)
- 下載
在網(wǎng)上查好多人都沒有說這一步,沒有安裝gcc會(huì)報(bào)以下錯(cuò),沒接觸的人一下就買有眉目了
"gcc": executable file not found in %PATH%
因?yàn)檫@個(gè)公司是美國企業(yè),下載這個(gè)東西不是很容易,找了好久發(fā)現(xiàn)一個(gè)離線的包,點(diǎn)擊獲取
- 環(huán)境變量配置
2.上代碼
- 外部調(diào)用
foo.c
里面有c調(diào)用了go的代碼
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
typedef UINT_PTR(__stdcall* GIRL_PROC)(int);
typedef UINT_PTR(__cdecl* GIRL_PROC_CDECL)(int);
UINT_PTR Func1(int n, GIRL_PROC gp)
{
printf("我是在go語言中嵌套的c++語言\n");
if (gp == NULL)
{
return 0;
}
return (*gp)(n);//這里其實(shí)是c調(diào)用了go的代碼
}
UINT_PTR Func2(int n, GIRL_PROC_CDECL gp)
{
if (gp == NULL)
{
return 0;
}
return (*gp)(n);
}
main.go
里面有g(shù)o調(diào)用了c的代碼
package main
import (
"fmt"
"syscall"
"unsafe"
)
// #include <stdio.h>
// #include <stdlib.h>
// #include "foo.c"
import "C"
func GirlProc(n int32) int32 {
return n + 97
}
func main() {
gp := syscall.NewCallback(GirlProc)
gop := (*[0]byte)(unsafe.Pointer(gp))
var t C.UINT_PTR = C.Func1(C.int(29), gop)//這里go調(diào)用了c的代碼
fmt.Println("t",t) // 126
}
- 內(nèi)部調(diào)用
內(nèi)部調(diào)用和外部調(diào)用有點(diǎn)不同就是內(nèi)部調(diào)用將c語言卸載了go語言里面
package main
/*
#include <stdio.h>
#include <stdlib.h>
char ch = 'M';
unsigned char uch = 253;
short st = 233;
int i = 257;
long lt = 11112222;
float f = 3.14;
double db = 3.15;
void * p;
char *str = "const string";
char str1[64] = "char array";
void printI(void *i)
{
printf("print i = %d\n", (*(int *)i));
}
struct ImgInfo {
char *imgPath;
int format;
unsigned int width;
unsigned int height;
};
void printStruct(struct ImgInfo *imgInfo)
{
if(!imgInfo) {
fprintf(stderr, "imgInfo is null\n");
return ;
}
fprintf(stdout, "imgPath = %s\n", imgInfo->imgPath);
fprintf(stdout, "format = %d\n", imgInfo->format);
fprintf(stdout, "width = %d\n", imgInfo->width);
}
*/
import "C"
import (
"fmt"
"reflect"
"unsafe"
)
func main() {
fmt.Println("----------------Go to C---------------")
fmt.Println(C.char('Y'))
fmt.Printf("%c\n", C.char('Y'))
fmt.Println(C.uchar('C'))
fmt.Println(C.short(254))
fmt.Println(C.long(11112222))
var goi int = 2
// unsafe.Pointer --> void *
cpi := unsafe.Pointer(&goi)
C.printI(cpi)
fmt.Println("----------------C to Go---------------")
fmt.Println(C.ch)
fmt.Println(C.uch)
fmt.Println(C.st)
fmt.Println(C.i)
fmt.Println(C.lt)
f := float32(C.f)
fmt.Println(reflect.TypeOf(f))
fmt.Println(C.f)
db := float64(C.db)
fmt.Println(reflect.TypeOf(db))
fmt.Println(C.db)
// 區(qū)別常量字符串和char數(shù)組,轉(zhuǎn)換成Go類型不一樣
str := C.GoString(C.str)
fmt.Println(str)
fmt.Println("reflect.TypeOf(C.str1)",reflect.TypeOf(C.str1))
//var charray []byte
//for i := range C.str1 {
// if C.str1[i] != 0 {
// charray = append(charray, byte(C.str1[i]))
// }
//}
//
//fmt.Println(charray)
//fmt.Println(string(charray))
for i := 0; i < 10; i++ {
imgInfo := C.struct_ImgInfo{imgPath: C.CString("../images/xx.jpg"), format: 0, width: 500, height: 400}
defer C.free(unsafe.Pointer(imgInfo.imgPath))
C.printStruct(&imgInfo)
}
fmt.Println("----------------C Print----------------")
}