简体   繁体   English

为什么Windows上的Tkinter堆栈溢出?

[英]Why does Tkinter stack overflow on Windows?

This short Python script debugwin.py works great on my Linux machine: 这个简短的Python脚本debugwin.py在我的Linux机器上运行良好:

>>> import debugwin
>>> l = []
>>> debuwin.watch(l)
0
>>> l.append(1)

However, people have told me that on Windows (Python 2.7.3 Windows 7) it sometimes doesn't update after you append, and sometimes gets a stack overflow: 然而, 有人告诉我 ,在Windows(Python 2.7.3 Windows 7)上,它有时在你追加后不会更新,有时会出现堆栈溢出:

>>> error in background error handler:
    out of stack space (infinite loop?) while executing "::tcl::Bgerror {out of stack
    space (infinite loop?)} {-code 1 -level 0 -errorcode NONE -errorinfo {out of stack
    space (infinite loop?)Unable to format..."

How can the script overflow? 脚本如何溢出?

It can overflow if the code that was written to report a bug has a bug. 如果为报告错误而编写的代码有错误,它可能会溢出。 When it tries to report a bug it calls the bug reporting code, but it has a bug so it tries to call the bug reporting code, ... I'm not saying that's the problem, but that's at least one way to get what you're seeing. 当它试图报告错误时它调用错误报告代码,但它有一个错误,所以它试图调用错误报告代码,...我不是说这是问题,但这至少是一种方法来获得什么你看到了。

I'm not particularly surprised you get crashes with the debugwin.py code you linked to (at least, the version of that code at the time I write this). 使用你链接到的debugwin.py代码崩溃我并不是特别感到惊讶(至少在我写这篇文章的时候是代码的版本)。 Tkinter isn't thread safe, and conventional wisdom is that it should only be run in the main thread of an application. Tkinter不是线程安全的,传统的观点是它应该只在应用程序的主线程中运行。 It looks like the code creates a tk interpreter in a sub-thread. 看起来代码在子线程中创建了一个tk解释器。 So, even if there's no bug in the bug reporting code, the fact that the tcl interpreter is running in a sub-thread makes me think it could be thread-related. 因此,即使错误报告代码中没有错误,tcl解释器在子线程中运行的事实使我认为它可能与线程相关。 Certainly, the fact that the crash seems random leads me to believe it's related to threading. 当然,崩溃似乎是随机的这一事实让我相信它与线程有关。

I see another thing that looks somewhat suspicious. 我看到另一件看起来有点可疑的事情。 All widgets have an update method which calls the standard tk update command. 所有小部件都有一个调用标准tk update命令的update方法。 You have a widget that inherits from Label, and you created your own update method. 您有一个继承自Label的小部件,并且您创建了自己的update方法。 That may not cause any problems, but it's a code smell. 这可能不会导致任何问题,但这是代码味道。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM