标签: qthread

PySide QThread.terminate() 导致致命的 python 错误

我使用的是 PySide 版本 1.2.2,它包装了 Qt v4.8 框架。QThread我面临的情况是,我必须在让我的应用程序等待我不再需要正常退出的情况(线程很可能会无限期地阻塞)和给无响应的线程一个宽限期(几秒钟)之间做出选择),然后调用QThread.terminate()它。尽管我希望可以,QThread但当底层线程仍在运行时,我不能让对象超出范围,因为这会抛出错误“QThread:线程仍在运行时被销毁”,并且几乎肯定会导致段错误。

请注意,我知道终止QThreads 是危险的并且强烈建议不要这样做。我只是想在这里探索我的选择。

然而,当我尝试终止线程时,我的应用程序崩溃并出现以下错误:

Python 致命错误:释放时该线程状态必须是当前状态

您可以通过复制/粘贴并运行以下代码自行尝试:

from PySide import QtCore, QtGui

class Looper(QtCore.QThread):
    """QThread that prints natural numbers, one by one to stdout."""
    def __init__(self, *args, **kwargs):
        super(Looper, self).__init__(*args, **kwargs)
        self.setTerminationEnabled(True)

    def run(self):
        i = 0
        while True:
            self.msleep(100)
            print(i)
            i += 1

# Initialize and start a looper.                                                                      
looper = Looper()
looper.start()

# Sleep main thread for 5 seconds.                                                                    
QtCore.QThread.sleep(5)

# Terminate …
Run Code Online (Sandbox Code Playgroud)

python qt multithreading pyside qthread

5
推荐指数
1
解决办法
4912
查看次数

暂停和恢复 QThread

我正在尝试暂停 QThread 并恢复它。

所以,我在 QThread 中有一个 RFID 读取循环,我想在读取器获得 RFID 代码时暂停无限循环。之后,进行数据库检查。在检查结束时,我想恢复 RFID 读取循环以获取其他代码。

MVCE:

def main():
    global Thread
    app = QtGui.QApplication(sys.argv)
    main = Main()
    Thread = RFID_Thread()
    Thread.rfid_event.connect(Main().on_event)
    Thread.start()
    sys.exit(app.exec_())

class Main(object):
    def __init__(self):
        self.accueil = MainWindow(self)
        self.access = AccessWindow()
        self.accueil.show()

    def on_event(self, data):
        # I WANT TO PAUSE THE QTHREAD HERE

        ###################################
        #   CHECKING DB & SHOWING UI      #
        ###################################

        # AND RESUME IT HERE
class RFID_Thread(QtCore.QThread):
    rfid_event = pyqtSignal(str, name='rfid_event')
    def run(self):
        while 1:
            ser = serial.Serial(port=Serial_Port, baudrate=Serial_Baudrate)
            a …
Run Code Online (Sandbox Code Playgroud)

python pyqt pyqt4 qthread

5
推荐指数
1
解决办法
7000
查看次数

如何使用 Qthread 通过 PyQt 更新 Matplotlib 图?

我真的很难理解如何在 PyQt 中使用线程。我做了一个简单的例子来说明我想在用户界面中做什么。在下面的代码中,我希望用户输入股票行情(例如,您可以输入“bby”、“goog”或“v”)并绘制特定时期内股票的价值。问题是在更复杂的用户界面中,或者在很长一段时间内,用户界面在绘图更新时冻结。所以我制作了一个“绘图仪”类,当它收到某个信号时更新绘图(覆盖 Qthread.run 显然不是你做错的正确方法)。我想让这个“绘图仪”在主线程之外的另一个线程中运行。

一旦我取消注释线程,程序就会停止工作。我尝试移动新线程的启动以及“连接”,但没有任何效果。我认为即使在阅读了文档并查看了 Qt 网站上的示例之后,我仍然不太理解 Qthread 的工作原理。

如果您知道如何做到这一点,那将会有很大帮助!(我正在使用 Python 3.5 和 PyQt5)

from PyQt5.QtCore import *
from PyQt5.QtWidgets import *
from matplotlib.axes._subplots import Axes
from matplotlib.figure import Figure
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg as FigureCanvas
import sys
from datetime import datetime, timedelta
import time
import quandl


class MyMplCanvas(FigureCanvas):
    """Ultimately, this is a QWidget (as well as a FigureCanvasAgg, etc.)."""
    send_fig = pyqtSignal(Axes, str, name="send_fig")

    def __init__(self, parent=None):
        self.fig = Figure()
        self.axes = self.fig.add_subplot(111)

        # …
Run Code Online (Sandbox Code Playgroud)

python pyqt matplotlib qthread

5
推荐指数
1
解决办法
5219
查看次数

PyQt:如何从QThread处理QPixmaps?

这是我在使用PyQT时遇到的最大麻烦:我已经为我的应用程序拼了一个缩略图线程(我必须缩略图大量的图像),看起来它会工作(而且几乎可以).每当我SIGNAL从我的线程发送一个时,我的主要问题是这个错误消息:

QPixmap: It is not safe to use pixmaps outside the GUI thread
Run Code Online (Sandbox Code Playgroud)

我无法弄清楚如何解决这个问题.我试过QIcon通过我的SIGNAL,但仍然会产生相同的错误.如果它有帮助,这里是处理这些东西的代码块:

Thumbnailer类:

class Thumbnailer(QtCore.QThread):
  def __init__(self, ListWidget, parent = None):
    super(Thumbnailer, self).__init__(parent)
    self.stopped = False
    self.completed = False
    self.widget = ListWidget

  def initialize(self, queue):
    self.stopped = False
    self.completed = False
    self.queue = queue

  def stop(self):
    self.stopped = True

  def run(self):
    self.process()
    self.stop()

  def process(self):
    for i in range(self.widget.count()):
      item = self.widget.item(i)

      icon = QtGui.QIcon(str(item.text()))
      pixmap = icon.pixmap(72, …
Run Code Online (Sandbox Code Playgroud)

pyqt4 qpixmap qthread

4
推荐指数
1
解决办法
3043
查看次数

通过信号/插槽将QVector <float>从工作线程传递到主线程

目前我有一些麻烦将QVector传递给线程.目前我有一个主线程(GUI-Thread)和一个频繁发出QVector数组的工作线程.直接在向量内部发射数据之前看起来很好.接收器是主线程中的一个插槽,但是插槽接收的数据是乱码.

以下是我的代码的一些部分:

在工作线程中发出:

void Pipeline::process
{
    QVector<float> buffer(w * h * d);

    // filling the vector with RGB-Values

    emit this->pushBuffer(buffer, w, h, d);
}
Run Code Online (Sandbox Code Playgroud)

主线程中信号和插槽的连接:

QObject::connect(this->_pipeline.data(), SIGNAL(pushBuffer(const QVector<float>, int, int, int)), this->ui->widgetFiltered, SLOT(setBuffer(const QVector<float>,int,int,int)));
Run Code Online (Sandbox Code Playgroud)

主线程中的插槽:

void GLWidget::setBuffer(const QVector<float> buffer, int dataSizeX, int dataSizeY, int dataSizeZ)
{
    // at this point the contents inside 'buffer' is garbled
}
Run Code Online (Sandbox Code Playgroud)

Thread通过使用QObject的moveToThread启动,并QVector<float>通过qRegisterMetaType< QVector<float> >("QVector<float>");main方法注册到元系统.

Pipeline::process返回后数据是否可能丢失?我不确定QVector这个多线程情况下隐式共享内部的行为如何.

任何帮助,将不胜感激.

问候

qt multithreading signals-slots qthread

4
推荐指数
1
解决办法
3148
查看次数

如何实现频繁启动/停止线程(QThread)

我需要使用按钮非常频繁地启动和停止线程..我正在使用Qt.最近我学会了创建一个worker的QObject并将其移动到QThread的对象,作为在Qt中实现线程的正确方法.以下是我的实施......

Worker.h

class worker : public QObject
{
    Q_OBJECT
public:
    explicit worker(QObject *parent = 0);
    void StopWork();
    void StartWork();
    bool IsWorkRunning();

signal:
    void SignalToObj_mainThreadGUI();

public slots:
    void do_Work();

private:
    void Sleep();

    volatile bool running,stopped;
    QMutex mutex;
    QWaitCondition waitcondition;
};
Run Code Online (Sandbox Code Playgroud)

Worker.cpp

 worker::worker(QObject *parent) :
    QObject(parent),stopped(false),running(false)
{
}

void worker::do_Work()
{
    running = true;
    while(!stopped)
    {
        emit SignalToObj_mainThreadGUI();
        Sleep();
    }
}

void worker::Sleep()
{
    mutex.lock();
    waitcondition.wait(&mutex,10);
    mutex.unlock();
}

void worker::StopWork()
{
    mutex.lock();
    stopped = true;
    running = false;
    mutex.unlock();
}

void worker::StartWork() …
Run Code Online (Sandbox Code Playgroud)

qt multithreading qthread

4
推荐指数
1
解决办法
8313
查看次数

如何在QThread中运行计时器?

我想在QThread中运行一个计时器.我写了一些代码,其中我在运行时遇到了一些错误.请引导我走向正确的方向.我究竟做错了什么?

(Parent is QThread(0x1498d10), parent's thread is QThread(0x11272b0), current thread is QThread(0x1498d10)
Run Code Online (Sandbox Code Playgroud)

mainwindow.h //主.h文件

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QMainWindow>
#include "mythread.h"
namespace Ui {
class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = 0);
    ~MainWindow();
    MyThread *myt;

private:
    Ui::MainWindow *ui;
};

#endif // MAINWINDOW_H
Run Code Online (Sandbox Code Playgroud)

mainwindow.cpp //主.cpp文件

#include "mainwindow.h"
#include "ui_mainwindow.h"

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    myt=new MyThread();
    myt->start();
    MainWindow w;
}

MainWindow::~MainWindow()
{
    delete ui;
}
Run Code Online (Sandbox Code Playgroud)

mythread.h //线程类

#ifndef MYTHREAD_H …
Run Code Online (Sandbox Code Playgroud)

c++ qt qt-creator qthread qtimer

4
推荐指数
2
解决办法
1万
查看次数

无法在QThread与多个Qthread的finished()信号之间进行连接

我有一个3个QThreads彼此调用(所有都继承自QThread.我知道有些人可能建议使用moveToThread,但现在暂时忽略这个事实).简化代码如下所示:

Thread1类:

void
Thread1::run
{
    // some execution
    Thread2 t2 = new Thread2();
    connect(t2,SIGNAL(finished),this,SLOT(onFinished));
    t2->start();

    while(!stop)  // stop was initialized as false
    {
        this->msleep(10);
    }    
}
void Thread1::onFinished(){ stop = true; }
Run Code Online (Sandbox Code Playgroud)

Thread2类:

void
Thread2::run
{
    // some execution
    Thread3 t3 = new Thread3();
    connect(t3,SIGNAL(finished),this,SLOT(onFinished));
    t3->start();

    while(!stop)  // stop was initialized as false
    {
        this->msleep(10);
    }    
}
void Thread2::onFinished(){ stop = true; }
Run Code Online (Sandbox Code Playgroud)

Thread3类:

void
Thread3::run
{
    // some execution
    QMutexLocker ml(&mMutex);
}
Run Code Online (Sandbox Code Playgroud)

当我只有两个线程时,它完全正常(例如,只有thread2和thread3).在我转移到三线程场景之后,onFinished()方法似乎不再正确连接finished()信号.已经调用了thread2中的onFinished().而且我很确定thread3的执行已经完成.

谁能告诉我哪里可能做错了?

c++ qt multithreading qthread

4
推荐指数
1
解决办法
1030
查看次数

使用Qthread-Qt5创建新线程

我正在尝试创建一个新的线程gpsthread,它应该在后台运行,并存储该值.

class gpsthread: public QThread{
    Q_OBJECT
private:nrega_status_t status2;

public: 
explicit gpsthread(QObject *parent = 0):QThread(parent) {
    // QTimer *t = new QTimer(this);
    // connect(t, SIGNAL(timeout()), this, SLOT(processgps()));
    // t->start(10000);
 }
 void run(){
    qDebug()<<"inside gps thread\n";
    QTimer *t = new QTimer(this);
     connect(t, SIGNAL(timeout()), this, SLOT(processgps()));
     t->start(10000);
    }

public slots:void processgps(){
    int status2;
    status2=gps_management();
}
};
Run Code Online (Sandbox Code Playgroud)

我的主要课程是quickview.

int main(int argc, char *argv[])
{

QString file = "qml/main.qml";
QApplication app(argc, argv);
TranslationTest myObj;
QuickView view;
subthread object;
gpsthread obj;
gprsthread gprs;
view.rootContext()->setContextProperty("rootItem", (QObject *)&myObj); …
Run Code Online (Sandbox Code Playgroud)

c++ multithreading qthread qt5

4
推荐指数
1
解决办法
1万
查看次数

如何释放Qthread对象的内存?

我做过这样的事情:

//in the mainwindow's constructor
QThread *thr = new QThread;
soundWorker * work = new soundWorker;
connect(this,SIGNAL(playsound()),work,SLOT(process()));
work->moveToThread(thr);
thr->start();
Run Code Online (Sandbox Code Playgroud)

我应该删除thr并在mainwindow的解构器中工作吗?

c++ qt qthread

4
推荐指数
1
解决办法
1636
查看次数