Boost-Python 原始指针构造函数

0 投票
1 回答
775 浏览
提问于 2025-04-16 00:19

我正在尝试使用boost-python将一个C++库暴露给Python。这个库实际上是对一个底层C API的封装,所以它经常使用原始指针。

// implementation of function that creates a Request object
inline Request Service::createRequest(const char* operation) const
{
    blpapi_Request_t *request;
    ExceptionUtil::throwOnError(
            blpapi_Service_createRequest(d_handle, &request, operation)
        );
    return Request(request);
}

// request.h
class Request {
    blpapi_Request_t *d_handle;
    Element           d_elements;
    Request& operator=(const Request& rhs); // not implemented
public:
    explicit Request(blpapi_Request_t *handle); 
    Request(RequestRef ref);
    Request(Request &src);
};

// request.cpp
BOOST_PYTHON_MODULE(request)
{
    class_<blpapi_Request_t>;
    class_<Request, boost::noncopyable>("Request", init<blpapi_Request_t *>())
    .def(init<Request&>())
    ;
}

虽然request.cpp编译成功,但当我尝试使用这个对象时却出现了以下错误:

// error output
TypeError: No to_python (by-value) converter found for C++ type: class Request

为了调用这个,Python代码看起来是这样的:

from session import *
from service import *
from request import *

so = SessionOptions()
so.setServerHost('localhost')
so.setServerPort(8194)

session = Session(so)

# start sesssion
if not session.start():
    print 'Failed to start session'
    raise Exception

if not session.openService('//blp/refdata'):
    print 'Failed to open service //blp/refdata'
    raise Exception

service = session.getService('//blp/refdata')
request = service.createRequest('ReferenceDataRequest')

其他对象(SessionOptions、Session、Service等)也是C++对象,我已经成功为它们创建了boost-python的封装。

根据我从boost-python文档中了解到的,这和传递原始指针有关,但我不太明白我还应该做些什么……

1 个回答

1

你的 class_<blpapi_Request_t>; 没有声明任何内容;这个代码是正确的吗?

如果是的话,那就更新一下:

class_<blpapi_Request_t>("blpapi_Request_t");

说到这里,这个错误的意思是你在尝试使用 Request 对象,但它自动转换成 Python 对象的方式并没有定义。

你会遇到这个错误的原因是因为你把 Request 包装成了 boost::noncopyable,然后提供了一个工厂方法返回一个 Request 对象的值;boost::noncopyable 的意思是没有生成复制构造函数,因此也就没有自动转换成 Python 的方法。

解决这个问题有两种方法:一种是去掉 noncopyable 的提示;另一种是注册一个转换器,它可以把 C++ 的 Request 转换成 Python 的 Request 对象。你真的需要 Request 的 noncopyable 特性吗?

撰写回答