2016-08-23 17 views
-2

私は、実行する一連のタスクを作成するアプリケーションを作成していますが、チェーンは、そのピースが追加されるというユーザーの希望に応じてタスクを実行します。ユーザーがstart_booしたい場合セロリで条件付きサブタスクのチェーンを作成するにはどうすればよいですか?

例えば、チェーンは次のようになります。foobazがすでに開始されている場合

def start_boo(): 
    chain = start_foo.s() | start_bar.s() | start_baz.s() 
    chain() 

しかし、我々はこれを行うにはしたくないでしょう。代わりに次のようなものを好む:

def start_boo(foo=True, bar=True, baz=True): 
    if not (foo or bar or baz): 
     raise Exception("At least one should be true...") 
    chain = None 
    if foo: 
     chain |= start_foo.s() 
    if bar: 
     chain |= start_bar.s() 
    if baz: 
     chain |= start_baz.s() 
    chain() 

start_boo(foo=False, baz=False) 

ただし、これはさまざまな理由で機能しません。

このようなことを行うイディオムはありますか?

+0

これは私の目標、私の理解、そして私の試みではかなり有効な質問です。私は質問をより良くすることができるようにdownvotesを説明してください。 – erip

答えて

1

イディオムはfunctoolsreduceの機能です。あなたは次のことができます:

def start_boo(foo=True, bar=True, baz=True): 
    if not (foo or bar or baz): 
     raise Exception("At least one should be true...") 

    todo_tasks = [foo, bar, baz] 
    start_tasks = [start_foo, start_bar, start_baz] 

    # tasks contains start tasks which should be done per the options. 
    # if it's False in todo_tasks, its associated start_task isn't added 
    tasks = [start_task for todo, start_task in zip(todo_tasks, start_tasks) if todo] 
    first_task, rest = *tasks 

    # start with the first task to be completed and chain it with remaining tasks 
    chain = functools.reduce(lambda x, y: x | y.s(), rest, first_task.s()) 
    chain() 
+0

優秀な答えですが、少し調整を加えなければなりませんでした。あなたの答えを編集します。私の編集に同意しない場合は、元気に元に戻してください。 – erip

+0

それはOkですが、私は今、それが –

+0

編集内のタスクの代わりにタスク[1:]になると信じています。再度、感謝します! – erip

関連する問題