linux c 调用python_在Python(linux)中调用复杂的C ++函数

我在C ++源代码中有一些函数,声明如下:

extern"C" {

int32_t comp_ip_long(const std::vector& in, std::vector& out);

}

C ++代码被编译成xxx.so(linux共享对象),我想在Python中调用该函数。 请注意,我无法修改C ++代码,因此像boost::python这样的东西是不可访问的。

我试过ctypes.CDLL,但我不知道如何将复杂的参数传递给xxx.so?

PS:

我给了一个带有一些函数的.so(带有上面的参数类型,但函数名称未知),函数名和参数由用户输入。

从长远来看,更多的工作但也许值得使用Boost.Python

从boost文档中获取的示例:

遵循C / C ++传统,让我们从"你好,世界"开始吧。一个C ++函数:

char const* greet()

{

return"hello, world";

}

可以通过编写Boost.Python包装器来暴露给Python:

#include

BOOST_PYTHON_MODULE(hello_ext)

{

using namespace boost::python;

def("greet", greet);

}

而已。我们完成了。我们现在可以将其构建为共享库。现在可以看到生成的DLL。这是一个Python会话示例:

>>> import hello_ext

>>> print hello_ext.greet()

hello, world

你不能从ctypes调用它,你至少需要扭曲C中的函数,所以你可以从Python调用它。

我不知道你的函数的细节,但是例如,如果你有这样的C ++代码:

#include

class Foo {

int bar;

public:

Foo(int bar) : bar(bar) {}

int getBar() const {

return bar;

}

void setBar(int bar) {

this->bar = bar;

}

void doSomething() const {

std::cout << bar << std::endl;

}

};

你可以这样扭曲:

// previous code here +

#define CAST_FOO(x) (static_cast(x))

#ifndef FOO_DEBUG

extern"C" {

#endif

void* foo_new(int bar) {

return static_cast(new Foo(bar));

}

int foo_get_bar(void *foo) {

return CAST_FOO(foo)->getBar();

}

void foo_set_bar(void *foo, int bar) {

CAST_FOO(foo)->setBar(bar);

}

void foo_do_something(void* foo) {

CAST_FOO(foo)->doSomething();

}

void foo_destroy(void* foo) {

delete CAST_FOO(foo);

}

#ifndef FOO_DEBUG

};

#endif

#ifdef FOO_DEBUG

int main(int argc, char **argv) {

void* foo = foo_new(10);

foo_do_something(foo);

foo_set_bar(foo, 20);

foo_do_something(foo);

foo_destroy(foo);

return 0;

}

#endif

现在它应该可以从ctypes调用,也可以从C调用。

$ g++ -Wall foo.cpp -DFOO_DEBUG

$ ./a.out

10

20

$ g++ -Wall foo.cpp -shared -o foo.so

$ python

>>> from ctypes import *

>>>

>>> so = cdll.LoadLibrary('foo.so')

>>> foo = so.foo_new(10)

>>>

>>> so.foo_do_something(foo)

10

>>> so.foo_set_bar(foo, 20)

>>> so.foo_do_something(foo)

20

>>> so.foo_destroy(foo)

>>>

我相信你需要声明为extern"C"的辅助粘合函数来构造(即初始化)并填充你的std::vector并从Python调用这些辅助函数。

也许

typedef std::vector columnvect_t;

extern"C" columnvect_t *new_vect()

{ return new columnvect_t; };

extern"C" void del_vect(columnvect_t*vec)

{ delete vec; };

extern"C" void pushback_vect(columnvect_t* vec, EachColumn* col)

{ vec->push_back(*col); };

同样适合你的EachColumn课程。

也许你需要制作一个链接到C ++库的胶水库和Python的dlopen -ed

基本上,Python比C ++友好更友好(因此你需要使C ++的胶水代码感觉像C的Python)。注意没有C ++异常抛出Python解释器(所以在你的粘合函数中捕获所有这些)

如果C或C ++代码很大,您可以考虑自定义GCC,以帮助生成这样的粘合代码,无论是使用MELT还是使用D.Malcom的GCC python插件。但这需要时间。

您仍然需要添加C ++代码。 实际上功能名称是由其他人提供的,我根本不知道它。

在 HTML ,按钮可以使用 `<button>` 标签来创建。要在按钮调用 Python 函数,你需要使用 JavaScript 来实现。 以下是一种实现方法: 1. 首先,创建一个按钮,给它一个 ID 并添加一个点击事件的监听器: ``` <button id="myButton" onclick="callPythonFunction()">点击这里</button> ``` 2. 在 JavaScript ,编写 `callPythonFunction()` 函数,并在其使用 AJAX 发送请求到后端 Python API: ``` function callPythonFunction() { var xhr = new XMLHttpRequest(); xhr.open("POST", "/api/my-python-function", true); xhr.setRequestHeader('Content-Type', 'application/json'); xhr.onreadystatechange = function() { if (xhr.readyState === 4 && xhr.status === 200) { console.log(xhr.responseText); } }; xhr.send(JSON.stringify({})); } ``` 在此示例,我们使用了 AJAX 发送一个 POST 请求到 `/api/my-python-function`,并将请求体设置为空 JSON 对象 `{}`。请注意,这里的 URL 应该是你自己的 Python API 的 URL。 3. 在后端 Python ,编写一个处理 `/api/my-python-function` 请求的函数,并在其执行你想要执行的 Python 代码: ``` @app.route('/api/my-python-function', methods=['POST']) def my_python_function(): # 执行你想要执行的 Python 代码 return 'Python 函数已被成功调用!' ``` 在此示例,我们使用 Flask 框架来编写后端 Python 代码。请注意,在实际应用,你需要根据自己的需求来选择合适的框架或库。 这就是实现按钮调用 Python 函数的基本方法。当用户点击按钮时,JavaScript 代码将发送一个请求到后端 Python API,并在收到响应后执行相应的操作。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值