golang繼承swig導出的c++基類
項目原來使用c++實現了底層邏輯,爲了方便業務方使用,現在需要支持golang語言的sdk。經過調研瞭解到swig可以將C++導出接口類供其他腳本語言或者高級編程語言調用,本文基於swig實現C++類導出golang的接口類,然後在golang中利用struct實現繼承。
爲了更好地演示,本文利用簡單的C++類進行描述。
首先定義C++的基類和一個輔助類,後面go會利用struct派生於基類BaseCase,輔助類用於調用派生類的函數。
// BaseCase.h
#include <string>
#include <iostream>
using namespace std;
class BaseCase
{
public:
BaseCase() {}
virtual ~BaseCase() {}
BaseCase(const BaseCase& rhs) {
m_caseName = rhs.m_caseName;
}
virtual void Run() {cout << "run the case in baseCase class." << endl;}
public:
string m_caseName;
};
class CaseRunner
{
public:
BaseCase* _baseCase_;
public:
CaseRunner():_baseCase_(0) {}
void RegisterCase(BaseCase *bc) {_baseCase_ = bc;}
void run() {if (_baseCase_) _baseCase_->Run();}
};
編寫swig.i文件
// swig.i
%module(directors="1") baseCase
%{
#include "BaseCase.h"
%}
%include "std_string.i"
%include "std_map.i"
%feature("director") BaseCase;
%include "BaseCase.h"
然後利用swig命令行將導出BaseCase和CaseRunner的Golang接口類
// swig command line
swig -go -cgo -intgosize 64 -c++ swig.i
執行完上面個的命令之後,會生成對應的swig_wrap.cxx,swig_wrap.h,baseCase.go
然後編寫test.go文件
package main
import (
"fmt"
. "baseCase"
)
type TestCase1Class interface {
BaseCase
deleteBaseCase()
IsTestCase1Class()
}
type testCase1Class struct {
BaseCase // 這個是swig導出來的interface接口
}
func (caseClass_ *testCase1Class) IsTestCase1Class() {}
func (caseClass_ *testCase1Class) deleteBaseCase() {
DeleteDirectorBaseCase(caseClass_.BaseCase)
}
type TestClass struct {
p BaseCase
}
func NewGoTestCase1Class() TestCase1Class {
om := &TestClass{}
p := NewDirectorBaseCase(om)
om.p = p
return &testCase1Class{BaseCase: p}
}
func (caseClass_ *TestClass) Run() {
fmt.Println("start to run caseClass ...")
caseClass_.case1()
caseClass_.case2()
}
// case1
func (caseClass_ *TestClass) case1() {
fmt.Println("run caseClass 1")
}
// case2
func (caseClass_ *TestClass) case2() {
fmt.Println("run caseClass 2")
}
func main() {
goCase := NewGoTestCase1Class()
caseRuner := NewCaseRunner()
caseRuner.RegisterCase(goCase)
caseRuner.Run()
return
}
執行打包命令,即可以編譯一個test的可執行文件
>> go build test.go
>> ./test
start to run caseClass ...
run caseClass 1
run caseClass 2