C++ 如何使Qt信号按值发出而不产生编译错误而不是引用?
我读到qt中的信号/插槽概念应该总是通过值而不是引用来传递参数,以确保信号/插槽在线程之间完美地工作 我现在有一段代码,只有当信号的参数通过引用而不是值发出时,它才会编译:C++ 如何使Qt信号按值发出而不产生编译错误而不是引用?,c++,qt,copy-constructor,qt-signals,C++,Qt,Copy Constructor,Qt Signals,我读到qt中的信号/插槽概念应该总是通过值而不是引用来传递参数,以确保信号/插槽在线程之间完美地工作 我现在有一段代码,只有当信号的参数通过引用而不是值发出时,它才会编译: #include <QObject> class mythirdclass { public: mythirdclass(); }; class mysecondclass : public QObject, public mythirdclass { public: mysecondclas
#include <QObject>
class mythirdclass {
public:
mythirdclass();
};
class mysecondclass : public QObject, public mythirdclass {
public:
mysecondclass(mythirdclass third);
};
class myclass : public QObject {
Q_OBJECT
public:
myclass();
signals:
// not working
void messageReceived(mysecondclass mymessage);
// working
// void messageReceived(mysecondclass &mymessage);
};
myclass::myclass()
{
mythirdclass third;
mysecondclass msg(third);
emit messageReceived(msg);
}
mysecondclass::mysecondclass(mythirdclass third)
{
// DO stuff
}
mythirdclass::mythirdclass()
{
}
基于这些错误,我曾考虑为mysecondclass
编写一个副本构造函数,但是经过一些尝试之后,我现在放弃了,因为我没有正确地编写它
因此,我的问题是:
- 为什么编译首先会失败
- 如果由于缺少复制构造函数而失败,为什么编译器不能隐式定义一个
- 在我的例子中,工作副本构造函数是什么样子的
提前感谢。对于第三个问题,如果您不想为mysecondclass定义默认构造函数,那么您的复制构造函数可能如下所示
mysecondclass(mysecondclass const &other) : mythirdclass() {
/// stuff
}
对于第二个问题,我假设(不确定)默认复制构造函数尝试使用已自动删除的默认构造函数,因为您已从mythirdclass的对象中定义了mysecondclass的另一个构造函数(我建议您在此处使用参数的常量引用,以避免无用的复制)
为什么编译首先会失败
因为按值传递意味着复制,如果复制构造函数被删除,那么它就不能按值传递,并且您的函数不能使用此签名进行编译,而它可以通过引用接收其参数,因为它不涉及复制
如果由于缺少复制构造函数而失败,为什么编译器不能隐式定义一个
它实际上失败了,因为它无法隐式地定义一个。原因是您的类派生自QObject
。而且是设计的QObject
。因此编译器不能隐式定义一个
在我的例子中,工作副本构造函数是什么样子的
考虑到
QObject
s的性质,以及当涉及到QObject
s不可复制时,其背后的设计决策,我建议不要使用采用QObject
s的信号和时隙,或者使用从其派生的值类(或者简单地说是任何这样做的函数,信号/插槽主要是深层的函数),而是通过引用或指针。感谢关于const&
的提示,我将把构造函数更改为mysecondclass::mysecondclass(const thirdclass&third)
。我还添加了一个默认构造函数,只是忘记了它。这种mysecondclass::mysecondclass()的存在
但是不会改变编译错误。你的mysecondclass
不是故意继承public QObject
…你是对的,忘记了。这是完整的代码吗?@JBL这是一个很小的例子。现实世界的场景是myclass
是一个包装类,它连接QCanBusDevice
和QCanBusFrame
mythirdclass
是一个QCanBusFrame
和mysecondclass
是我在应用层的任何地方使用的一个特定消息类。这是相关的:感谢您的深入解释!只要我没有遇到任何与信号发射和多重区域相关的问题,我将参考丁。
mysecondclass(mysecondclass const &other) : mythirdclass() {
/// stuff
}