QThread - threads how to kill all of them?
-
Hi guys!
I'm stuck with QThreads again. Since i got all the threads and worker stuff going i wonder hot to end all of them at once? So far i can only end the current thread but this is very unsatisfying. Since i use them for dont-/uploading images and xml files on ftp servers, i really need a way to end all of the up and downloads at once.
thread = new QThread; worker = new Worker(commands); worker->moveToThread(thread); connect signals and slots ...
Works like a charm and i can end the current thread using
worker->abort();
But how to end all the running threads? I did try to for loop the worker->abort(); for the count of running threads. Did not work. Then i added
QList<QThread*> myThreads;
to the private and added every thread by
myThreads.append(thread->currentThread());
I got a list now but all the threads are the same. I even did try to keep track of threads by using a QStringList and added thread->setObjectName and worker->setObjectName successfully. But i still did not figure out how to loop though all the threads and kill them one by one or all of them.
There are examples out there but so far non of them did show hot to end all running threads. Only the current running one. There has to be a way, i guess. Any ideas how this may work?
Thanks!
-
Hi,
How many threads are you expecting to use ?
There's a limit of resource on your systems and also, QNetworkAccessManager already handle queuing of requests.
-
3 to 5 Threads at the same time, i let the user choose. I did test 35 Threads (just for fun) on an i7 quad core and the cpu usage was around 22%. I guess about 100 threads is possible on a modern core i7 quad core.
I want to be able to end all threads because if one threads is done it starts the next thread and i use QFtp.
-
Why not make re-usable objects ? And use e.g. QThreadPool ?
-
Do you mean like the one provided in the details of QThreadPool's documentation ?
-
If you have a fixed number of threads then just keep a list of them and stop them when needed.
if you make your worker object you can make it re-usuable so you only have to restart the thread.
-
@qDebug said in QThread - threads how to kill all of them?:
How do i keep "a list" and how can i use this list to stop the threads?
Instead of:
thread = new QThread; ... myThreads.append(thread->currentThread());
which is adding the controlling thread each time, add the child threads instead, like:
thread = new QThread; ... myThreads.append(thread);
Then you can do something like:
foreach (QThread * thread, myThreads) { thread->terminate(); }
Cheers.
-
@Paul-Colby Thanks you, that helps.
But in general i'm not sure if i use threads in the best known way yet. I got the thread, a worker class and inside the worker class i start a QFtp download. So all the worker classes show as child the QFtp. In my case i guess i have to stop the QFtp download. The download stops if i stop the worker. So far so good.
Not sure right now if i even need a worker class for QFtp. Can i just move the QFtp download to the thread?
So... do i loop through all the threads or the worker classes and call the abort function i've created to stop the QFtp download? I really can't find any examples about that particular problem.
Thanks!
-
@qDebug said in QThread - threads how to kill all of them?:
But in general i'm not sure if i use threads in the best known way yet. ... Not sure right now if i even need a worker class for QFtp.
I'm not at all familiar with QFtp, but a few notes that may help:
- QFtp is no longer exported in Qt5, so as per the Qt5 docs, I'd recommend you use the QNetworkAccessManager class directly if that's possible for you.
- with both classes, it should be possible to do the download asynchronously without using any threads. The only reason I'd use worker threads here, is if you had to do any real processing of the data as it was arriving, or you have some slick UI animation going on and don't want any stutters / artefacts.
- if you can use QNetworkAccessManager, then have a look at either Network Download Example or Network Download Manager Example, neither of which require threads.
- otherwise check out the (older) FTP Example, which also doesn't require threads.
Good luck :)
-
@qDebug said in QThread - threads how to kill all of them?:
But in general i'm not sure if i use threads in the best known way yet.
If you need to call
QThread::terminate
then you're doing something very wrong. I like to say that this (doiung forceful termination) is the equivalent of hitting your girl with baseball bat after having a nice dinner. :) -
After a lot of try and error, mostly error and crashes, i ended up with this working solution:
foreach(FTPDownload* w, g_Worker) { if(w->_working) { w->abort(); // sets _working = false and _abort = true w->ftp->deleteLater(); // ends the QFtp download w->thread()->quit(); w->thread()->deleteLater(); } }
The only problem left is when i remove the table from the QTableView the progress update wont terminate and the app crashes, because the table does not exist anymore.
I guess i have to add the the function that executes the code from above somehow in a event loop so the code after that deletes the table wont be executed before all the downloads are really stopped. Right?