Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/358.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python多态性。下注问题 我有C++中的基类列表,我想用Python访问它们的派生类的列表。_Python_C++_Boost - Fatal编程技术网

Python多态性。下注问题 我有C++中的基类列表,我想用Python访问它们的派生类的列表。

Python多态性。下注问题 我有C++中的基类列表,我想用Python访问它们的派生类的列表。,python,c++,boost,Python,C++,Boost,在Boost.Python中是否有一种内置方法来满足这一需求 我举了一个例子来说明我面临的问题: // ------------------------------- Code ----------------------------------// #include<memory> #include<iostream> #include<vector> namespace boost { template<class T> T* get_poin

在Boost.Python中是否有一种内置方法来满足这一需求

我举了一个例子来说明我面临的问题:

// ------------------------------- Code ----------------------------------//
#include<memory>
#include<iostream>
#include<vector>
namespace boost { template<class T> T* get_pointer(std::shared_ptr<T>& p){ return p.get(); }}

struct Vehicle{ virtual ~Vehicle(){} friend bool operator==(const Vehicle& lhs, const Vehicle& rhs) { return true; }};
struct Boat: public Vehicle{ 
    virtual ~Boat(){} 
    friend bool operator==(const Boat& lhs, const Boat& rhs) { return true; }
    char const* testBoatSpecificMethod() { return "Floating."; }    
};
struct Truck: public Vehicle{ 
    virtual ~Truck(){} 
    friend bool operator==(const Truck& lhs, const Truck& rhs) { return true; }
    char const* testTruckSpecificMethod() { return "Trucking."; }
};

class Garage
{
public:
    Garage() {};
    ~Garage() {};
    char const* test() {  std::string temp = "Vehicle List Size: " + std::to_string(m_VehicleList.size()); return temp.c_str(); }
    friend bool operator==(const Garage& lhs, const Garage& rhs) { return true; }
    std::vector<std::shared_ptr<Vehicle>>& vehicleList() { return m_VehicleList; }
private:
    std::vector<std::shared_ptr<Vehicle>> m_VehicleList;
};

#include <boost/python.hpp>
#include <boost/python/suite/indexing/vector_indexing_suite.hpp> 
BOOST_PYTHON_MODULE(garage_ext)
{
    using namespace boost::python;
    class_<Garage>("Garage")
        .def("test", &Garage::test)
        .def("vehicleList", &Garage::vehicleList, return_internal_reference<1>());
    class_<Vehicle,std::shared_ptr<Vehicle>>("Vehicle");
    class_<Boat,std::shared_ptr<Boat>,bases<Vehicle>>("Boat")
        .def("testBoatSpecificMethod", &Boat::testBoatSpecificMethod);
    class_<Truck,std::shared_ptr<Truck>,bases<Vehicle>>("Truck")
        .def("testTruckSpecificMethod", &Truck::testTruckSpecificMethod);   

    implicitly_convertible<std::shared_ptr<Boat>,std::shared_ptr<Vehicle>>();
    implicitly_convertible<std::shared_ptr<Truck>,std::shared_ptr<Vehicle>>();
    class_<std::vector<std::shared_ptr<Vehicle>> >("stl_vector_Vehicle")
       .def(vector_indexing_suite<std::vector<std::shared_ptr<Vehicle>> >());
}

// --------------------------- Test Script -------------------------------//
import garage_ext
g = garage_ext.Garage()
l = g.vehicleList()
l.append(garage_ext.Boat())
print "Expecting a Boat object:"
print str(l[0])
print g.vehicleList()[0].testBoatSpecificMethod()
garage_ext.f2("Done.")
/------------------------------------代码----------------------------------//
#包括
#包括
#包括
命名空间boost{template T*get_指针(std::shared_ptr&p){return p.get();}
结构Vehicle{virtual~Vehicle(){}友元布尔运算符==(const Vehicle&lhs,const Vehicle&rhs){返回true;};
结构艇:公共车辆{
虚拟~Boat(){}
friend bool运算符==(const Boat&lhs、const Boat&rhs){return true;}
char const*testBoatSpecificMethod(){返回“Floating.”;}
};
结构卡车:公共车辆{
虚拟~Truck(){}
friend bool运算符==(常数卡车和左侧、常数卡车和右侧){return true;}
char const*testTruckSpecificMethod(){返回“Trucking.”;}
};
班级车库
{
公众:
车库{};
~Garage(){};
char const*test(){std::string temp=“车辆列表大小:”+std::to_string(m_VehicleList.Size());return temp.c_str();}
friend bool运算符==(const Garage&lhs、const Garage&rhs){return true;}
std::vector&vehicleList(){return m_vehicleList;}
私人:
std::矢量m_车辆列表;
};
#包括
#包括
BOOST_PYTHON_模块(车库扩展)
{
使用名称空间boost::python;
第二类(“车库”)
.def(“测试”和车库::测试)
.def(“车辆列表”和车库::车辆列表,返回内部参考();
第二类(“车辆”);
第二类(“船”)
.def(“TestBoatsSpecificMethod”和Boat::TestBoatsSpecificMethod);
第二类(“卡车”)
.def(“testTruckSpecificMethod”和卡车::testTruckSpecificMethod);
隐式可转换();
隐式可转换();
类别(“stl矢量车辆”)
.def(向量索引套件());
}
//------------------------------测试脚本-------------------------------//
导入车库扩展
g=车库\外部车库()
l=g.车辆列表()
l、 附加(车库外部船())
打印“预期船对象:”
打印str(l[0])
打印g.vehicleList()[0].testBoatSpecificMethod()
车库分机f2(“完成”)
//-------------------------------------输出---------------------------------//

期待一个船的对象 回溯(最近一次呼叫最后一次): 文件“test_garage.py”,第7行,在 打印g.vehicleList()[0].testBoatSpecificMethod() AttributeError:“Vehicle”对象没有属性“TestBoatsSpecificMethod”

“Vehicle”对象没有属性“TestBoatsSpecificMethod” 在这里,我希望车辆是一个船的对象

如果没有内置或推荐/已知的Boost.Python方法来处理此问题, 我将尝试用get访问器返回boost::python::list,将派生的大多数类型存储在python list对象中,从而包装列表(在我的库中有很多包装工作要做)。通过调用重写的“getAsDerivedClass”方法获取派生的most类型。 我想避免这种情况。出于我们的设计和愿景价值/原因,我不喜欢向库中添加python使用特定的方法。另一个问题是,这种方式将引入大量额外的维护工作

编辑: 当我使用原始指针而不是智能指针时,我想要的工作正常。 因为我觉得很明显的原因,我不想用原始指针代替智能指针。
这确实让我松了一口气,因为知道我想要什么这个概念并不像我开始担心的那样牵强。(我仍在努力使它与智能指针一起工作。python对象需要一个转换器,手工编写转换器的工作量太大。)

继承错误:你不能存储向量并期望它具有运行时多态性。这只是普通的C++,你需要存储向量或SypDypPTR等。@ JohnZwinck谢谢约翰,我把代码修好了。我错误地忘记了将列表作为共享指针的列表。通过Boost.Python转换代码,您可以注意到vector就是我们的意图。这个问题仍然存在,不幸的是,不仅仅是一般C++,正如你可以从我的描述中所看到的。现在看来,问题似乎是<>代码> BoAtActudio方法< /代码>等在基类中不存在为<代码>虚拟< /代码>方法。我认为,它们必须是……或者你的向量需要包含boost::python::objects或者其他一些会让生活变得更棘手的东西。是的,这就是我现在所处的位置。这就是为什么我提到使用boost::python::list包装列表,该列表存储派生的most类型。出于上述原因,这是不需要的,我正在尝试找出Boost.Python中是否没有内置的机制。注意,我调用了BoatSpecificMethod来证明我只想使用特定于派生类的方法,而不是作为虚拟方法存在于基中。