Example #1
0
        /// <summary>
        /// Removes and returns an item from one of the specified collections in an asynchronous manner.
        /// </summary>
        public static ValueTask <AnyResult <T> > TakeFromAnyAsync(AsyncCollection <T>[] collections, CancellationToken cancellationToken)
        {
            if (collections == null)
            {
                throw new ArgumentNullException("collections");
            }

            if (collections.Length <= 0 || collections.Length > TakeFromAnyMaxCollections)
            {
                throw new ArgumentException(String.Format("The collection array can't contain less than 1 or more than {0} collections.", TakeFromAnyMaxCollections), "collections");
            }

            if (cancellationToken.IsCancellationRequested)
            {
                return(CanceledValueTask <AnyResult <T> > .Value);
            }

            ExclusiveCompletionSourceGroup <T> exclusiveSources = new ExclusiveCompletionSourceGroup <T>();

            //	Fast route: we attempt to take from the top-priority queues that have any items.
            //	If the fast route succeeds, we avoid allocating and queueing a bunch of awaiters.
            for (int i = 0; i < collections.Length; i++)
            {
                if (collections[i].Count > 0)
                {
                    AnyResult <T>?result = TryTakeFast(exclusiveSources, collections[i], i);
                    if (result.HasValue)
                    {
                        return(new ValueTask <AnyResult <T> >(result.Value));
                    }
                }
            }

            //	No luck during the fast route; just queue the rest of awaiters.
            for (int i = 0; i < collections.Length; i++)
            {
                AnyResult <T>?result = TryTakeFast(exclusiveSources, collections[i], i);
                if (result.HasValue)
                {
                    return(new ValueTask <AnyResult <T> >(result.Value));
                }
            }

            //	None of the collections had any items. The order doesn't matter anymore, it's time to start the competition.
            exclusiveSources.UnlockCompetition(cancellationToken);
            return(new ValueTask <AnyResult <T> >(exclusiveSources.Task));
        }
Example #2
0
 public bool Equals(AnyResult <T> other) => EqualityComparer <T> .Default.Equals(Value, other.Value) && EqualityComparer <int> .Default.Equals(CollectionIndex, other.CollectionIndex);