スレッドデコレータ[Python]

Oct 27 2020

Pythonソケットとスレッドライブラリを使用して簡単なプログラムを作成しようとしています。デコレータを使用して次の手順を自動化したいと思います。

t = threading.Thread(target=function, args=(arg1, arg2))
t.start()

プログラムはOOPを使用して構造化されているため、メインサブクラス内にすべてのデコレータを含むサブクラスを定義しました(この記事でこのメソッドについて読みました: https://medium.com/@vadimpushtaev/decorator-inside-python-class-1e74d23107f6)。したがって、私はこのような状況にあります:

class Server(object):

    class Decorators(object):

        @classmethod
        def threaded_decorator(cls, function):
            def inner_function():
                function_thread = threading.Thread(target=function)
                function_thread.start()
            return inner_function

    def __init__(self, other_arguments):
        # other code
        pass

    @Decorators.threaded_decorator
    def function_to_be_threaded(self):
        # other code
        pass

しかし、実行しようとすると、次のエラーが発生しますTypeError: function_to_be_threaded() missing one required argument: 'self'。どういうわけか関数self.function_to_be_threaded全体を渡さないthreading.Thread(target = function)を呼び出すと、問題がその部分にあると思われます。したがって、これを修正する方法を知っている場合は、教えていただけますか?また、Threadクラスに次のように渡される引数を受け入れるデコレータを実装する方法があるかどうか教えてくださいargs=(arguments_of_the_decorator)

どうもありがとうございました。英語を失礼します。まだ練習中です。

回答

1 napuzba Oct 27 2020 at 15:15

*args構文を使用して引数を移動します。つまり、を使用*argsしてすべての位置引数をタプルとして収集し、として移動しthreading.Threadますargs

import threading
import time
class Server(object):

    class Decorators(object):

        @classmethod
        def threaded_decorator(cls, function):
            def inner_function(*args):
                function_thread = threading.Thread(target=function,args=args)
                function_thread.start()
            return inner_function

    def __init__(self, count,sleep):
        self.count = count
        self.sleep = sleep

    @Decorators.threaded_decorator
    def function_to_be_threaded(self,id):
        for xx in range(self.count):
            time.sleep(self.sleep)
            print("{} ==> {}".format(id,xx))
           

>>> Server(6,1).function_to_be_threaded('a')
>>> Server(2,3).function_to_be_threaded('b')

a ==> 0
a ==> 1
a ==> 2
b ==> 0
a ==> 3
a ==> 4
a ==> 5
b ==> 1

ある関数から別の関数に引数を渡すにはどうすればよいですか?も参照してください。