问题在于:我有一个源代码,如果由if / else语句填充,旨在执行相同的指令,但在不同类型的数据中。我不喜欢这个,我想为这种不同的数据类型创建一个抽象,我可以在之前设置正确的数据类型,然后执行相同的指令。我们的想法是删除污染代码的整个if / else语句。好吧,我做了很多搜索,似乎解决我的问题的方法是使用多态。所以,我们来了。上面是我为创建多态而创建的类的标题。这个,平台是基类,另外两个, Vero 和 Pionner 是派生的。
#ifndef VEHICLE_H
#define VEHICLE_H
#include <ros/ros.h>
#include <geometry_msgs/Twist.h>
#include <ransac_project/CarCommand.h>
class Platform{
public:
virtual void setmsg(const double &, const double &) = 0;
//X m_msg; //Some king of genetic type
};
class Vero: public Platform{
public:
ransac_project::CarCommand m_msg;
Vero();
void setmsg(const double &velocity, const double &steering);
};
class Pionner: public Platform{
public:
geometry_msgs::Twist m_msg;
Pionner();
void setmsg(const double &linear_vel, const double &angular_vel);
};
#endif /* VEHICLE_H */
总的来说,我有这样的事情:
Platform* platform;
if(which_car.compare("vero")==0){
Vero vero; platform = &vero;
platform = static_cast<Vero*>(platform);
}
else{
Pionner pionner; platform = &pionner;
platform = static_cast<Pionner*>(platform);
}
到目前为止,这么好。但是,之后,在其他地方有:
int a=0;
int b=0;
platform->setmsg(a,b); //WORKS
platform->m_msg; //DOES NOT WOTK
好吧,最后一个语句不起作用,因为基类没有成员变量m_msg,我无法创建它,因为它的类型在派生类中有所不同。我也阅读了关于模板和void指针但我无法提供解决方案。事实上,使用void指针,我可以这样做:
void* platform;
if(which_car.compare("vero")==0){
Vero vero; platform = &vero;
}
else{
Pionner pionner; platform = &pionner;
}
static_cast<Vero*>(platform)->m_msg;
但事实上,这并没有解决我的问题,因为我明确指出了演员流程中的类型。
这个问题的任何简单解决方案?对此问题的任何其他方法都是受欢迎的。
由于
答案 0 :(得分:1)
如果m_msg
在派生类中可以是不同类型,则它不能存在于基类中。 (或者更确切地说,它将被派生类中声明的m_msg
隐藏。)
即使它确实如此,编译器也无法在编译时确定其类型,因此它不知道如何处理该语句
platform->m_msg; //DOES NOT WOTK
正如您所说,模板可用于解决此问题。 void
指针也有效,但由于缺乏类型安全性,我不能推荐它们,除非替代方法不起作用。
此外,m_
用于表示通常为私有的成员变量,因此无论如何都不应该以这种方式使用它。
另外,这个块:
Platform* platform;
if(which_car.compare("vero")==0){
Vero vero; platform = &vero;
platform = static_cast<Vero*>(platform);
}
else{
Pionner pionner; platform = &pionner;
platform = static_cast<Pionner*>(platform);
}
是一个问题,应该提出一些警告。具体来说,在这样的块中:
{
Vero vero; platform = &vero;
platform = static_cast<Vero*>(platform);
}
{...}
定义了一个本地范围。
您正在创建一个新的Vero
,将其地址分配给platform
,然后vero
在块结束时释放platform
作为悬空指针。 (有关详细信息,请参阅Wiki article on dangling pointers。)
此外,声明
platform = static_cast<Vero*>(platform);
为什么要为自己分配平台?这没用。