当前位置:网站首页>SWIG Tutorial "One"
SWIG Tutorial "One"
2022-08-10 14:54:00 【Akure Studio】
Swig《一》
Instruction file description
The most important conversion between different languages is the encapsulation of syntax between different languages,swigIt's used to do these things.And these fields are the guidanceswiginstructions to accomplish these operations
/* File : example.i */
%module example
%{
/* Put headers and other declarations here */
extern double My_variable;
extern int fact(int);
extern int my_mod(int n, int m);
%}
extern double My_variable;
extern int fact(int);
extern int my_mod(int n, int m);
module:指定swigmodule will be created
%module mymodule
%{
// Here is what is needed in the source code
#include "myheader.h"
%}
// Here is what is needed in the object code after conversion
// Now list ISO C/C++ declarations
int foo;
int bar(int x);
...
%{....%}
所有在%{....%}The content in between will be placed literallyswigin the created package file.This area is usually used to place someswigDefinitions or declarations that will not be generated,对应C/C++The wrapper is usually used to import header files
%+指令
大多数的swigInstructions are like this%开头的指令,The purpose is to reconcileCcan be distinguished well
默认情况下,swig是不会对includein the incoming header file#include进行展开的,除非你指定-includeall
%{
/* Include in the generated wrapper file */
typedef unsigned int size_t;
%}
/* Tell SWIG about it */
typedef unsigned int size_t;
Or
%inline %{
typedef unsigned int size_t;
%}
像C语言一样,swig中也能使用swigType redefinition
%include 引入头文件
使用%includeinstructions to importswig定义的头文件
%import引入头文件
If you just want to import the file using the macro definitions and types in the file can be usedimport
%import "foo.i"
预定义变量
To differentiate between different languages and to be able to differentiate in some guidance documents,siwgSome variables are predefined in advance
SWIG Always defined when SWIG is processing a file
SWIGIMPORTED Defined when SWIG is importing a file with %import
SWIG_VERSION Hexadecimal (binary-coded decimal) number containing SWIG version,
such as 0x010311 (corresponding to SWIG-1.3.11).
SWIGCSHARP Defined when using C#
SWIGD Defined when using D
SWIGGO Defined when using Go
SWIGGUILE Defined when using Guile
SWIGJAVA Defined when using Java
SWIGJAVASCRIPT Defined when using Javascript
SWIG_JAVASCRIPT_JSC Defined when using Javascript with -jsc
SWIG_JAVASCRIPT_V8 Defined when using Javascript with -v8 or -node
SWIGLUA Defined when using Lua
SWIGMZSCHEME Defined when using Mzscheme
SWIGOCAML Defined when using OCaml
SWIGOCTAVE Defined when using Octave
SWIGPERL Defined when using Perl
SWIGPHP Defined when using PHP (any version)
SWIGPHP7 Defined when using PHP7
SWIGPYTHON Defined when using Python
SWIGR Defined when using R
SWIGRUBY Defined when using Ruby
SWIGSCILAB Defined when using Scilab
SWIGTCL Defined when using Tcl
SWIGXML Defined when using XML
__LINE__ Current line number
__FILE__ Current file name
__STDC__ Defined to indicate ISO C
__cplusplus Defined when -c++ option used
SWIG_D_VERSION Unsigned integer target version when using D
SWIGGO_CGO Defined when using Go for cgo
SWIGGO_GCCGO Defined when using Go for gccgo
SWIGGO_INTGO_SIZE Size of the Go type int when using Go (32 or 64)
SWIGPYTHON_PY3 Defined when using Python with -py3
SWIGPYTHON_BUILTIN Defined when using Python with -builtin
SWIG_RUBY_AUTORENAME Defined when using Ruby with -autorename
Enhanced macro definitions
In order to better realize the encapsulation of the source code,swigProvides an enhanced macro definition directive, %define 和 %enddef
%define ARRAYHELPER(type, name)
%inline %{
type *new_ ## name (int nitems) {
return (type *) malloc(sizeof(type)*nitems);
}
void delete_ ## name(type *t) {
free(t);
}
type name ## _get(type *t, int index) {
return t[index];
}
void name ## _set(type *t, int index, type val) {
t[index] = val;
}
%}
%enddef
ARRAYHELPER(int, IntArray)
ARRAYHELPER(double, DoubleArray)
指令透传
正常情况下,in the function that needs to be encapsulated,swig会将#define进行处理,If you want the corresponding macro definition not to be preprocessed, you can do so#前面添加%来实现
%extend Foo {
void bar() {
%#ifdef DEBUG
printf("I'm in bar\n");
%#endif
}
}
指针处理(cpointer.i)
A pointer needs to be passed in some functions,But there may not be a concept of pointers in other functions,因此swigDeliberately provide a way to encapsulate pointers%pointer_functions(int**, intp);的含义就是,Provides a function wrapper,This function encapsulates what can be executed by creating a pointer,The meaning here is to apply for a pieceint大小的内存并返回
%include "cpointer.i"
/* Create some functions for working with "int *" */
%pointer_functions(int, intp);
/* A function that uses an "int *" */
void add(int x, int y, int *result);
If you want to deal with complex or custom onesclass可以使用%pointer_class(int, intp);来进行处理,相比之下使用pointer_classIt is more convenient and convenient for garbage collection to manage the content of the application as an object
%module example
%include "cpointer.i"
/* Wrap a class interface around an "int *" */
%pointer_class(int, intp);
/* A function that uses an "int *" */
void add(int x, int y, int *result);
类型转换
When some types need to be converted, type conversion instructions can be usedpointer_cast,The first parameter is the current type,The second parameter is the parameter after conversion,The third is the encapsulated function name
%include "cpointer.i"
%pointer_cast(int *, unsigned int *, int_to_uint);
数组(carrays.i)
Import header files before use,指令方式%array_functions(type, name)
%include "carrays.i"
%array_functions(double, doubleArray);
void print_array(double x[10]);
同样,这里可以使用array_classto encapsulate an array of custom types
%module example
%include "carrays.i"
%array_class(double, doubleArray);
void print_array(double x[10]);
内存管理(cmalloc.i)
swigProvides modules for memory management,Use these commands to correctmalloc,calloc,realloc和free进行封装,The specific command form is as follows
%malloc(type [, name=type])
%calloc(type [, name=type])
%realloc(type [, name=type])
%free(type [, name=type])
%sizeof(type [, name=type])
%allocators(type [, name=type])
// SWIG interface
%include "cmalloc.i"
%malloc(int);
%free(int);
%malloc(int *, intp);
%free(int *, intp);
%allocators(double);
CType data encapsulation(cdata.i)
引入cdata.i模块后,will be provided in the wrapper codeCdata*, memmove()The encapsulation of other functions is used to apply and releaseC类型数据.
The following methods can be used if the type is known
%include "carrays.i"
%include "cdata.i"
%array_class(int, intArray);
If the type is an unknown type,就需要借助cdata指令了%cdata(type [, name=type])
内存释放
当一个CThe function in allocates a block of memory,并返回一个char *类型时,swigIt may not be possible to determine whether the corresponding content needs to be released,新版本的swigIt has been able to make self-judgment on simple source code,If the source code applies for a piece of memory but does not release it,在目标代码中swigBy default, functions that are freed are encapsulated,比如go中没有char * 类型的数据,在进行封装时swig会创建一个string类型数据,并将原有的char *内容赋值到string对象中,Then the object is automatically released according to the judgment,But when the function is complex, it needs to be specified manually,Commands are required at this time%newobject来进行指定
%newobject foo;
char *foo() {
char *result = (char *) malloc(sizeof(char));
return result;
}
STL的支持
对于STLSupport is a gradual process,目前已经支持的STL如下所示
使用STLBe careful when throwing exceptions,Appropriate encapsulation of possible exceptions is usually required when using them
%module example
%include "std_vector.i"
%typemap(throws) std::out_of_range {
// custom exception handler
}
%template(VectInt) std::vector<int>;
A more general approach is to wrap all exceptions
%include "exception.i"
%exception {
try {
$action
} catch (const std::exception& e) {
SWIG_exception(SWIG_RuntimeError, e.what());
}
}
SWIG_exception(int code, const char *message)Used to throw exceptions in the encapsulated target function code,Common error types are as follows
SWIG_MemoryError
SWIG_IOError
SWIG_RuntimeError
SWIG_IndexError
SWIG_TypeError
SWIG_DivisionByZero
SWIG_OverflowError
SWIG_SyntaxError
SWIG_ValueError
SWIG_SystemError
参数类型(typemaps.i)
If there is the following function,如果不对result进行声明,那么swigIt will only be processed in the form of a pointerresult参数,If you pass in an empty one directlyresultThe bottom layer will crash directly on assignment
void add(double a, double b, double *result) {
*result = a + b;
}
因此需要使用%applycommand to guide the parameters,Add a directive to the parameter%apply double *OUTPUT之后,swig已经知道resultis a parameter that needs to be output,因此会对resultthe legitimacy of the test,If it is an outlier(null)那么直接抛出异常
%include "typemaps.i"
%apply double *OUTPUT { double *result };
%inline %{
extern void add(double a, double b, double *result);
extern void Sum(double a, double b, double *result);
%}
If there are multiple parameters to output,Just add it backwards in the form of a list
%include "typemaps.i"
%apply int *OUTPUT { int *width, int *height };
// Returns a pair (width, height)
void getwinsize(int winid, int *width, int *height);
If you think it is troublesome to write a long series of instructions every time, you can simplify the above process into the following way,Directly replace the corresponding parameters with OUTPUT即可
%include "typemaps.i"
%inline %{
extern void add(double a, double b, double *OUTPUT);
%}
另外需要注意的是,一旦使用%apply进行声明,那么后续所有的double *resultparameters are processed,如果想取消%applyThe role needs to be declared as follows:
%clear double *result; // Remove all typemaps for double *result
Our more commonly used form is :
入参
int *INPUT
short *INPUT
long *INPUT
unsigned int *INPUT
unsigned short *INPUT
unsigned long *INPUT
double *INPUT
float *INPUT
出参
int *OUTPUT
short *OUTPUT
long *OUTPUT
unsigned int *OUTPUT
unsigned short *OUTPUT
unsigned long *OUTPUT
double *OUTPUT
float *OUTPUT
That is, the input and the output
int *INOUT
short *INOUT
long *INOUT
unsigned int *INOUT
unsigned short *INOUT
unsigned long *INOUT
double *INOUT
float *INOUT
the above writing,directly on the parameter,等同使用applyof the following command form
// Make double *result an output value
%apply double *OUTPUT { double *result };
// Make Int32 *in an input value
%apply int *INPUT { int32 *in };
// Make long *x inout
%apply long *INOUT {long *x};
...
%clear double *result;
%clear Int32 *in, long *x;
边栏推荐
- PyTorch multi-machine multi-card training: DDP combat and skills
- 【MindSpore易点通机器人-02】设计与技术选型
- MQTT服务器搭建
- Parallels 将扩展桌面平台产品,以进一步改善在 Mac 上运行 Windows 的用户体验和工作效率
- 阿里五位MySQL封神大佬耗17个月总结出53章性能优化法则
- 强意识 压责任 安全培训筑牢生产屏障
- In the second half of 2012 system architecture designers afternoon paper II
- List集合
- MySQL Principle and Optimization: Update Optimization
- Summary of Force Buckle Solution 640 - Solving Equations
猜你喜欢
随机推荐
领域驱动模型设计与微服务架构落地-从项目去剖析领域驱动
Appium进行APP自动化测试
SWIG教程《一》
高薪程序员&面试题精讲系列135之你对分布式是怎么理解的?CAP理论你知道吗?
关于已拦截跨源请求CORS 头缺少 ‘Access-Control-Allow-Origin‘问题解决
【剑指offer】---数组中的重复数字
每个月工资表在数据库如何存储?求一个设计思路
BCG库简介
力扣解法汇总640-求解方程
2022-08-10日报: Swin Transformer作者曹越加入智源,开展视觉基础模型研究
2022年网络安全培训火了,缺口达95%,揭开网络安全岗位神秘面纱
【语义分割】DeepLab系列
PyTorch multi-machine multi-card training: DDP combat and skills
解题-->在线OJ(十九)
快速了解大端模式和小端模式
E. Cross Swapping(并查集变形/好题)
使用Uiautomator2进行APP自动化测试
Send a post request at the front desk can't get the data
MySQL - storage engine for databases
Boss raises salary!Look at my WPF Loading!!!