Beispiel #1
0
        public static IEnumerable <int> Range(int start, int count)
        {
            long max = ((long)start) + count - 1;

            if (count < 0 || max > Int32.MaxValue)
            {
                throw Error.ArgumentOutOfRange("count");
            }
            if (count == 0)
            {
                return(new EmptyPartition <int>());
            }
            return(new RangeIterator(start, count));
        }
Beispiel #2
0
        public static IEnumerable <TResult> Repeat <TResult>(TResult element, int count)
        {
            if (count < 0)
            {
                throw Error.ArgumentOutOfRange(nameof(count));
            }

            if (count == 0)
            {
                return(EmptyPartition <TResult> .Instance);
            }

            return(new RepeatIterator <TResult>(element, count));
        }
Beispiel #3
0
 TElement IList <TElement> .this[int index]
 {
     get
     {
         if (index < 0 || index >= count)
         {
             throw Error.ArgumentOutOfRange("index");
         }
         return(elements[index]);
     }
     set
     {
         throw Error.NotSupported();
     }
 }
Beispiel #4
0
        /// <summary>
        /// Applies a timeout policy for each element in the async-enumerable sequence.
        /// If the next element isn't received within the specified timeout duration starting from its predecessor, a TimeoutException is propagated to the observer.
        /// </summary>
        /// <typeparam name="TSource">The type of the elements in the source sequence.</typeparam>
        /// <param name="source">Source sequence to perform a timeout for.</param>
        /// <param name="timeout">Maximum duration between values before a timeout occurs.</param>
        /// <returns>The source sequence with a TimeoutException in case of a timeout.</returns>
        /// <exception cref="ArgumentNullException"><paramref name="source"/> is null.</exception>
        /// <exception cref="ArgumentOutOfRangeException"><paramref name="timeout"/> is less than TimeSpan.Zero.</exception>
        /// <exception cref="TimeoutException">(Asynchronous) If no element is produced within <paramref name="timeout"/> from the previous element.</exception>
        /// <remarks>
        /// <para>
        /// In case you only want to timeout on the first element, consider using the <see cref="Amb{TSource}(IAsyncEnumerable{TSource}, IAsyncEnumerable{TSource})"/>
        /// operator applied to the source sequence and a delayed <see cref="Throw{TResult}(Exception)"/> sequence.
        /// <!-- FIXME: Timeout with initial and per item timeout option not implemented yet.
        /// Alternatively, the general-purpose overload
        /// of Timeout, <see cref="Timeout{TSource, TTimeout}(IObservable{TSource}, IObservable{TTimeout}, Func{TSource, IObservable{TTimeout}})"/> can be used.
        /// -->
        /// </para>
        /// <para>
        /// Specifying a TimeSpan.Zero value for <paramref name="timeout"/> is not recommended but supported, causing timeout timers to be scheduled that are due
        /// immediately. However, this doesn't guarantee a timeout will occur, even for the first element. This is a side-effect of the asynchrony introduced by the
        /// scheduler, where the action to propagate a timeout may not execute immediately, despite the TimeSpan.Zero due time. In such cases, the next element may
        /// arrive before the scheduler gets a chance to run the timeout action.
        /// </para>
        /// </remarks>
        public static IAsyncEnumerable <TSource> Timeout <TSource>(this IAsyncEnumerable <TSource> source, TimeSpan timeout)
        {
            if (source == null)
            {
                throw Error.ArgumentNull(nameof(source));
            }

            var num = (long)timeout.TotalMilliseconds;

            if (num < -1L || num > int.MaxValue)
            {
                throw Error.ArgumentOutOfRange(nameof(timeout));
            }

            return(new TimeoutAsyncIterator <TSource>(source, timeout));
        }
Beispiel #5
0
        public static IEnumerable <int> Range(int start, int count)
        {
            long max = ((long)start) + count - 1;

            if (count < 0 || max > int.MaxValue)
            {
                throw Error.ArgumentOutOfRange(nameof(count));
            }

            if (count == 0)
            {
                return(Empty <int>());
            }

            return(new RangeIterator(start, count));
        }
Beispiel #6
0
        public static IAsyncEnumerable <IList <TSource> > Buffer <TSource>(this IAsyncEnumerable <TSource> source, int count, int skip)
        {
            if (source == null)
            {
                throw Error.ArgumentNull(nameof(source));
            }
            if (count <= 0)
            {
                throw Error.ArgumentOutOfRange(nameof(count));
            }
            if (skip <= 0)
            {
                throw Error.ArgumentOutOfRange(nameof(skip));
            }

            return(AsyncEnumerable.Create(Core));

            async IAsyncEnumerator <IList <TSource> > Core(CancellationToken cancellationToken)
            {
                var buffers = new Queue <IList <TSource> >();

                var index = 0;

                await foreach (var item in source.WithCancellation(cancellationToken).ConfigureAwait(false))
                {
                    if (index++ % skip == 0)
                    {
                        buffers.Enqueue(new List <TSource>(count));
                    }

                    foreach (var buffer in buffers)
                    {
                        buffer.Add(item);
                    }

                    if (buffers.Count > 0 && buffers.Peek().Count == count)
                    {
                        yield return(buffers.Dequeue());
                    }
                }

                while (buffers.Count > 0)
                {
                    yield return(buffers.Dequeue());
                }
            }
        }
Beispiel #7
0
        public static TSource ElementAt <TSource>(this IEnumerable <TSource> source, int index)
        {
            if (source == null)
            {
                throw Error.ArgumentNull(nameof(source));
            }

            IPartition <TSource> partition = source as IPartition <TSource>;

            if (partition != null)
            {
                bool    found;
                TSource element = partition.TryGetElementAt(index, out found);
                if (found)
                {
                    return(element);
                }
            }
            else
            {
                IList <TSource> list = source as IList <TSource>;
                if (list != null)
                {
                    return(list[index]);
                }

                if (index >= 0)
                {
                    using (IEnumerator <TSource> e = source.GetEnumerator())
                    {
                        while (e.MoveNext())
                        {
                            if (index == 0)
                            {
                                return(e.Current);
                            }

                            index--;
                        }
                    }
                }
            }

            throw Error.ArgumentOutOfRange(nameof(index));
        }
Beispiel #8
0
        public static IAsyncEnumerable <int> Range(int start, int count)
        {
            if (count < 0)
            {
                throw Error.ArgumentOutOfRange(nameof(count));
            }

            var end = (long)start + count - 1L;

            if (end > int.MaxValue)
            {
                throw Error.ArgumentOutOfRange(nameof(count));
            }

            if (count == 0)
            {
                return(Empty <int>());
            }

            return(new RangeAsyncIterator(start, count));
        }
Beispiel #9
0
        public static IAsyncEnumerable <IList <TSource> > Buffer <TSource>(this IAsyncEnumerable <TSource> source, int count)
        {
            if (source == null)
            {
                throw Error.ArgumentNull(nameof(source));
            }
            if (count <= 0)
            {
                throw Error.ArgumentOutOfRange(nameof(count));
            }

#if USE_ASYNC_ITERATOR
            return(AsyncEnumerable.Create(Core));

            async IAsyncEnumerator <IList <TSource> > Core(CancellationToken cancellationToken)
            {
                var buffer = new List <TSource>(count);

                await foreach (var item in AsyncEnumerableExtensions.WithCancellation(source, cancellationToken).ConfigureAwait(false))
                {
                    buffer.Add(item);

                    if (buffer.Count == count)
                    {
                        yield return(buffer);

                        buffer = new List <TSource>(count);
                    }
                }

                if (buffer.Count > 0)
                {
                    yield return(buffer);
                }
            }
#else
            return(new BufferAsyncIterator <TSource>(source, count, count));
#endif
        }
Beispiel #10
0
            static async ValueTask <TSource> Core(IAsyncEnumerable <TSource> _source, int _index, CancellationToken _cancellationToken)
            {
                if (_source is IAsyncPartition <TSource> p)
                {
                    var first = await p.TryGetElementAtAsync(_index, _cancellationToken).ConfigureAwait(false);

                    if (first.HasValue)
                    {
                        return(first.Value);
                    }
                }
                else
                {
                    if (_source is IList <TSource> list)
                    {
                        return(list[_index]);
                    }

                    if (_index >= 0)
                    {
                        await foreach (var item in AsyncEnumerableExtensions.WithCancellation(_source, _cancellationToken).ConfigureAwait(false))
                        {
                            if (_index == 0)
                            {
                                return(item);
                            }

                            _index--;
                        }
                    }
                }

                // NB: Even though index is captured, no closure is created.
                //     The nameof expression is lowered to a literal prior to creating closures.

                throw Error.ArgumentOutOfRange(nameof(index));
            }
Beispiel #11
0
        /// <summary>
        /// Repeats the async-enumerable sequence a specified number of times.
        /// </summary>
        /// <typeparam name="TSource">The type of the elements in the source sequence.</typeparam>
        /// <param name="source">Observable sequence to repeat.</param>
        /// <param name="count">Number of times to repeat the sequence.</param>
        /// <returns>The async-enumerable sequence producing the elements of the given sequence repeatedly.</returns>
        /// <exception cref="ArgumentNullException"><paramref name="source"/> is null.</exception>
        /// <exception cref="ArgumentOutOfRangeException"><paramref name="count"/> is less than zero.</exception>
        public static IAsyncEnumerable <TSource> Repeat <TSource>(this IAsyncEnumerable <TSource> source, int count)
        {
            if (source == null)
            {
                throw Error.ArgumentNull(nameof(source));
            }
            if (count < 0)
            {
                throw Error.ArgumentOutOfRange(nameof(count));
            }

            return(AsyncEnumerable.Create(Core));

            async IAsyncEnumerator <TSource> Core(CancellationToken cancellationToken)
            {
                for (var i = 0; i < count; i++)
                {
                    await foreach (var item in source.WithCancellation(cancellationToken).ConfigureAwait(false))
                    {
                        yield return(item);
                    }
                }
            }
        }
Beispiel #12
0
 public TElement ElementAt(int index)
 {
     throw Error.ArgumentOutOfRange("index");
 }