2010-12-15 63 views
1

je code dans Qt qui va comme ceci:Quand un thread sort-il?

void doSomeStuff() 
{ 
    ... 
    if(blah blah) 
     someObj.start(); 
    ... 
} 

puis someObj.run():

void someObj::run() 
{ 
    blah blah blah, do some stuff 
    doSomeStuff() 
} 

Ce que j'étais ont l'intention est pour le nouveau thread créé à someObj.start() pour mettre fin, puis la fonction doSomeStuff dans le thread principal est appelé à nouveau une fois qu'il s'arrête. Mais mon programme s'est écrasé au hasard, et quand j'ai suivi de près le code, j'ai réalisé que le vrai cas était que le nouveau thread appelle simplement la fonction sans mourir, engendrant ainsi de nouveaux threads en continu. Mes soupçons sont-ils corrects? Si oui, comment dois-je y remédier?

+0

Pourquoi aurait appeler une fonction dans une cause de fil cette fonction à exécuter ailleurs que le thread qui l'appelle? Aussi, -1 pour ne pas l'avoir essayé en premier. – Falmarri

+0

@Falmarri exactement, donc je voulais vérifier ici si mon intuition était correcte. Btw, que devrais-je essayé en premier? – wrongusername

+0

@Falmarri peut-être que vous pensiez que j'avais écrit du code et ne l'avais pas encore essayé et posté ici ... Je devrais mettre à jour la question pour le rendre plus clair – wrongusername

Répondre

3

doSomeStuff() est actuellement appelée lorsque le fil est exectured moi le fil sera toujours en vie sinon il ne serait pas appelé du tout ^^ seulement quand doSomeStuff est terminé, votre fil quittera

En jetant un regard sur la doc QT (je ne suis pas expert Qt) J'ai trouvé

http://doc.qt.io/qt-5/qthread.html

bool isFinished() const

vous pourriez dire un rappel à partir de là

+0

Comment j'implémenterais un rappel ? – wrongusername

+0

Nevermind, j'ai fait une chose de slot de signal :) – wrongusername

1

cela semble un peu déroutant. Vous dites que votre thread principal appelle doSomeStuff() pour lancer un thread de temps en temps, mais vous l'appelez aussi dans la fonction d'exécution de thread. Je vais juste supposer qu'il y a deux cas. Je pense que le cas le plus probable est que vous voulez que le fil d'exécuter exactement une fois pour chaque fois que le doSomeStuff est appelé dans le thread principal, le cas échéant:

void doSomeStuff() 
{ 
    ... 
    if(blah blah) 
    { 
     if(someObj.isRunning()) 
      someObj.wait(); 
     someObj.start(); 
    } 
    ... 
} 

void someObj::run() 
{ 
    blah blah blah, do some stuff 
} 

Si vous avez réellement envie le corps de fil à boucle sur et plus, utilisez simplement une boucle while au lieu d'essayer de l'appeler à nouveau. Vous avez sans doute, dans ce cas, l'intention du fil à certainement en cours d'exécution pour sûr chaque fois doSomeStuff est appelé, vous devez donc être un peu plus intelligent:

bool someObjRun = false; 
QMutex someObjRunLock; 

void doSomeStuff() 
{ 
    ... 
    if(blah blah) 
    { 
     someObjRunLock.lock(); 
     someObjRun = true; 

     if (!someObj.isRunning()) 
      someObj.start(); 

     someObjRunLock.unlock(); 
    } 
    ... 
} 

void someObj::run() 
{ 
    someObjRunLock.lock() 
    while(someObjRun) 
    { 
     someObjRunLock.unlock(); 

     blah blah blah, do some stuff 

     someObjRunLock.lock() 
     if(should quit...) 
     { 
      someObjRun = false; 
     } 

    } 
    someObjRunLock.unlock() 
} 
+0

Je pense que c'est le premier cas. Je souhaite que la boucle principale appelle le thread, que le thread exécute ses instructions, puis meure, puis que la fonction 'doSomeStuff' soit exécutée à nouveau. Donc 'someObj.wait' attendrait jusqu'à ce que l'autre thread ait cessé de tourner? – wrongusername

+0

oui, 'QThread.wait()' bloque le thread appelant jusqu'à ce que le thread cible se termine. (http://doc.trolltech.com/4.7/qthread.html#wait) – SingleNegationElimination