我总是使用下面的代码连接到sqlite数据库。出于某些原因,我决定以一种使用*QSqlDatabase而不是QSqlDatabase的方式重写它。
我所做的只是在我的旧代码( Line_12 )前面使用了Line_12。但是代码在第6行中崩溃。
不管怎样,有人给了我line_14,它起作用了。
所以..。我不明白我的第一段代码有什么问题,以及为什么建议的代码使它工作。
Foo::Foo(QString path_="db_path_name") {
InitialDataBase(path_);
bool isOpened = db->open();
if(!isOpened) exit(1);
else
queryExecutor = new QSqlQuery(*db); // --> Line_6
}
void Foo::InitialDataBase(QString path_) {
// Line_12 => DOESN'T WORK
db = &(QSqlDatabase::addDatabase("QSQLITE"));
// Line_14 => WORK
db = new QSqlDatabase(QSqlDatabase::addDatabase("QSQLITE"));
db->setHostName("localhost");
db->setDatabaseName(path_);
db->setUserName("admin");
db->setPassword("admin");
}发布于 2014-03-14 08:12:37
在第12行中,您将获取由QSqlDatabase返回的addDatabase()对象的地址。该对象是临时的,在语句结束后立即销毁(在第12行之后)。因此,您将得到一个悬空指针,即指向已删除对象的指针。删除悬空指针是未定义的行为。在实践中,它通常会崩溃。
在第14行中,在堆上创建一个新的QSqlDatabase对象,创建从addDatabase()返回的临时QSqlDatabase对象的副本。这里调用复制构造函数QSqlDatabase( constructor &)。临时对象被销毁,但堆上的副本仍然保留。请注意,以后必须删除db,否则将导致内存和资源泄漏(打开DB连接)。
你为什么在这里使用指针?尤其是作为初学者,它只会导致崩溃和泄漏,如本例所示;)
https://stackoverflow.com/questions/22398783
复制相似问题