根据输入初始化特定的子类

时间:2015-04-02 12:38:44

标签: c++ interface

我想根据用户是否使用-m或-f调用程序来初始化特定的子类。

我写了这样一个界面:

class DatabaseInterface {

   public:
  virtual std::vector<Newsgroup> list_newsgroups() = 0;
  virtual std::vector<Article> list_articles(const size_t article_id) const = 0;
  virtual bool create_newsgroup(const std::string& newsgroup_name) = 0;
  virtual bool create_article(const size_t newsgroup_id, const std::string& title, const std::string& author, const std::string& text) = 0;
  virtual bool delete_newsgroup(const size_t newsgroup_id) = 0;
  virtual std::pair<int,Article> get_article(const size_t newsgroup_id, const size_t article_id) const = 0 ;
  virtual int delete_article(const size_t newsgroup_id, const size_t article_id) = 0;
};

在我使用数据库的班级中,我有以下几行:

string file_memory;
DatabaseMemory db;
try {
  file_memory = argv[2];
  if(file_memory.compare("-file") == 0 || file_memory.compare("-f") == 0 ) {
     DatabaseFile db;
     cout << file_memory << endl;
  } else if (file_memory.compare("-memory") == 0 || file_memory.compare("-m") == 0 ) {
        DatabaseMemory db;
  } else {
     cerr << "Specify saving on disk with '-f' or in memory with '-m' " << endl;
     exit(1);
  }
  } catch ( exception& e ) {
  cerr << "Specify saving on disk or in memory" << endl;
  exit(1);

}

正如您所看到的,我正在尝试初始化派生的DatabaseMemory只是为了取悦编译器,但是,这似乎是一种伪劣的方法。我该怎么做才能做得更好?

我希望能够写出类似

的内容
 DatabaseInterface db;
if(file_memory == "-m") {
    db = DatabaseMemory();
} else if ( file_memory == "-f") {
    db = DatabaseFile();
} else {
exit(1);
}
//.... do stuff

我该怎么做呢?此时,我的界面什么都没给我。我想我可能已经错过了在这里使用它的意义。

1 个答案:

答案 0 :(得分:2)

您需要间接(即指向基类的指针或引用)来支持多态性。像

这样的东西
std::unique_ptr<DatabaseInterface> db;
if (file_memory == "-f") {
    db = std::make_unique<DatabaseFile>();
} else if (file_memory == "-m") {
    db = std::make_unique<DatabaseMemory>();
}

如果您还没有使用C ++ 14,可以将make_unique替换为

db.reset(new DatabaseFile);