0

我正在设计一个数据库浏览应用程序,到目前为止它还支持 MySQL,但最近我也开始实现对 Sqlite 的支持,并且在设计连接架构的实现方式时遇到了一些丑陋的问题。这仅与“连接”部分有关(即:您获取用户/数据库/主机的位置,或者对于 sqlite 文件名),而不是数据库功能。那已经整理好了。

我有一个基类“Connection”,它公开“普通”方法,例如name(),或纯虚拟方法,virtual string fullLocation() = 0它们返回一个可用于标识数据库的字符串(例如:database@host对于 MySql,或/etc/mydb.sqlite对于 Sqlite)。

现在,用户当然需要指定他想要连接的数据库,因此在应用程序的 GUI 中,他只需选择类型,然后填写凭据即可。我的麻烦就从这里开始了。我创建了一个MySqlConnection和一个SqliteConnection类,它们都派生自Connection但大多数情况下我最终得到的结果如下:

        Connection* c = 0;
        if(gui->engine_name() == "MYSQL")
        {
            string host = gui->getHost();
            string user = gui->getUser();
            string password = gui->getPassword();
            int port = gui->getPort();
            string db = gui->getDatabase();
            c = new MySqlConnection(host, user, password, db, port);
        }
        else
        {
            string dbFile = gui->getSqliteDbFile();
            c = new SqliteConnection(dbFile);
        }
        string meta = application->use_connection(&c);

而且我担心这将在整个应用程序中继续存在,因为这两个数据库引擎的性质如此不同。

您对如何以优雅的方式解决此问题有一些指导吗?

4

2 回答 2

0

一种更优雅的方法是设计一个工厂类并在该GenerateConnection()工厂的方法中处理 GUI 输入:

void ConnectionFactory::GenerateConnection(Connection* c)
{
 if(gui->engine_name() == "MYSQL")
    {
        string host = gui->getHost();
        string user = gui->getUser();
        string password = gui->getPassword();
        int port = gui->getPort();
        string db = gui->getDatabase();
        c = new MySqlConnection(host, user, password, db, port);
    }
    else
    {
        string dbFile = gui->getSqliteDbFile();
        c = new SqliteConnection(dbFile);
    }

}

如果您不喜欢对 gui 的依赖,您可以定义一个名为 Parameters 的结构并根据 gui 输入更新其实例,并将此对象提供给连接工厂的连接生成方法。

于 2013-04-15T12:19:24.337 回答
0

您需要模式工厂,它将以抽象的方式为您创建连接。是肤浅的回答。这个工厂将是很好的 Builder 模式的参数化。像这样的东西:

 ParamBuilder *b = new ParamBuilder;
 if(gui->engine_name() == "MYSQL")
 {
      b->setHost(gui->getHost())
       ->setUser(gui->getUser());
       ->setPassword(gui->getPassword());
        ...
  }
  else
  {
      b->setFile(gui->getSqliteDbFile());
  }
  Connection *c = globalConnectionFactory->createConnection(b);
于 2013-04-15T12:22:57.863 回答