问题描述
我有很多正在运行的C ++ 11线程,它们都需要在某个时间访问数据库.在主要方面,我会初始化数据库连接并打开数据库. Qt文档说查询不是线程安全的,因此在线程内部存在QSqlQuery之前,我将使用全局互斥锁.
I have a lot of C++11 threads running which all need database access at some time. In main I do initalize the database connection and open the database. Qt documentation says that queries are not threadsafe so I use a global mutex until a QSqlQuery exists inside a thread.
这行得通,但是否可以保证正常工作,或者我有时会遇到问题?
This works but is that guaranteed to work or do I run into problems at some time?
推荐答案
看看文档告诉我们,
因此,您确实确实需要每个线程一个连接.我通过基于线程生成动态名称来解决了这个问题:
So you do indeed need one connection per thread. I solved this by generating dynamic names based on the thread:
auto name = "my_db_" + QString::number((quint64)QThread::currentThread(), 16);
if(QSqlDatabase::contains(name))
return QSqlDatabase::database(name);
else {
auto db = QSqlDatabase::addDatabase( "QSQLITE", name);
// open the database, setup tables, etc.
return db;
}
如果您使用不受Qt管理的线程,请使用 QThreadStorage
为每个线程生成名称:
In case you use threads not managed by Qt make use of QThreadStorage
to generate names per thread:
// must be static, to be the same for all threads
static QThreadStorage<QString> storage;
QString name;
if(storage.hasLocalData())
name = storage.localData();
else {
//simple way to get a random name
name = "my_db_" + QUuid::createUuid().toString();
storage.setLocalData(name);
}
重要提示:Sqlite可能会或可能不会处理多线程.请参见 https://sqlite.org/threadsafe.html .据我所知,嵌入到Qt中的sqlite是线程安全的,这就是默认设置,我在源代码中找不到任何禁用它的标志.但是,如果您使用的是其他sqlite版本,请确保它确实支持线程.
Important: Sqlite may or may not be able to handle multithreading. See https://sqlite.org/threadsafe.html. As far as I know, the sqlite embedded into Qt is threadsafe, as thats the default, and I could not find any flags that disable it in the sourcecode. But If you are using a different sqlite version, make shure it does actually support threads.
这篇关于从多个线程使用QSqlQuery的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!