22
33
44class QueueEmpty (Exception ):
5+ """Raised when Queue.get_nowait() is called on an empty Queue."""
56 pass
67
78
89class QueueFull (Exception ):
10+ """Raised when the Queue.put_nowait() method is called on a full Queue."""
911 pass
1012
1113
1214class Queue :
15+ """
16+ A queue, useful for coordinating producer and consumer coroutines.
17+
18+ If maxsize is less than or equal to zero, the queue size is infinite. If it
19+ is an integer greater than 0, then "await put()" will block when the
20+ queue reaches maxsize, until an item is removed by get().
21+
22+ Unlike CPython's asyncio.Queue, this implementation is backed by a list rather
23+ than `collections.deque` because smaller boards may not have the library
24+ implemented.
25+ """
26+
1327 def __init__ (self , maxsize = 0 ):
1428 self .maxsize = maxsize
15- self ._queue = list ()
29+
30+ self ._queue = []
1631
1732 self ._join_counter = 0
1833 self ._join_event = event .Event ()
@@ -37,41 +52,86 @@ def _put(self, val):
3752 self ._put_event .clear ()
3853
3954 async def get (self ):
55+ """
56+ Remove and return an item from the queue.
57+
58+ If queue is empty, wait until an item is available.
59+ """
4060 while self .empty ():
4161 await self ._put_event .wait ()
4262 return self ._get ()
4363
4464 def get_nowait (self ):
65+ """
66+ Remove and return an item from the queue.
67+
68+ If queue is empty, raise QueueEmpty.
69+ """
4570 if self .empty ():
4671 raise QueueEmpty ()
4772 return self ._get ()
4873
4974 async def put (self , val ):
75+ """
76+ Put an item into the queue.
77+
78+ If the queue is full, waits until a free
79+ slot is available before adding item.
80+ """
5081 while self .full ():
5182 await self ._get_event .wait ()
5283 self ._put (val )
5384
5485 def put_nowait (self , val ):
86+ """
87+ Put an item into the queue.
88+
89+ If the queue is full, raises QueueFull.
90+ """
5591 if self .full ():
5692 raise QueueFull ()
5793 self ._put (val )
5894
5995 def qsize (self ):
96+ """
97+ Number of items in this queue.
98+ """
6099 return len (self ._queue )
61100
62101 def empty (self ):
102+ """
103+ Return True if the queue is empty.
104+ """
63105 return len (self ._queue ) == 0
64106
65107 def full (self ):
108+ """
109+ Return True if there are maxsize items in the queue.
110+ """
66111 return 0 < self .maxsize <= self .qsize ()
67112
68113 def task_done (self ):
69- self ._join_counter -= 1
114+ """
115+ Indicate that a formerly enqueued task is complete.
116+
117+ If a join() is currently blocking, it will resume when all items have
118+ been processed (meaning that a task_done() call was received for every
119+ item that had been put() into the queue).
70120
71- if self ._join_counter <= 0 :
121+ Raises ValueError if called more times than there were items placed in
122+ the queue.
123+ """
124+ if self ._join_counter == 0 :
72125 # Can't have less than 0
73- self ._join_counter = 0
126+ raise ValueError ("task_done() called too many times" )
127+
128+ self ._join_counter -= 1
129+
130+ if self ._join_counter == 0 :
74131 self ._join_event .set ()
75132
76133 async def join (self ):
134+ """
135+ Block until all items in the queue have been gotten and processed.
136+ """
77137 await self ._join_event .wait ()
0 commit comments