2009-08-12 3 views

risposta

41

Dipende. Da documentation:

Quando viene emesso un segnale, gli slot ad esso collegati vengono generalmente eseguiti immediatamente, proprio come una normale chiamata di funzione. Quando ciò accade, il meccanismo di segnali e slot è totalmente indipendente da qualsiasi loop di eventi GUI. L'esecuzione del codice che segue l'istruzione emit avverrà dopo che tutti gli slot saranno ritornati. La situazione è leggermente diversa quando si utilizza queued connections; in tal caso, il codice che segue la parola chiave emit continuerà immediatamente e gli slot verranno eseguiti in seguito.

Quindi, in casi normali, sarà sincrono e bloccante e con le connessioni in coda sarà asincrono e non bloccante.

+10

Si noti inoltre che per impostazione predefinita le connessioni tra oggetti nello stesso thread sono dirette (sincrone) e le connessioni tra oggetti in thread diversi vengono messe in coda. Se ci pensi è piuttosto logico. – quark

+0

@quark Questo non è esattamente corretto. Non importa se gli oggetti sono nella stessa discussione o no. Importa se il thread che emette il segnale è il thread in cui si trova l'oggetto ricevente. La documentazione Qt ha persino sbagliato.Fonte: [Segnali e spazi tra i thread] (http://qt-project.org/wiki/Threads_Events_QObjects#913fb94dd61f1a62fc809f8d842c3afa). Sono d'accordo sul fatto che il comportamento di Qt sia logico. –

9

La risposta di sopra è corretta. Un altro punto però: se tutti i tuoi QObjects appartengono allo stesso thread e non hai specificato manualmente le connessioni in coda, allora l'esecuzione degli slot connessi al segnale avviene in modo sincrono - tutta l'elaborazione verrà eseguita prima della riga successiva dopo l'emissione 'affermazione. Poiché questo è il caso più comune, la risposta alla tua domanda è normalmente "sì".

La documentazione su signals and slots across multiple threads può essere utile.

25

Il problema più grande è che non si può sapere. Cioè, se stai guardando dal punto di vista della classe. Quando si emettono, non si sa che cosa accadrà:

  • Se nessuno è collegato al segnale, non succede nulla
  • Se qualcuno dallo stesso filo è collegato con qualsiasi tipo ad eccezione di Qt :: QueuedConnection, la chiamata verrà bloccata
  • Se qualcuno dello stesso thread è connesso utilizzando Qt :: QueuedConnection, la chiamata sarà non bloccante
  • Se qualcuno da un thread diverso è connesso utilizzando Qt :: DirectConnection (prestare molta attenzione quando lo fai!) o Qt :: BlockingQueuedConnection, la chiamata verrà bloccata
  • Se qualcuno da un thread diverso viene collegato utilizzando Qt :: AutoConnection o Qt :: QueuedConnection, la chiamata sarà non bloccante

Diventa ancora più difficile sapere che cosa accadrà se più oggetti sono collegati al segnale. In tal caso, alcuni slot potrebbero essere eseguiti mentre altri sono ancora in coda. Non c'è, a proposito, nessun thread coinvolto con una connessione non bloccante. C'è solo un evento che viene pubblicato nel ciclo di eventi del thread dell'oggetto ricevente.