
    MiD                         S r SSKrSSKrSSKrSSKJr  SSKJr  \R                  " \
5      r " S S\5      r " S S\5      r\R                  S
S	 j5       rg)z\Common functionality for concurrent processing. The main entry point is :func:`create_pool`.    N)deque)ThreadPoolExecutorc                   (    \ rS rSrSrSSS.S jrSrg)r      z+Subclass with a lazy consuming imap method.N   )timeoutqueued_tasks_per_workerc             '   @  ^^#    [        5       U R                  US-   -  peUR                  UR                  U R                  smpxUU4S jn	[        U6  H,  n
U" U" U/U
Q76 5        [        U5      U:X  d  M#  U	" 5       v   M.     U(       a  U	" 5       v   U(       a  M  gg7f)a_  Ordered imap that consumes iterables just-in-time.

References:
    https://gist.github.com/ddelange/c98b05437f80e4b16bf4fc20fde9c999

Args:
    fn: Function to apply.
    iterables: One (or more) iterable(s) to pass to fn (using zip) as positional argument(s).
    timeout: Per-future result retrieval timeout in seconds.
    queued_tasks_per_worker: Amount of additional items per worker to fetch from iterables to
            fill the queue: this determines the total queue size.
        Setting 0 will result in a true just-in-time behaviour: when a worker finishes a task,
            it waits until a result is consumed from the imap generator, at which point next()
            is called on the input iterable(s) and a new task is submitted.
        Default 2 ensures there is always some work to pick up. Note that at imap startup,
            the queue will fill up before the first yield occurs.

Example:
    long_generator = itertools.count()
    with ThreadPoolExecutor(42) as pool:
        result_generator = pool.imap(fn, long_generator)
        for result in result_generator:
            print(result)
   c                  0   > T " 5       R                  T5      $ )z8Block until the next task is done and return the result.)result)popleftr   s   p/var/www/eduai.edurigo.com/storigo/production/storigo_env/lib/python3.13/site-packages/smart_open/concurrency.pyget$ThreadPoolExecutor.imap.<locals>.get3   s    9##G,,    N)r   _max_workersr   appendsubmitziplen)selffnr   r	   	iterablesfuturesmaxlenr   r   r   argsr   s     `        @r   imapThreadPoolExecutor.imap   s     2  '4#4#48ORS8S#T")//7>>4;;	- OD6"$t$%7|v%e $
 %K gs   A.B6$BB )__name__
__module____qualname____firstlineno____doc__r   __static_attributes__r    r   r   r   r      s    5+/ & &r   r   c                   *    \ rS rSrSrS rS rS rSrg)ConcurrentFuturesPoolD   z_A class that mimics multiprocessing.pool.Pool but uses concurrent futures instead of processes.c                      [        US9U l        g )Nmax_workers)r   executor)r   r,   s     r   __init__ConcurrentFuturesPool.__init__F   s    *{Cr   c              #      #    U Vs/ s H  o0R                   R                  X5      PM     nn[        R                  R	                  U5       H  nUR                  5       v   M     g s  snf 7f)N)r-   r   
concurrentr   as_completedr   )r   functionitemsitemr   futures         r   imap_unordered$ConcurrentFuturesPool.imap_unorderedI   sS     DIJED==''7EJ ((55g>F--/! ? Ks   A+$A&A A+c                 6    U R                   R                  SS9  g )NT)wait)r-   shutdown)r   s    r   	terminateConcurrentFuturesPool.terminateN   s    D)r   )r-   N)	r!   r"   r#   r$   r%   r.   r7   r<   r&   r    r   r   r(   r(   D   s    iD"
*r   r(   c              #   r   #    [         R                  SU 5        [        U S9nUv   UR                  5         g 7f)Nz0creating concurrent futures pool with %i workersr+   )loggerinfor(   r<   )	processespools     r   create_poolrC   R   s-     
KKBIN Y7D
JNNs   57)r   )r%   concurrent.futuresr1   
contextlibloggingcollectionsr   r   _ThreadPoolExecutor	getLoggerr!   r?   objectr(   contextmanagerrC   r    r   r   <module>rL      s^    c     H			8	$), )`*F *  r   