Map func on a list using gevent greenlets.

    :param func: function applied on iterable elements
    :type func: function
    :param iterable: elements to map the function over
    :type iterable: iterable
    :param args: arguments of func
    :type args: tuple
    :param kwargs: keyword arguments of func
    :type kwargs: dict
    :param workers: limit the number of greenlets
                    running in parrallel
    :type workers: int

def parallel_map(func, iterable, args=None, kwargs=None, workers=None):
    """Map func on a list using gevent greenlets.

    :param func: function applied on iterable elements
    :type func: function
    :param iterable: elements to map the function over
    :type iterable: iterable
    :param args: arguments of func
    :type args: tuple
    :param kwargs: keyword arguments of func
    :type kwargs: dict
    :param workers: limit the number of greenlets
                    running in parrallel
    :type workers: int
    """
    if args is None:
        args = ()
    if kwargs is None:
        kwargs = {}
    if workers is not None:
        pool = Pool(workers)
    else:
        pool = Group()
    iterable = [pool.spawn(func, i, *args, **kwargs) for i in iterable]
    pool.join(raise_error=True)
    for idx, i in enumerate(iterable):
        i_type = type(i.get())
        i_value = i.get()
        if issubclass(i_type, BaseException):
            raise i_value
        iterable[idx] = i_value
    return iterable