如果我有一个用C++定义的类,如下所示
class sample
{
private:
int data;
public:
sample()
{
data=0;
}
int get_data()
{
return data;
}
void set_data(int data)
{
this->data = data;
}
};
的类,我想把它暴露在cython代码中。
cdef extern from "sample.cpp":
cdef cppclass sample:
sample() except +
int get_data()
void set_data(int n)
有没有办法把类中的getter和setter暴露出来 这样就可以在cython中使用了
a = obj.data
而不是
a = obj.get_data()
我知道可以通过包装cython定义的类来实现,但我想避免这种情况,避免这种开销。
也许我的要求太高了。
声明:我不懂cython,所以我不能说下面的内容对cython是否适用。然而,我的策略是通过以下方式实现访问。s.data
已经在C++代码中,以保持绑定的纤细和直接。
C++没有属性,但人们可以模仿它们。
#include <iostream>
template <typename T,typename M,M (T::*getter)(),void (T::*setter)(M)>
struct Attribute {
T* parent;
Attribute(T* parent) : parent(parent){}
operator M() const {
return (parent->*getter)();
}
void operator=(const M& m){
(parent->*setter)(m);
}
};
class sample
{
private:
int data_;
public:
sample()
{
data_=0;
}
int get_data()
{
return data_;
}
void set_data(int data_)
{
this->data_ = data_;
}
Attribute<sample,int,&sample::get_data,&sample::set_data> data{this};
};
int main() {
sample s;
s.data = 42;
std::cout << s.data;
}
输出是 42
. 请注意,我必须假设一个 int
参数的设置器。也要启用 const int&
需要更多一点。
使用上面@idclev 463035818接受的回复中的c++样例类的定义,为了方便,复制到这里。
#include <iostream>
template <typename T,typename M,M (T::*getter)(),void (T::*setter)(M)>
struct Attribute {
T* parent;
Attribute(T* parent) : parent(parent){}
operator M() const {
return (parent->*getter)();
}
void operator=(const M& m){
(parent->*setter)(m);
}
};
class sample
{
private:
int data_;
public:
sample()
{
data_=0;
}
int get_data()
{
return data_;
}
void set_data(int data_)
{
this->data_ = data_;
}
Attribute<sample,int,&sample::get_data,&sample::set_data> data{this};
};
我测试了在cython中用一个扁平的公共属性来声明那个C++类,然后... ...它成功了!这样就可以了。
cdef extern from "sample.cpp":
cdef cppclass sample:
sample() except +
int data
测试了一下,并对例子中的访问器进行了仪器测试,显示访问器被正确调用。
非常感谢大家! 那是 很 有帮助的。