2 つの異なる Python の質問から得た回答を組み合わせようとしています。
これが最初の質問と回答です。基本的に、2 つのスレッドを生成したかっただけです。1 つは powerDown() に、もう 1 つは powerUp() に、powerUp() は powerDown() で保留されます。
Pythonで同じオブジェクトの別のスレッド内にスレッドを生成する方法は?
import threading
class Server(threading.Thread):
# some code
def run(self):
self.reboot()
# This is the top level function called by other objects
def reboot(self):
# perhaps add a lock
if not hasattr(self, "_down"):
self._down = threading.Thread(target=self.__powerDown)
self._down.start()
up = threading.Thread(target=self.__powerUp)
up.start()
def __powerDown(self):
# do something
def __powerUp(self):
if not hasattr(self, "_down"):
return
self._down.join()
# do something
del self._down
これが2番目の質問と回答です。基本的には、スレッドを開始してから、オブジェクトの関数を呼び出したいと考えていました。
import queue
import threading
class SomeClass(threading.Thread):
def __init__(self, q, loop_time = 1.0/60):
self.q = q
self.timeout = loop_time
super(SomeClass, self).__init__()
def onThread(self, function, *args, **kwargs):
self.q.put((function, args, kwargs))
def run(self):
while True:
try:
function, args, kwargs = self.q.get(timeout=self.timeout)
function(*args, **kwargs)
except queue.Empty:
self.idle()
def idle(self):
# put the code you would have put in the `run` loop here
def doSomething(self):
pass
def doSomethingElse(self):
pass
これが結合されたアイデアコードです。基本的には、スレッドを生成してから、実行する関数 (この場合は reboot()) をキューに入れたいと考えていました。次に、reboot() は、powerDown() スレッドと powerUp() スレッドの 2 つのスレッドを作成します。ここで、powerDown() は powerUp() を保留します。
import threading
import Queue
class Server(threading.Thread):
def __init__(self, q, loop_time = 1.0/60):
self.q = q
self.timeout = loop_time
super(Server, self).__init__()
def run(self):
while True:
try:
function, args, kwargs = self.q.get(timeout=self.timeout)
function(*args, **kwargs)
except queue.Empty:
self.idle()
def idle(self):
# put the code you would have put in the `run` loop here
# This is the top level function called by other objects
def reboot(self):
self.__onthread(self.__reboot)
def __reboot(self):
if not hasattr(self, "_down"):
self._down = threading.Thread(target=self.__powerDown)
self._down.start()
up = threading.Thread(target=self.__powerUp)
up.start()
def __onThread(self, function, *args, **kwargs):
self.q.put((function, args, kwargs))
def __powerDown(self):
# do something
def __powerUp(self):
if not hasattr(self, "_down"):
return
self._down.join()
# do something
del self._down
2 つのサーバー サブクラスを作成する場合を除いて、すべて動作します。
class ServerA(Server):
pass
class ServerB(Server):
pass
両方のサブクラスを開始し、start() 関数と再起動関数を呼び出すコードは次のとおりです。
serverA = ServerA(None)
serverB = ServerB(None)
serverA.start()
serverB.start()
serverA.reboot()
serverB.reboot()
serverA.reboot() と serverB.reboot() が同時に発生することを期待していますが、これは私が望んでいることですが、そうではありません! serverB.reboot() は、serverA.reboot() の実行後に実行されます。つまり、printステートメントを入れると、
serverA started
serverB started
serverA.reboot() called
serverA.__powerDown called
serverA.__powerUp called
serverB.reboot() called
serverB.__powerDown called
serverB.__powerUp called
ServerAの再起動には時間がかかるという事実を知っているので、このようなことを期待しています
serverA started
serverB started
serverA.reboot() called
serverB.reboot() called
serverA.__powerDown called
serverB.__powerDown called
serverB.__powerUp called
serverA.__powerUp called
それが理にかなっていることを願っています。もしそうなら、reboot() 関数が同時に実行されないのはなぜですか?