在Python中检查当前线程是否是主线程

时间:2014-04-21 22:02:51

标签: python multithreading

之前已经回答了AndroidObjective CC++,但显然不适用于Python。如何可靠地确定当前线程是否是主线程?我可以想到一些方法,其中没有一个真正让我满意,因为它可以像threading.MainThread一样容易,如果它存在的话。

检查线程名称

主线程在threading.py中实例化,如下所示:

Thread.__init__(self, name="MainThread")

所以可以做到

if threading.current_thread().name == 'MainThread'

但是这个名字是固定的吗?我看过的其他代码检查了MainThread是否包含在帖子名称的任何位置。

存储起始线程

我可以在程序启动的那一刻存储对起始线程的引用,即当时还没有其他线程。这绝对可靠,但对于这样一个简单的查询来说太麻烦了?

有更简洁的方法吗?

3 个答案:

答案 0 :(得分:43)

threading.current_thread().name == 'MainThread'的问题在于人们总能做到:

threading.current_thread().name = 'MyName'
assert threading.current_thread().name == 'MainThread' # will fail

也许以下内容更为可靠:

threading.current_thread().__class__.__name__ == '_MainThread'

话虽如此,人们仍然可以巧妙地做到:

threading.current_thread().__class__.__name__ = 'Grrrr'
assert threading.current_thread().__class__.__name__ == '_MainThread' # will fail

但这个选择似乎仍然更好; "after all, we're all consenting adults here."

<强>更新

Python 3.4引入了threading.main_thread(),它比上面的要好得多:

assert threading.current_thread() is threading.main_thread()

更新2:

对于Python&lt; 3.4,也许最好的选择是:

isinstance(threading.current_thread(), threading._MainThread)

答案 1 :(得分:8)

这里的答案是旧的和/或坏的,所以这是当前的解决方案:

if threading.current_thread() is threading.main_thread():
    ...

此方法自Python 3.4+起可用。

答案 2 :(得分:1)

如果像我一样访问受保护的属性会为您提供Heebie-jeebies,那么您可能需要使用threading._MainThread替代suggested。在这种情况下,您可以利用only the Main Thread can handle signals的事实,因此以下内容可以完成这项工作:

import signal
def is_main_thread():
    try:
        # Backup the current signal handler
        back_up = signal.signal(signal.SIGINT, signal.SIG_DFL)
    except ValueError:
        # Only Main Thread can handle signals
        return False
    # Restore signal handler
    signal.signal(signal.SIGINT, back_up)
    return True

更新以解决@ user4815162342指出的潜在问题。