2020-03-24:新增Qt::UniqueConnection类型
处理结论
链接参数 | 参数描述 |
---|---|
Qt::AutoConnection | 自动处理,缺省参数,在发送端与接收端处于同一线程时,等同于Qt::DirectConnection,否则自动使用Qt::QueuedConnection |
Qt::DirectConnection | 最终处理效果类似于回调函数,槽函数于信号发送者处于同一线程 |
Qt::QueuedConnection | 槽函数不会马上被执行,槽函数于信号发送者位于不同线程,且触发信号时,信号发送线程会继续执行,注意传输到槽函数的变量有可能会被释放 |
Qt::BlockingQueuedConnection | 槽函数与信号发送者位于不同线程,且信号发送线程会在发送信号后阻塞,等待槽函数执行完毕后继续执行。这种方式线程安全,但是接受者与发送者处于同一线程时,会触发死锁 |
Qt::UniqueConnection | 这个类型可以与上面的任意类型结合使用。这种类型可以避免信号重复连接,即一旦设置了这个类型,那么当相同对象的相同槽函数去连接同一个信号时,connect返回连接失败。此类型在Qt 4.6被引入 |
处理效果
// 信号触发类定义如下
class QDemoThread:public QThread
{
Q_OBJECT
public:
QDemoThread();
signals:
void signalDemo(const QString strText);
protected:
void run();
};
void QDemoThread::run()
{
sleep(1);
QString str = QString("sender signals thread id:%1").arg(GetCurrentThreadId());
qDebug() << str;
qDebug() << tr("sender") << QDateTime::currentDateTime().toString("HH:mm:ss.zzz");
emit signalDemo(str);
qDebug() << tr("sender") << QDateTime::currentDateTime().toString("HH:mm:ss.zzz");
}
// 槽函数定义如下
void QRecvObject::slotDemo(const QString strText)
{
qDebug() << tr("recv") << QDateTime::currentDateTime().toString("HH:mm:ss.zzz");
QString str = QString("recv signals thread id:%1").arg(GetCurrentThreadId());
qDebug() << str;
Sleep(2000);
qDebug() << tr("recv") << QDateTime::currentDateTime().toString("HH:mm:ss.zzz");
}
Qt::DirectConnection
可以看出,非常类似于回调的一种处理方式,信号的发送者和接受者位于同一线程,所以信号发送后的代码只能等待槽函数执行完毕后继续执行
Qt::QueuedConnection
信号的发送者和接受者位于不同线程,且两线程的执行时间无关联,信号发送者发送信号后,线程立即继续执行
Qt::BlockingQueuedConnection
信号的发送者和接受者位于不同的线程,但是信号发送者发出信号后,进入阻塞状态,等待槽函数执行完毕后,信号发送者继续执行