コード例 #1
0
        /// <summary>
        /// Executes this operation
        /// </summary>
        /// <param name="rows">Rows in pipeline. These are only used if a left part of the join was not specified.</param>
        /// <returns></returns>
        public override IEnumerable <Row> Execute(IEnumerable <Row> rows)
        {
            Initialize();

            Guard.Against(left == null, "Left branch of a join cannot be null");
            Guard.Against(right == null, "Right branch of a join cannot be null");

            var leftRows = new EventRaisingEnumerator(left, left.Execute(leftRegistered ? null : rows)).GetEnumerator();

            leftRows.MoveNext();
            var leftRow = (Row)leftRows.Current;

            var rightRows = new EventRaisingEnumerator(right, right.Execute(null)).GetEnumerator();

            rightRows.MoveNext();
            var rightRow = (Row)rightRows.Current;

            while (leftRow != null && rightRow != null)
            {
                var match     = MatchJoinCondition(leftRow, rightRow);
                Row mergedRow = null;

                if (match == 0)
                {
                    mergedRow = MergeRows(leftRow, rightRow);
                    leftRow   = leftRows.MoveNext()
                        ? (Row)leftRows.Current
                        : null;
                    rightRow = rightRows.MoveNext()
                        ? (Row)rightRows.Current
                        : null;
                }
                else if (match < 0)
                {
                    if ((JoinType & JoinType.Left) != 0)
                    {
                        mergedRow = MergeRows(leftRow, new Row());
                    }
                    else
                    {
                        LeftOrphanRow(leftRow);
                    }

                    leftRow = leftRows.MoveNext()
                        ? (Row)leftRows.Current
                        : null;
                }
                else if (match > 0)
                {
                    if ((JoinType & JoinType.Right) != 0)
                    {
                        mergedRow = MergeRows(new Row(), rightRow);
                    }
                    else
                    {
                        RightOrphanRow(rightRow);
                    }

                    rightRow = rightRows.MoveNext()
                        ? (Row)rightRows.Current
                        : null;
                }

                if (mergedRow != null)
                {
                    yield return(mergedRow);
                }
            }

            if (leftRow == null && rightRow != null && (JoinType & JoinType.Right) != 0)
            {
                yield return(MergeRows(new Row(), rightRow));
            }
        }
コード例 #2
0
        /// <summary>
        ///     Executes this operation
        /// </summary>
        /// <param name="rows">Rows in pipeline. These are only used if a left part of the join was not specified.</param>
        /// <returns></returns>
        public override IEnumerable <Row> Execute(IEnumerable <Row> rows)
        {
            Initialize();

            Guard.Against(left == null, "Left branch of a join cannot be null");
            Guard.Against(right == null, "Right branch of a join cannot be null");

            var matchedRightRows = new Dictionary <Row, object>();
            var rightEnumerable  = new CachingEnumerable <Row>(
                new EventRaisingEnumerator(right, right.Execute(null))
                );
            var execute = left.Execute(leftRegistered ? null : rows);

            foreach (Row leftRow in new EventRaisingEnumerator(left, execute))
            {
                var leftNeedOuterJoin = true;
                currentLeftRow = leftRow;
                foreach (Row rightRow in rightEnumerable)
                {
                    currentRightRow = rightRow;
                    if (MatchJoinCondition(leftRow, rightRow))
                    {
                        leftNeedOuterJoin          = false;
                        matchedRightRows[rightRow] = null;
                        yield return(MergeRows(leftRow, rightRow));
                    }
                }
                if (leftNeedOuterJoin)
                {
                    var emptyRow = new Row();
                    emptyRow[IsEmptyRowMarker] = IsEmptyRowMarker;
                    currentRightRow            = emptyRow;
                    if (MatchJoinCondition(leftRow, emptyRow))
                    {
                        yield return(MergeRows(leftRow, emptyRow));
                    }
                    else
                    {
                        LeftOrphanRow(leftRow);
                    }
                }
            }
            foreach (Row rightRow in rightEnumerable)
            {
                if (matchedRightRows.ContainsKey(rightRow))
                {
                    continue;
                }
                currentRightRow = rightRow;
                var emptyRow = new Row();
                emptyRow[IsEmptyRowMarker] = IsEmptyRowMarker;
                currentLeftRow             = emptyRow;
                if (MatchJoinCondition(emptyRow, rightRow))
                {
                    yield return(MergeRows(emptyRow, rightRow));
                }
                else
                {
                    RightOrphanRow(rightRow);
                }
            }
        }