【发布时间】:2020-09-13 07:38:17
【问题描述】:
一般来说,我们使用虚函数或组合来设计类。据我所知,使用虚函数会使类更有条理;使用组合将很容易实现,但可能会编写更多重复的代码。 在这种情况下:我需要一个解析器,它将用于不同的协议。现在,我假设它将用于名为 AParser 的 A-Protocol,名为 BParser 的 B-Protocol,如下所示:
class Parser {
public:
Parser(...);
virtual ~Parser() = default;
virtual bool Parse(...) = 0;
private:
// some attributes may be common
};
class AParser() : public Parser {
public:
AParser(...) : Parser() {};
~AParser() override = default;
void bool Parser(...) override;
inline AData Data() const { return AData_;}
private:
AData_;
}
class BParser() : public Parser {
public:
BParser(...) : Parser() {};
~BParser() override = default;
void bool Parser(...) override;
inline BData Data() const { return BData_;}
private:
BData_;
}
嗯,AData 和 BData 都是自己的私有数据,不应该放在基类中,
另外,不应该virtual AData/BData Data() = 0(错误!!!)
那么,如何设计类来解决问题呢? 现在我有两个想法,但我认为它们不能满足我
- 用
static_cast<derived_class>(this)->derivedFunc(),第一这个操作不优雅,第二如果我用这个操作,Inheritance + encapsulation还有意义吗? - 使用普通函数,比如
virtual std::map<std::string, void *> GetData() = 0,然后使用member field name获取归档数据,但是如何使用派生函数还是个问题?
我认为这个问题可能是一个班级设计问题,请你帮我回答这个问题吗?
【问题讨论】:
-
GetData()函数的意义何在?为什么你不能通过它们的基类接口使用你的解析器?您是否可能在基类接口中缺少GetData()? -
完全不清楚您的要求。即便如此,您的描述也不清楚。示例:“虚函数或组合” 什么是“组合”。什么的组合?请少描述所有背景,专注于编程相关的事情。顺便说一句:“inline”关键字在这种情况下是模糊的!
-
不,我不能。因为 A B 是不同的协议,不能设计一个
GetData(),它们返回不同的类型,不同的类型有自己的文件。还有一个问题:基类ptr/ref中的派生类函数,如果不能设计成虚函数,如何使用派生类函数 -
您需要从
Parser &拨打getData吗?需要AData的东西可以用AParser,需要BData的东西可以改用BParser,不关心的就不用调用了吗? -
@Klaus 我问的是如何在这种情况下设计课程,你现在清楚了吗?
combination,sorry,我的意思是composition,它也可以完成目标,但可能会写更多的重复代码,我想知道如何实现目标使用继承。为什么我描述了这么多背景?因为这么多相关问题的答案是“在基类中定义虚函数”我认为具体的问题需要特定的背景,你不这么认为吗?
标签: c++ inheritance combinations virtual-functions class-design