Skip to content

Instantly share code, notes, and snippets.

@pushkarnimkar
Last active July 23, 2019 09:25
Show Gist options
  • Save pushkarnimkar/2070a142a7d47580af348831fdd249ef to your computer and use it in GitHub Desktop.
Save pushkarnimkar/2070a142a7d47580af348831fdd249ef to your computer and use it in GitHub Desktop.
This gist is sample code for a question posted on stackoverflow related to working of Future.set_result function in multi-threaded setting. https://stackoverflow.com/questions/57144657/unable-to-understand-behavior-of-future-set-result-on-futures-in-another-thread
import asyncio
import threading
from typing import Dict
import numpy as np
import time
# import logging
# logging.basicConfig(level=logging.DEBUG)
def read():
delay = np.round(np.random.uniform(0.5, 1), 3)
time.sleep(delay)
choice = np.random.choice((3, 6, 9))
# logging.debug("choice %d delay %f", choice, delay)
return choice, delay
class RandomReader:
def __init__(self):
self.loop = asyncio.get_event_loop()
self.service = 3
self.thread = threading.Thread(target=self.reader)
self.thread.start()
self.futures: Dict[int, asyncio.Future] = {}
def reader(self):
while self.service != 0:
k, v = read()
if k in self.futures:
if self.futures[k].done():
continue
self.loop.call_soon_threadsafe(self.futures[k].set_result, v)
self.service -= 1
async def wait(self, v: int):
self.futures[v] = self.loop.create_future()
a = await self.futures[v]
# logging.debug("value %d received %f", v, a)
return v, a
async def main():
reader = RandomReader()
t1 = asyncio.create_task(reader.wait(3))
print(await t1)
t2 = asyncio.create_task(reader.wait(6))
t3 = asyncio.create_task(reader.wait(9))
print(await t2)
print(await t3)
reader.thread.join()
if __name__ == '__main__':
loop_ = asyncio.get_event_loop()
loop_.run_until_complete(main())
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment