//---------------------------------------------------------------------------------------
            // Walks the two data sources, left and then right, to produce the union.
            //

            internal override bool MoveNext(ref TInputOutput currentElement, ref ConcatKey <TLeftKey, TRightKey> currentKey)
            {
                Contract.Assert(m_leftSource != null);
                Contract.Assert(m_rightSource != null);

                if (m_outputEnumerator == null)
                {
                    IEqualityComparer <Wrapper <TInputOutput> > wrapperComparer = new WrapperEqualityComparer <TInputOutput>(m_comparer);
                    Dictionary <Wrapper <TInputOutput>, Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> > > union =
                        new Dictionary <Wrapper <TInputOutput>, Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> > >(wrapperComparer);

                    Pair <TInputOutput, NoKeyMemoizationRequired> elem = default(Pair <TInputOutput, NoKeyMemoizationRequired>);
                    TLeftKey leftKey = default(TLeftKey);

                    int i = 0;
                    while (m_leftSource.MoveNext(ref elem, ref leftKey))
                    {
                        if ((i++ & CancellationState.POLL_INTERVAL) == 0)
                        {
                            CancellationState.ThrowIfCanceled(m_cancellationToken);
                        }

                        ConcatKey <TLeftKey, TRightKey> key =
                            ConcatKey <TLeftKey, TRightKey> .MakeLeft(m_leftOrdered?leftKey : default(TLeftKey));

                        Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> > oldEntry;
                        Wrapper <TInputOutput> wrappedElem = new Wrapper <TInputOutput>(elem.First);

                        if (!union.TryGetValue(wrappedElem, out oldEntry) || m_keyComparer.Compare(key, oldEntry.Second) < 0)
                        {
                            union[wrappedElem] = new Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> >(elem.First, key);
                        }
                    }

                    TRightKey rightKey = default(TRightKey);
                    while (m_rightSource.MoveNext(ref elem, ref rightKey))
                    {
                        if ((i++ & CancellationState.POLL_INTERVAL) == 0)
                        {
                            CancellationState.ThrowIfCanceled(m_cancellationToken);
                        }

                        ConcatKey <TLeftKey, TRightKey> key =
                            ConcatKey <TLeftKey, TRightKey> .MakeRight(m_rightOrdered?rightKey : default(TRightKey));

                        Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> > oldEntry;
                        Wrapper <TInputOutput> wrappedElem = new Wrapper <TInputOutput>(elem.First);

                        if (!union.TryGetValue(wrappedElem, out oldEntry) || m_keyComparer.Compare(key, oldEntry.Second) < 0)
                        {
                            union[wrappedElem] = new Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> >(elem.First, key);;
                        }
                    }

                    m_outputEnumerator = union.GetEnumerator();
                }

                if (m_outputEnumerator.MoveNext())
                {
                    Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> > current = m_outputEnumerator.Current.Value;
                    currentElement = current.First;
                    currentKey     = current.Second;
                    return(true);
                }

                return(false);
            }
Example #2
0
            //---------------------------------------------------------------------------------------
            // MoveNext advances to the next element in the output.  While the first data source has
            // elements, this consists of just advancing through it.  After this, all partitions must
            // synchronize at a barrier and publish the maximum index N.  Finally, all partitions can
            // move on to the second data source, adding N+1 to indices in order to get the correct
            // index offset.
            //

            internal override bool MoveNext([MaybeNullWhen(false), AllowNull] ref TSource currentElement, ref ConcatKey <TLeftKey, TRightKey> currentKey)
            {
                Debug.Assert(_firstSource != null);
                Debug.Assert(_secondSource != null);

                // If we are still enumerating the first source, fetch the next item.
                if (!_begunSecond)
                {
                    // If elements remain, just return true and continue enumerating the left.
                    TLeftKey leftKey = default(TLeftKey) !;
                    if (_firstSource.MoveNext(ref currentElement !, ref leftKey))
                    {
                        currentKey = ConcatKey <TLeftKey, TRightKey> .MakeLeft(leftKey);

                        return(true);
                    }
                    _begunSecond = true;
                }

                // Now either move on to, or continue, enumerating the right data source.
                TRightKey rightKey = default(TRightKey) !;

                if (_secondSource.MoveNext(ref currentElement !, ref rightKey))
                {
                    currentKey = ConcatKey <TLeftKey, TRightKey> .MakeRight(rightKey);

                    return(true);
                }

                return(false);
            }
Example #3
0
            //---------------------------------------------------------------------------------------
            // Walks the two data sources, left and then right, to produce the union.
            //

            internal override bool MoveNext(ref TInputOutput currentElement, ref ConcatKey currentKey)
            {
                Debug.Assert(_leftSource != null);
                Debug.Assert(_rightSource != null);

                if (_outputEnumerator == null)
                {
                    IEqualityComparer <Wrapper <TInputOutput> > wrapperComparer = new WrapperEqualityComparer <TInputOutput>(_comparer);
                    Dictionary <Wrapper <TInputOutput>, Pair>   union           =
                        new Dictionary <Wrapper <TInputOutput>, Pair>(wrapperComparer);

                    Pair     elem    = new Pair(default(TInputOutput), default(NoKeyMemoizationRequired));
                    TLeftKey leftKey = default(TLeftKey);

                    int i = 0;
                    while (_leftSource.MoveNext(ref elem, ref leftKey))
                    {
                        if ((i++ & CancellationState.POLL_INTERVAL) == 0)
                        {
                            CancellationState.ThrowIfCanceled(_cancellationToken);
                        }

                        ConcatKey key =
                            ConcatKey.MakeLeft <TLeftKey, TRightKey>(_leftOrdered ? leftKey : default(TLeftKey));
                        Pair oldEntry;
                        Wrapper <TInputOutput> wrappedElem = new Wrapper <TInputOutput>((TInputOutput)elem.First);

                        if (!union.TryGetValue(wrappedElem, out oldEntry) || _keyComparer.Compare(key, (ConcatKey)oldEntry.Second) < 0)
                        {
                            union[wrappedElem] = new Pair(elem.First, key);
                        }
                    }

                    TRightKey rightKey = default(TRightKey);
                    while (_rightSource.MoveNext(ref elem, ref rightKey))
                    {
                        if ((i++ & CancellationState.POLL_INTERVAL) == 0)
                        {
                            CancellationState.ThrowIfCanceled(_cancellationToken);
                        }

                        ConcatKey key =
                            ConcatKey.MakeRight <TLeftKey, TRightKey>(_rightOrdered ? rightKey : default(TRightKey));
                        Pair oldEntry;
                        Wrapper <TInputOutput> wrappedElem = new Wrapper <TInputOutput>((TInputOutput)elem.First);

                        if (!union.TryGetValue(wrappedElem, out oldEntry) || _keyComparer.Compare(key, (ConcatKey)oldEntry.Second) < 0)
                        {
                            union[wrappedElem] = new Pair(elem.First, key);;
                        }
                    }

                    _outputEnumerator = union.GetEnumerator();
                }

                if (_outputEnumerator.MoveNext())
                {
                    Pair current = _outputEnumerator.Current.Value;
                    currentElement = (TInputOutput)current.First;
                    currentKey     = (ConcatKey)current.Second;
                    return(true);
                }

                return(false);
            }
            //---------------------------------------------------------------------------------------
            // Walks the two data sources, left and then right, to produce the union.
            //

            internal override bool MoveNext([MaybeNullWhen(false), AllowNull] ref TInputOutput currentElement, ref ConcatKey <TLeftKey, TRightKey> currentKey)
            {
                Debug.Assert(_leftSource != null);
                Debug.Assert(_rightSource != null);

                if (_outputEnumerator == null)
                {
                    IEqualityComparer <Wrapper <TInputOutput> > wrapperComparer = new WrapperEqualityComparer <TInputOutput>(_comparer);
                    Dictionary <Wrapper <TInputOutput>, Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> > > union =
                        new Dictionary <Wrapper <TInputOutput>, Pair <TInputOutput, ConcatKey <TLeftKey, TRightKey> > >(wrapperComparer);

                    Pair <TInputOutput, NoKeyMemoizationRequired> elem = default(Pair <TInputOutput, NoKeyMemoizationRequired>);
                    TLeftKey leftKey = default(TLeftKey) !;

                    int i = 0;
                    while (_leftSource.MoveNext(ref elem, ref leftKey))
                    {
                        if ((i++ & CancellationState.POLL_INTERVAL) == 0)
                        {
                            _cancellationToken.ThrowIfCancellationRequested();
                        }
                        ;

                        ConcatKey <TLeftKey, TRightKey> key =
                            ConcatKey <TLeftKey, TRightKey> .MakeLeft(_leftOrdered?leftKey : default);