简体   繁体   中英

“AssertionError: Thread.__init__() not called” when initializing a subclass of threading.Thread

I would like to make a program which runs two threads which can be simultaneously interrupted using ctrl + C . The following script is a simplified version of this:

import time
import threading

class Controller(object):
    def __init__(self, name=None):
        self.name = name

    def run_once(self):
        print("Controller {} is running once...".format(self.name))

    def run_forever(self):
        while True:
            self.run_once()
            time.sleep(1)

if __name__ == "__main__":
    controller1 = Controller(name="1")
    controller2 = Controller(name="2")
    thread1 = threading.Thread(target=controller1.run_forever)
    thread2 = threading.Thread(target=controller2.run_forever)
    thread1.daemon = True
    thread2.daemon = True
    thread1.start()
    thread2.start()


    try:
        while True:
            thread1.join(1)
            thread2.join(1)
            if not thread1.isAlive() or not thread2.isAlive():
                break
    except KeyboardInterrupt:
        pass

I'm trying to make the code a bit more DRY by doing the following:

import time
import threading

class Controller(object):
    def __init__(self, name=None):
        self.name = name

    def run_once(self):
        print("Controller {} is running once...".format(self.name))

    def run_forever(self):
        while True:
            self.run_once()
            time.sleep(1)

class ThreadController(Controller, threading.Thread):
    def __init__(self, *args, **kwargs):
        Controller.__init__(self, *args, **kwargs)
        threading.Thread.__init__(self, target=self.run_forever)
        self.daemon = True
        self.start()


if __name__ == "__main__":
    thread1 = ThreadController(name="1")
    thread2 = ThreadController(name="2")

    try:
        while True:
            thread1.join(1)
            thread2.join(1)
            if not thread1.isAlive() or not thread2.isAlive():
                break
    except KeyboardInterrupt:
        pass

However, when I try to run the latter script, I get the following error:

Traceback (most recent call last):
  File "threading_test3.py", line 34, in <module>
    thread1 = ThreadController(name="1")
  File "threading_test3.py", line 18, in __init__
    Controller.__init__(self, *args, **kwargs)
  File "threading_test3.py", line 6, in __init__
    self.name = name
  File "/usr/lib/python2.7/threading.py", line 971, in name
    assert self.__initialized, "Thread.__init__() not called"
AssertionError: Thread.__init__() not called

I don't understand why Thread.__init__() is not called, because it seems like it is called in the __init__ of ThreadController . What is causing this error?

Call Thread's init, first;

class ThreadController(Controller, threading.Thread):
    def __init__(self, *args, **kwargs):
        threading.Thread.__init__(self, target=self.run_forever)
        Controller.__init__(self, *args, **kwargs)
        self.daemon = True
        self.start()

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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