Я новичок в asyncio (используется с python3.4), и я не уверен, что использую его как нужно. Я видел в this thread, что его можно использовать для выполнения функции каждые n секунд (в моем случае ms) без необходимости погружения в потоки.Использование цикла событий asyncio рекурсивно
Я использую его для получения данных от лазерных датчиков через базовый последовательный протокол каждые n мс до тех пор, пока не получу m выборок.
Вот определение из моих функций:
def countDown(self,
loop,
funcToDo,
*args,
counter = [ 1 ],
**kwargs):
""" At every call, it executes funcToDo (pass it args and kwargs)
and count down from counter to 0. Then, it stop loop """
if counter[ 0 ] == 0:
loop.stop()
else:
funcToDo(*args, **kwargs)
counter[ 0 ] -= 1
def _frangeGen(self, start = 0, stop = None, step = 1):
""" use to generate a time frange from start to stop by step step """
while stop is None or start < stop:
yield start
start += step
def callEvery(self,
loop,
interval,
funcToCall,
*args,
now = True,
**kwargs):
""" repeat funcToCall every interval sec in loop object """
nb = kwargs.get('counter', [ 1000 ])
def repeat(now = True,
times = self._frangeGen(start = loop.time(),
stop=loop.time()+nb[0]*interval,
step = interval)):
if now:
funcToCall(*args, **kwargs)
loop.call_at(next(times), repeat)
repeat(now = now)
И это, как я использую его (getAllData это функция, управление последовательной связи):
ts = 0.01
nbOfSamples = 1000
loop = asyncio.get_event_loop()
callEvery(loop, ts, countDown, loop, getAllData, counter = [nbOfSamples])
loop.run_forever()
Я хочу поставить этот блок в функцию и называть ее так часто, как я хочу, примерно так:
for i in range(nbOfMeasures):
myFunction()
processData()
Но секция Тест ond не вызывает getAllData 1000 раз, только дважды, иногда три раза. Интересный факт - один раз в два, я получаю столько данных, сколько хочу. Я действительно не понимаю, и я не могу найти что-либо в документах, поэтому я прошу вас о помощи. Любое объяснение или более простой способ сделать это с радостью приветствуется :)
Я не изучил ваш код в глубину, однако, возможно, в вашем случае просто вызвать funcToCall, запустив его внутри задачи asyncio.async()? Вы можете использовать функцию asyncio.sleep() внутри цикла True внутри вашего funcToCall, чтобы позволить ему «спать» на заданную продолжительность. Просто создайте столько задач, сколько вам нужно, и они будут эффективно запускаться одновременно в одном цикле. – shongololo