在pyQt5而不是pyQt4退出时的分段故障 [英] Segmentation fault on exit in pyQt5 but not pyQt4

查看:973
本文介绍了在pyQt5而不是pyQt4退出时的分段故障的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

此回答在退出时发生崩溃的解决方法适用于pyqt4。

The workaround to a crash upon exit given in this answer works in pyqt4.

但不使用pyqt5,其中常常有一半以上的分段错误。

But not using pyqt5, where there is often (more than half the times) a segmentation fault.

只有导入行被修改

#!/usr/bin/python

import sys

#toolkit = "Qt4"
toolkit = "Qt5"
if toolkit == "Qt4":
  # Qt4 (no crash)
  from PyQt4.QtCore import *
  from PyQt4.QtGui import *
elif toolkit == "Qt5":
  # Qt5 (crash)
  from PyQt5.QtWidgets import (
    QApplication, QGraphicsScene, QGraphicsView
  )


app = QApplication(sys.argv)

grview = QGraphicsView()

# no crash
scene = QGraphicsScene(parent=grview)

grview.setScene(scene)

grview.show()

sys.exit(app.exec_())

这里是backtrace,从核心转储(as

Here is the backtrace, from the core dump (as a side note, inside gdb, there is no crash)

[New LWP 4684]
[New LWP 4683]
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib64/libthread_db.so.1".
Core was generated by `python grview_qt5.py'.
Program terminated with signal SIGSEGV, Segmentation fault.
#0  0x00007f5233393e69 in ?? ()
(gdb) bt
#0  0x00007f5233393e69 in  ()
#1  0x00007f522fee6f20 in  ()
#2  0x0000000000e0d340 in  ()
#3  0x00007f522fee6f20 in  ()
#4  0x0000000000e0d5f0 in  ()
#5  0x00007f523e0bc000 in _rtld_local () at /lib64/ld-linux-x86-64.so.2
#6  0x00007f523ae7285f in QThreadPrivate::start(void*) (arg=0xe0d340) at thread/qthread_unix.cpp:337
#7  0x00007f523d8780a4 in start_thread (arg=0x7f522fee7700) at pthread_create.c:309
#8  0x00007f523d5adcbd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:111
(gdb) info threads
  Id   Target Id         Frame 
  2    Thread 0x7f523e06f700 (LWP 4683) 0x00007f523deb21c7 in munmap () at ../sysdeps/unix/syscall-template.S:81
* 1    Thread 0x7f522fee7700 (LWP 4684) 0x00007f5233393e69 in ?? ()

为什么pyqt4和pyqt5之间有区别?

Why the difference between pyqt4 and pyqt5 ?

这当然与退出时的对象破坏有关,但是如何?

避免此崩溃的正确方法是什么?

What is the correct way to avoid this crash ?

推荐答案

我无法使用Fedora 24的PyQt来使你的示例崩溃。

I cannot make your example crash using Fedora 24's PyQt.

然而,我也看到这个问题,在python退出之前清理Qt对象。我的应用程序有1000的Qt对象,我不能清楚hopw我将跟踪所有的对象,未能清理。

However I am also seeing this problem and do not have a definitive answer on how to clean up Qt objects before python exits. My app has 1000's of Qt objects and I'm not at all clear on hopw I will track down all the objects that fail to clean up.

我认为密钥是您必须以相反的构造顺序删除所有已创建的对象。注意从具有对其他对象的引用的任何Qt对象中删除对象。例如布局中的小部件。

I think the key is that you have to delete all the objects you have created in the reverse order of construction. Taking care to remove objects from any Qt object that has a reference to an other object. e.g widgets in a layout.

正如我在评论中说的,差异来自于从python2到python3的变化,对象删除和垃圾回收。

As I said in the comment the difference comes from changes from python2 to python3 to do with object deletion and garbage collection.

使用sys.exit()避免清理不够好。

Using sys.exit() to avoid the clean up is not good enough.

您需要使用os._exit ),这将防止python运行onitit处理程序。这更有可能抑制seg故障。但你需要确保任何重要的onExit处理程序运行。例如要删除临时文件。

You need to use os._exit( code ) which will prevent python from running onExit handlers. That is more likely to suppress the seg fault. But you will need to make sure that any important onExit handlers are run. For example to delete temp files.

尝试退出,查看是否会出现问题。

Try exiting like this and see if for you the problem goes away.

grview.show()
rc = app.exec_()

del grview
del scene
del app

sys.exit( rc )

这篇关于在pyQt5而不是pyQt4退出时的分段故障的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆