2014-11-06 3 views
0

я шел через Qt учебник here, когда я наткнулся на этот следующий кусок кода:Что означают слоты и сигналы в классах Qt?

#include <QObject> 

class Counter : public QObject 
{ 
    Q_OBJECT 

public: 
    Counter() { m_value = 0; } 

    int value() const { return m_value; } 

public slots: 
    void setValue(int value); 

signals: 
    void valueChanged(int newValue); 

private: 
    int m_value; 
}; 

Может кто-нибудь объяснить мне, что это использование в public slots, signals в декларации? Я, хотя есть только два, public и private. Как они называются и каково их использование?

+1

@Cupidvogel: Да, я пропустил ссылку. Итак, вам лучше прочитать этот документ еще раз ... это основа Qt, которую вы должны четко понимать. И официальная документация довольно понятна. – zaufi

+0

Похож на это. Лучше закройте вопрос, не так ли, Барри? – SexyBeast

+0

Для этого нужно еще 3 голоса. – JBL

ответ

3

Сигналы и слоты является конструкция языка введена в Qt для связи между объектами [1], что делает его легко реализовать шаблон наблюдателя, избегая при этом шаблонный код. Концепция заключается в том, что Виджеты GUI могут отправлять сигналы, содержащие информацию о событии, которая может быть , полученная другими элементами управления, с использованием специальных функций, известных как слоты.

Система сигналов/слотов хорошо подходит для использования графическим пользователем Интерфейсы разработаны. Аналогично, система сигналов/слотов может использоваться для других не-графических интерфейсов, например асинхронных операций ввода-вывода (включая сокетов, труб, последовательных устройств и т. Д.) Или ассоциировать события таймаута с соответствующими экземплярами объектов и методы или функции. Он прост в использовании и не нужно записывать код регистрации/регистрации/вызова, , потому что Qt's Meta Object Compiler (MOC) автоматически создает необходимую инфраструктуру .

Общепринятая метафора - это электронная таблица. В таблице есть ячейки , которые наблюдают за исходной ячейкой (ями). Когда исходная ячейка изменяется, зависимые ячейки обновляются из события.

Не плохо объяснено с Wikipedia


Поскольку Qt в основном изобрел понятие было бы лучше для вас, на самом деле читать статью, которую вы размещены в вашем вопросе.

Особенно:

Сигналы

Сигналы испускаются объектом, когда его внутреннее состояние изменилось каким-то образом, что может быть интересно для клиента или владельца объекта. Только класс, который определяет сигнал и его подклассы, может излучать сигнал .

Когда сигнал испускается, подключенные к нему слоты обычно равны , как и обычный вызов функции. Когда это происходит , механизм сигналов и слотов полностью не зависит от любого цикла событий GUI. Выполнение кода, следующего за выводом эмиттера , произойдет после возвращения всех слотов. Ситуация немного отличается от при использовании очередей; в таком случае код , следующий за ключевым словом emit, будет продолжен немедленно, и слоты будут выполнены позже.

Если несколько разъемов подключены к одному сигналу, слоты будут , выполненные один за другим, в том порядке, в котором они были подключены, при испускании сигнала.

Сигналы генерируются автоматически moc и не должны быть , реализованных в файле .cpp. У них никогда не может быть типов возврата (т. Е. использовать void).

Замечание о аргументах: наш опыт показывает, что сигналы и слоты являются более многоразовыми, если они не используют специальные типы. Если QScrollBar :: valueChanged() должны были использовать специальный тип, например, гипотетический QScrollBar :: Range, его можно было бы подключить только к слотам , разработанным специально для QScrollBar. Подключение разных входных сигналов . Виджеты вместе были бы невозможны.

и

Слоты

слот вызывается, когда сигнал, подключенный к нему сигнал. Слоты: обычные функции C++ и могут быть вызваны нормально; их единственная специальная функция состоит в том, что к ним могут быть подключены сигналы.

Поскольку слоты являются нормальными функциями-членами, они следуют нормальным правилам C++ при вызове напрямую. Однако в качестве слотов они могут быть вызваны любым компонентом, независимо от его уровня доступа, через сигнальный разъем . Это означает, что сигнал, испущенный из экземпляра произвольного класса , может вызвать вызов частного слота в экземпляре неродственного класса.

Вы также можете определить слоты, чтобы быть виртуальными, которые мы нашли довольно полезными на практике.

По сравнению с обратными вызовами сигналы и разъемы немного медленнее, потому что повышенной гибкости, которую они обеспечивают, хотя разница для реальных приложений невелика. В общем случае, излучение сигнала, которое подключено к некоторым слотам, примерно в десять раз медленнее, чем , вызывающее приемники напрямую, с не виртуальными вызовами функций. Это - это накладные расходы, необходимые для нахождения объекта соединения, безопасно итерации по всем соединениям (т. Е. Проверка того, что последующие приемники не были уничтожены во время эмиссии) и для маршаллинга любых параметров в общем виде. В то время как десять не виртуальных вызовов функций могут звучать как много, это намного меньше накладных расходов, чем любая новая или удаление операции , например. Как только вы выполняете строку, векторную или операцию списка, которая за сценой требует новых или удаленных, служебные данные и слоты несут ответственность за очень небольшую долю от полной стоимости вызова функции.

То же самое верно, когда вы выполняете системный вызов в слоте; или косвенно вызовите более десяти функций. На i586-500 вы можете испускать около 2 000 000 сигналов в секунду, подключенных к одному приемнику, или около 1 200 000 в секунду, подключенных к двум приемникам.Простота и гибкость механизма сигналов и слотов хорошо стоят накладных расходов , которые ваши пользователи даже не заметят.

Обратите внимание, что другие библиотеки, определяющие переменные, называемые сигналами, или слоты , могут вызывать предупреждения и ошибки компилятора при компиляции вместе с приложением Qt. Чтобы решить эту проблему, #undef оскорбительный символ препроцессора .