Return n independent iterators from a single iterable.

    Once tee() has made a split, the original iterable should not be used
    anywhere else; otherwise, the iterable could get advanced without the tee
    objects being informed.

    This itertool may require significant auxiliary storage (depending on how
    much temporary data needs to be stored). In general, if one iterator uses
    most or all of the data before another iterator starts, it is faster to use
    list() instead of tee().

def tee(iterable, n=2):
    """Return n independent iterators from a single iterable.

    Once tee() has made a split, the original iterable should not be used
    anywhere else; otherwise, the iterable could get advanced without the tee
    objects being informed.

    This itertool may require significant auxiliary storage (depending on how
    much temporary data needs to be stored). In general, if one iterator uses
    most or all of the data before another iterator starts, it is faster to use
    list() instead of tee().
    """
    tees = tuple(AsyncTeeIterable(iterable) for _ in range(n))
    for tee in tees:

        tee._siblings = tees

    return tees