How to run a thread again?



  • Hello,
    I have created a thread which does calculation tasks:

    #ifndef CALCULATOR_H
    #define CALCULATOR_H
    #include <QThread>
    #include <QString>
    #include <vector>
    #include <iostream>
    #include "Summand.h"
    #include <QObject>
    class CalculatorThread : public QObject {
    	Q_OBJECT
    	
    public:
    	CalculatorThread();
    	~CalculatorThread();
    	void setArg(double _accuracy, QString _term, int _startWertX, int _newtonIterations); 
    	public slots:
    	void process();
    private:
    	double accuracy;
    	QString term;
    	int startWertX;
    	// Define signal:
    Q_SIGNALS:
    	void changeGuess(QString text);
    	void changeGuess2(QString text, QString stylesheet);
    	void changeNewton(QString text);
    	void changeResult(QString text);
    	void changeGuessStyleSheet(QString stylesheet);
    	void changeNewtonStyleSheet(QString stylesheet);
    	void changeResultStyleSheet(QString stylesheet);
    	void finished();
    };
    #endif
    
    #include "CalculatorThread.h"
    
    
    
    CalculatorThread::CalculatorThread() { // Constructor
    				 
    }
    
    CalculatorThread::~CalculatorThread() { // Destructor
    			
    }
    
    void CalculatorThread::setArg(double _accuracy, QString _term, int _startWertX, int _newtonIterations)
    {
    	accuracy = _accuracy; term = _term; startWertX = _startWertX; newtonIterations = _newtonIterations;
    }
    void CalculatorThread::process()
    {
    	emit changeNewton("Waiting for guessing to finish...");
    	emit changeResult("Waiting for guessing to finish...");
    	emit changeNewtonStyleSheet("QLabel { color : red; }");
    	emit changeResultStyleSheet("QLabel { color : red; }");
    
    	term.remove("x");
    	QStringList e = term.split("+");
    
    	[...]
    
    
    	
    	emit changeNewton("Newton iterations finished");
    	emit changeNewtonStyleSheet("QLabel { color : green; }");
    	emit changeResult(QString("Result: x=") + QString::number(xStart));
    	emit changeResultStyleSheet(QString("QLabel { color : green; }"));
    	std::cout << "Result: " << xStart << std::endl;
    
    	//emit finished();
    
    }
    

    This is how I create it in the main thread:

    {
    	mInputParser = new InputParser();
       calculatorThread = new CalculatorThread();
    
       thread = new QThread;
       calculatorThread->moveToThread(thread);
       connect(thread, SIGNAL(started()), calculatorThread, SLOT(process()));
       connect(calculatorThread, SIGNAL(finished()), thread, SLOT(quit()));
       connect(calculatorThread, SIGNAL(finished()), calculatorThread, SLOT(deleteLater()));
       connect(thread, SIGNAL(finished()), thread, SLOT(deleteLater()));
    
    	connect(calculatorThread, SIGNAL(changeGuess(QString)),
    		SLOT(onChangeGuess(QString)));
    	connect(calculatorThread, SIGNAL(changeGuess2(QString, QString)),
    		SLOT(onChangeGuess2(QString, QString)));
    	connect(calculatorThread, SIGNAL(changeNewton(QString)),
    		SLOT(onChangeNewton(QString)));
    	connect(calculatorThread, SIGNAL(changeResult(QString)),
    		SLOT(onChangeResult(QString)));
    	connect(calculatorThread, SIGNAL(changeGuessStyleSheet(QString)),
    		SLOT(onChangeGuessStyleSheet(QString)));
    	connect(calculatorThread, SIGNAL(changeNewtonStyleSheet(QString)),
    		SLOT(onChangeGuessStyleSheet(QString)));
    	connect(calculatorThread, SIGNAL(changeResultStyleSheet(QString)),
    		SLOT(onChangeGuessStyleSheet(QString)));
    
    	connect(calculatorThread, SIGNAL(finished()),
    		calculatorThread, SLOT(deleteLater()));
    

    And this is how I start the thread:

    ::calculate()
    {
    double acc = std::pow(10, -mAccuracySpinBox->text().toInt());
    QString term = mInputParser->parseInput(mTermLineEdit->text());
    calculatorThread->setArg(acc , term , mStartSpinBox->text().toInt(), mIterationsSpinBox->text().toInt());
    thread->start();
    }
    

    When I run the calculate method the first time, it works. However, if I run it a second time, it does nothing. How can I fix this?
    Also, the stylesheet emits don't work correctly. For example, "emit changeNewtonStyleSheet("QLabel { color : green; }");" doesn't make the lable green.
    Here's the corresponding method:

    void Nullstellen::onChangeNewtonStyleSheet(QString stylesheet) {
    	mNewtonOutputLabel->setStyleSheet(stylesheet);
    }
    


  • Hi @xLlama

    checked your example, as per my estimation thread did not stop, if thread is already running thread wont restart



  • @yuvaram
    When I add

    thread->terminate()
    

    before I start the thread, the second time I run it, it still does nothing but the gui thread freezes, so I can't click anything.

    thread->exit()
    

    and

    thread->quit()
    

    both do nothing.
    What's the correct way to stop the thread?


  • Lifetime Qt Champion

    Hi,

    The terminate as it names suggest kills the the thread so it's state is not guaranteed as mentioned in the documentation.

    Not that you are automagically destroying everything once your operation is done. See your connections to the deleteLater slots.



Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.