예제 #1
0
        /// <summary>
        /// Gets the number of items in this and subsequent nodes by walking the linked list.
        /// </summary>
        public int GetCount()
        {
            int count = 0;

            for (SingleLinkedNode <TSource> node = this; node != null; node = node.Linked)
            {
                count++;
            }

            return(count);
        }
예제 #2
0
        /// <summary>
        /// Gets the node at a logical index by walking the linked list.
        /// </summary>
        /// <param name="index">The logical index.</param>
        /// <remarks>
        /// The caller should make sure <paramref name="index"/> is less than this node's count.
        /// </remarks>
        public SingleLinkedNode <TSource> GetNode(int index)
        {
            Debug.Assert(index >= 0 && index < GetCount());

            SingleLinkedNode <TSource> node = this;

            for (; index > 0; index--)
            {
                node = node.Linked !;
                Debug.Assert(node != null);
            }

            return(node);
        }
예제 #3
0
            public AppendPrependN(IEnumerable <TSource> source, SingleLinkedNode <TSource> prepended, SingleLinkedNode <TSource> appended, int prependCount, int appendCount)
                : base(source)
            {
                Debug.Assert(prepended != null || appended != null);
                Debug.Assert(prependCount > 0 || appendCount > 0);
                Debug.Assert(prependCount + appendCount >= 2);
                Debug.Assert((prepended?.GetCount() ?? 0) == prependCount);
                Debug.Assert((appended?.GetCount() ?? 0) == appendCount);

                _prepended    = prepended;
                _appended     = appended;
                _prependCount = prependCount;
                _appendCount  = appendCount;
            }
예제 #4
0
            public IEnumerator <TSource> GetEnumerator()
            {
                TSource[] array = new TSource[Count];
                int       index = Count;

                for (SingleLinkedNode <TSource> node = this; node != null; node = node.Linked)
                {
                    --index;
                    array[index] = node.Item;
                }

                Debug.Assert(index == 0);
                return(((IEnumerable <TSource>)array).GetEnumerator());
            }
예제 #5
0
            /// <summary>
            /// Returns an <see cref="T:TSource[]"/> that contains the items of this node's singly-linked list in reverse.
            /// </summary>
            public TSource[] ToArray()
            {
                TSource[] array = new TSource[Count];
                int       index = Count;

                for (SingleLinkedNode <TSource> node = this; node != null; node = node.Linked)
                {
                    --index;
                    array[index] = node.Item;
                }

                Debug.Assert(index == 0);
                return(array);
            }
예제 #6
0
        /// <summary>
        /// Returns an array that contains the items of this node's singly-linked list in reverse.
        /// </summary>
        /// <param name="count">The number of items in this node.</param>
        public TSource[] ToArray(int count)
        {
            Debug.Assert(count == GetCount());

            TSource[] array = new TSource[count];
            int       index = count;

            for (SingleLinkedNode <TSource>?node = this; node != null; node = node.Linked)
            {
                --index;
                array[index] = node.Item;
            }

            Debug.Assert(index == 0);
            return(array);
        }
예제 #7
0
            public override bool MoveNext()
            {
                switch (_state)
                {
                case 1:
                    _node  = _prepended;
                    _state = 2;
                    goto case 2;

                case 2:
                    if (_node != null)
                    {
                        _current = _node.Item;
                        _node    = _node.Linked;
                        return(true);
                    }

                    GetSourceEnumerator();
                    _state = 3;
                    goto case 3;

                case 3:
                    if (LoadFromEnumerator())
                    {
                        return(true);
                    }

                    if (_appended == null)
                    {
                        return(false);
                    }

                    _enumerator = _appended.GetEnumerator(_appendCount);
                    _state      = 4;
                    goto case 4;

                case 4:
                    return(LoadFromEnumerator());
                }

                Dispose();
                return(false);
            }
예제 #8
0
            public override List <TSource> ToList()
            {
                int            count = GetCount(onlyIfCheap: true);
                List <TSource> list  = count == -1 ? new List <TSource>() : new List <TSource>(count);

                for (SingleLinkedNode <TSource>?node = _prepended; node != null; node = node.Linked)
                {
                    list.Add(node.Item);
                }

                list.AddRange(_source);

                if (_appended != null)
                {
                    list.AddRange(_appended.ToArray(_appendCount));
                }

                return(list);
            }
예제 #9
0
            public override TSource[] ToArray()
            {
                int count = GetCount(onlyIfCheap: true);

                if (count == -1)
                {
                    return(LazyToArray());
                }

                TSource[] array = new TSource[count];
                int       index = 0;

                for (SingleLinkedNode <TSource> node = _prepended; node != null; node = node.Linked)
                {
                    array[index] = node.Item;
                    ++index;
                }

                ICollection <TSource> sourceCollection = _source as ICollection <TSource>;

                if (sourceCollection != null)
                {
                    sourceCollection.CopyTo(array, index);
                }
                else
                {
                    foreach (TSource item in _source)
                    {
                        array[index] = item;
                        ++index;
                    }
                }

                index = array.Length;
                for (SingleLinkedNode <TSource> node = _appended; node != null; node = node.Linked)
                {
                    --index;
                    array[index] = node.Item;
                }

                return(array);
            }
예제 #10
0
            public override List <TSource> ToList()
            {
                int            count = GetCount(onlyIfCheap: true);
                List <TSource> list  = count == -1 ? new List <TSource>() : new List <TSource>(count);

                for (SingleLinkedNode <TSource> node = _prepended; node != null; node = node.Linked)
                {
                    list.Add(node.Item);
                }

                list.AddRange(_source);
                if (_appended != null)
                {
                    IEnumerator <TSource> e = _appended.GetEnumerator();
                    while (e.MoveNext())
                    {
                        list.Add(e.Current);
                    }
                }

                return(list);
            }
예제 #11
0
            private TSource[] LazyToArray()
            {
                Debug.Assert(GetCount(onlyIfCheap: true) == -1);

                var builder = new LargeArrayBuilder <TSource>(initialize: true);

                for (SingleLinkedNode <TSource> node = _prepended; node != null; node = node.Linked)
                {
                    builder.Add(node.Item);
                }

                builder.AddRange(_source);

                if (_appended != null)
                {
                    foreach (TSource item in _appended.ToArray())
                    {
                        builder.Add(item);
                    }
                }

                return(builder.ToArray());
            }
예제 #12
0
            internal override UnionIterator <TSource> Union(IEnumerable <TSource> next)
            {
                var sources = new SingleLinkedNode <IEnumerable <TSource> >(_first).Add(_second).Add(next);

                return(new UnionIteratorN <TSource>(sources, 2, _comparer));
            }
예제 #13
0
            protected override async ValueTask <bool> MoveNextCore()
            {
                switch (_state)
                {
                case AsyncIteratorState.Allocated:
                    _mode  = 1;
                    _state = AsyncIteratorState.Iterating;
                    goto case AsyncIteratorState.Iterating;

                case AsyncIteratorState.Iterating:
                    switch (_mode)
                    {
                    case 1:
                        _node = _prepended;
                        _mode = 2;
                        goto case 2;

                    case 2:
                        if (_node != null)
                        {
                            _current = _node.Item;
                            _node    = _node.Linked;
                            return(true);
                        }

                        GetSourceEnumerator(_cancellationToken);
                        _mode = 3;
                        goto case 3;

                    case 3:
                        if (await LoadFromEnumeratorAsync().ConfigureAwait(false))
                        {
                            return(true);
                        }

                        if (_appended != null)
                        {
                            _appendedEnumerator = _appended.GetEnumerator(_appendCount);
                            _mode = 4;
                            goto case 4;
                        }

                        break;


                    case 4:
                        if (_appendedEnumerator.MoveNext())
                        {
                            _current = _appendedEnumerator.Current;
                            return(true);
                        }
                        break;
                    }

                    break;
                }

                await DisposeAsync().ConfigureAwait(false);

                return(false);
            }
예제 #14
0
            protected override async Task <bool> MoveNextCore(CancellationToken cancellationToken)
            {
                switch (state)
                {
                case AsyncIteratorState.Allocated:
                    mode  = 1;
                    state = AsyncIteratorState.Iterating;
                    goto case AsyncIteratorState.Iterating;

                case AsyncIteratorState.Iterating:
                    switch (mode)
                    {
                    case 1:
                        node = prepended;
                        mode = 2;
                        goto case 2;

                    case 2:
                        if (node != null)
                        {
                            current = node.Item;
                            node    = node.Linked;
                            return(true);
                        }

                        GetSourceEnumerator();
                        mode = 3;
                        goto case 3;

                    case 3:
                        if (await LoadFromEnumerator(cancellationToken)
                            .ConfigureAwait(false))
                        {
                            return(true);
                        }

                        if (appended != null)
                        {
                            appendedEnumerator = appended.GetEnumerator();
                            mode = 4;
                            goto case 4;
                        }

                        break;


                    case 4:
                        if (appendedEnumerator.MoveNext())
                        {
                            current = appendedEnumerator.Current;
                            return(true);
                        }
                        break;
                    }

                    break;
                }

                Dispose();
                return(false);
            }
예제 #15
0
 public SingleLinkedNode(TSource first, TSource second)
 {
     Linked = new SingleLinkedNode <TSource>(first);
     Item   = second;
     Count  = 2;
 }
예제 #16
0
 public AppendPrependN(IEnumerable <TSource> source, SingleLinkedNode <TSource> prepended, SingleLinkedNode <TSource> appended)
     : base(source)
 {
     Debug.Assert(prepended != null || appended != null);
     _prepended = prepended;
     _appended  = appended;
 }
예제 #17
0
 /// <summary>
 /// Constructs a node linked to the specified node.
 /// </summary>
 /// <param name="linked">The linked node.</param>
 /// <param name="item">The item to place in this node.</param>
 private SingleLinkedNode(SingleLinkedNode <TSource> linked, TSource item)
 {
     Debug.Assert(linked != null);
     Linked = linked;
     Item   = item;
 }
예제 #18
0
            public AppendPrependNAsyncIterator(IAsyncEnumerable <TSource> source, SingleLinkedNode <TSource> prepended, SingleLinkedNode <TSource> appended)
                : base(source)
            {
                Debug.Assert(prepended != null || appended != null);

                this.prepended = prepended;
                this.appended  = appended;
            }