CellTreeNodeVisitors.cs source code in C# .NET

Source code for the .NET framework in C#

                        

Code:

/ 4.0 / 4.0 / untmp / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / fx / src / DataEntity / System / Data / Map / ViewGeneration / Structures / CellTreeNodeVisitors.cs / 1305376 / CellTreeNodeVisitors.cs

                            //---------------------------------------------------------------------- 
// 
//      Copyright (c) Microsoft Corporation.  All rights reserved.
// 
// 
// @owner [....]
// @backupOwner [....] 
//--------------------------------------------------------------------- 

using System.Collections.Generic; 
using System.Data.Common.Utils.Boolean;
using System.Diagnostics;
using System.Data.Common.Utils;
using System.Data.Metadata.Edm; 

namespace System.Data.Mapping.ViewGeneration.Structures 
{ 

    using WrapperBoolExpr = BoolExpr; 
    using WrapperTreeExpr = TreeExpr;
    using WrapperAndExpr = AndExpr;
    using WrapperOrExpr = OrExpr;
    using WrapperNotExpr = NotExpr; 
    using WrapperTermExpr = TermExpr;
    using WrapperTrueExpr = TrueExpr; 
    using WrapperFalseExpr = FalseExpr; 

    internal partial class CellTreeNode 
    {

        #region Abstract Visitors
        // Abstract visitor implementation for Cell trees 
        // TOutput is the return type of the visitor and TInput is a single
        // parameter that can be passed in 
        internal abstract class CellTreeVisitor 
        {
            internal abstract TOutput VisitLeaf(LeafCellTreeNode node, TInput param); 
            internal abstract TOutput VisitUnion(OpCellTreeNode node, TInput param);
            internal abstract TOutput VisitInnerJoin(OpCellTreeNode node, TInput param);
            internal abstract TOutput VisitLeftOuterJoin(OpCellTreeNode node, TInput param);
            internal abstract TOutput VisitFullOuterJoin(OpCellTreeNode node, TInput param); 
            internal abstract TOutput VisitLeftAntiSemiJoin(OpCellTreeNode node, TInput param);
        } 
 
        // Another abstract visitor that does not distinguish between different
        // operation nodes 
        internal abstract class SimpleCellTreeVisitor
        {
            internal abstract TOutput VisitLeaf(LeafCellTreeNode node, TInput param);
            internal abstract TOutput VisitOpNode(OpCellTreeNode node, TInput param); 
        }
        #endregion 
 
        #region Default CellTree Visitor
        // Default visitor implementation for CellTreeVisitor 
        // TInput is the type of the parameter that can be passed in to each visit
        // Returns a CellTreeVisitor as output
        private class DefaultCellTreeVisitor : CellTreeVisitor
        { 

            internal override CellTreeNode VisitLeaf(LeafCellTreeNode node, TInput param) 
            { 
                return node;
            } 

            internal override CellTreeNode VisitUnion(OpCellTreeNode node, TInput param)
            {
                return AcceptChildren(node, param); 
            }
 
            internal override CellTreeNode VisitInnerJoin(OpCellTreeNode node, TInput param) 
            {
                return AcceptChildren(node, param); 
            }

            internal override CellTreeNode VisitLeftOuterJoin(OpCellTreeNode node, TInput param)
            { 
                return AcceptChildren(node, param);
            } 
 
            internal override CellTreeNode VisitFullOuterJoin(OpCellTreeNode node, TInput param)
            { 
                return AcceptChildren(node, param);
            }

            internal override CellTreeNode VisitLeftAntiSemiJoin(OpCellTreeNode node, TInput param) 
            {
                return AcceptChildren(node, param); 
            } 

            private OpCellTreeNode AcceptChildren(OpCellTreeNode node, TInput param) 
            {
                List newChildren = new List();
                foreach (CellTreeNode child in node.Children)
                { 
                    newChildren.Add(child.Accept(this, param));
                } 
                return new OpCellTreeNode(node.ViewgenContext, node.OpType, newChildren); 
            }
        } 
        #endregion


        #region Flattening Visitor 
        // Flattens the tree, i.e., pushes up nodes that just have just one child
        private class FlatteningVisitor : SimpleCellTreeVisitor 
        { 
            #region Constructor/Fields/Invocation
            protected FlatteningVisitor() 
            {
            }

            // effects: Flattens node and returns a new tree that is flattened 
            internal static CellTreeNode Flatten(CellTreeNode node)
            { 
                FlatteningVisitor visitor = new FlatteningVisitor(); 
                return node.Accept(visitor, true);
            } 
            #endregion

            #region Visitors
            internal override CellTreeNode VisitLeaf(LeafCellTreeNode node, bool dummy) 
            {
                return node; 
            } 

            // effects: Visits an internal Op node and processes it 
            internal override CellTreeNode VisitOpNode(OpCellTreeNode node, bool dummy)
            {
                // Flatten the children first
                List flattenedChildren = new List(); 
                foreach (CellTreeNode child in node.Children)
                { 
                    CellTreeNode flattenedChild = child.Accept(this, dummy); 
                    flattenedChildren.Add(flattenedChild);
                } 

                Debug.Assert(flattenedChildren.Count >= 1, "node must have more than 1 child and be an OpCellTreeNode");
                // If only one child, return that
                if (flattenedChildren.Count == 1) 
                {
                    return flattenedChildren[0]; 
                } 

                Debug.Assert(flattenedChildren.Count > 1, "Opnode has 0 children?"); 
                Debug.Assert(node.OpType != CellTreeOpType.Leaf, "Wrong op type for operation node");

                OpCellTreeNode result = new OpCellTreeNode(node.ViewgenContext, node.OpType, flattenedChildren);
                return result; 
            }
            #endregion 
        } 
        #endregion
 
        #region AssociativeOpFlatteningVisitor
        // Flattens associative ops and single children nodes. Like the
        // FlatteningVisitor, it gets rid of the single children
        // nodes. Furthermore, it also collapses nodes of associative operations, 
        // i.e., A IJ (B IJ C) is changed to A IJ B IJ C
        private class AssociativeOpFlatteningVisitor : SimpleCellTreeVisitor 
        { 
            #region Constructor/Fields/Invocation
            private AssociativeOpFlatteningVisitor() 
            {
            }

            internal static CellTreeNode Flatten(CellTreeNode node) 
            {
                // First do simple flattening and then associative op flattening 
                CellTreeNode newNode = FlatteningVisitor.Flatten(node); 
                AssociativeOpFlatteningVisitor visitor = new AssociativeOpFlatteningVisitor();
                return newNode.Accept(visitor, true); 
            }
            #endregion

            #region Visitors 
            internal override CellTreeNode VisitLeaf(LeafCellTreeNode node, bool dummy)
            { 
                return node; 
            }
 
            internal override CellTreeNode VisitOpNode(OpCellTreeNode node, bool dummy)
            {
                List flattenedChildren = new List();
                // Flatten the children first 
                foreach (CellTreeNode child in node.Children)
                { 
                    CellTreeNode flattenedChild = child.Accept(this, dummy); 
                    flattenedChildren.Add(flattenedChild);
                } 

                Debug.Assert(flattenedChildren.Count > 1, "node must have more than 1 child and be an OpCellTreeNode");

                // If this op is associative and a child's OP is the same as this 
                // op, add those to be this nodes children
                List finalChildren = flattenedChildren; 
                if (CellTreeNode.IsAssociativeOp(node.OpType)) 
                {
                    finalChildren = new List(); 
                    foreach (CellTreeNode child in flattenedChildren)
                    {
                        if (child.OpType == node.OpType)
                        { 
                            finalChildren.AddRange(child.Children);
                        } 
                        else 
                        {
                            finalChildren.Add(child); 
                        }
                    }
                }
 
                OpCellTreeNode result = new OpCellTreeNode(node.ViewgenContext, node.OpType, finalChildren);
                return result; 
            } 
            #endregion
        } 
        #endregion

        #region LeafVisitor
        // This visitor returns all the leaf tree nodes in this 
        private class LeafVisitor : SimpleCellTreeVisitor>
        { 
 
            private LeafVisitor() { }
 
            internal static IEnumerable GetLeaves(CellTreeNode node)
            {
                LeafVisitor visitor = new LeafVisitor();
                return node.Accept>(visitor, true); 
            }
 
            internal override IEnumerable VisitLeaf(LeafCellTreeNode node, bool dummy) 
            {
                yield return node; 
            }

            internal override IEnumerable VisitOpNode(OpCellTreeNode node, bool dummy)
            { 
                foreach (CellTreeNode child in node.Children)
                { 
                    IEnumerable children = child.Accept>(this, dummy); 
                    foreach (LeafCellTreeNode leafNode in children)
                    { 
                        yield return leafNode;
                    }
                }
            } 
        }
        #endregion 
    } 
}

// File provided for Reference Use Only by Microsoft Corporation (c) 2007.


                        

Link Menu

Network programming in C#, Network Programming in VB.NET, Network Programming in .NET
This book is available now!
Buy at Amazon US or
Buy at Amazon UK