2010-05-07 2 views
15

Мне нужно подождать в сценарии, пока не будет выполнено определенное количество условий?Есть ли простой способ в Python дождаться определенного условия?

Я знаю, что могу катить мои собственные события с использованием переменных условий и друзей, но я не хочу испытывать трудности с его внедрением, поскольку некоторые изменения свойств объекта происходят из внешнего потока в завернутой библиотеке C++ (Boost .Python), поэтому я не могу просто захватить __setattr__ в классе и поставить там переменную условия, которая оставляет меня либо пытаться создать и сигнализировать переменную состояния Python из C++, либо обернуть собственный, и ждать на ней в Python , оба из которых звучат странно, бесполезно сложно и скучно.

Есть ли более простой способ сделать это, запрещая непрерывный опрос состояния?

В идеале было бы по линии

res = wait_until(lambda: some_predicate, timeout) 
if (not res): 
    print 'timed out' 

ответ

16

К сожалению, единственная возможность удовлетворить свои ограничения, чтобы периодически опрос, например ....:

import time 

def wait_until(somepredicate, timeout, period=0.25, *args, **kwargs): 
    mustend = time.time() + timeout 
    while time.time() < mustend: 
    if somepredicate(*args, **kwargs): return True 
    time.sleep(period) 
    return False 

или тому подобное. Это может быть оптимизировано несколькими способами, если somepredicate может быть разложен (например, если известно, что это несколько статей, особенно если некоторые из них, в свою очередь, подвержены оптимизации, будучи детектируемыми через threading.Event s или тому подобное и т. Д. И т. Д.), , но в общих чертах, о которых вы просите, этот неэффективный подход является единственным выходом.

+0

Вот что я в конечном итоге делает. К счастью, производительность не является проблемой (это тестовый скрипт). –

+0

может быть другое решение http://stackoverflow.com/a/7836454/995714 –

2

Вы в основном ответили на свой вопрос: нет.

Поскольку вы имеете дело с внешними библиотеками в boost.python, которые могут изменять объекты на досуге, вам нужно либо заставить эти процедуры вызвать обновление обработчика событий, либо работать с условием.

0

Вот потоковая продление на решение Алекса:

import time 
import threading 

# based on https://stackoverflow.com/a/2785908/1056345                                                                   
def wait_until(somepredicate, timeout, period=0.25, *args, **kwargs): 
    must_end = time.time() + timeout 
    while time.time() < must_end: 
     if somepredicate(*args, **kwargs): 
      return True 
     time.sleep(period) 
    return False 

def wait_until_par(*args, **kwargs): 
    t = threading.Thread(target=wait_until, args=args, kwargs=kwargs) 
    t.start() 
    print ('wait_until_par exits, thread runs in background') 

def test(): 
    print('test') 

wait_until_par(test, 5) 
Смежные вопросы