Пример #1
0
        private static QueryPlanNode BuildPlanNode(
            int numStreams,
            int streamNo,
            string[] streamNames,
            QueryGraph queryGraph,
            OuterInnerDirectionalGraph outerInnerGraph,
            OuterJoinDesc[] outerJoinDescList,
            InnerJoinGraph innerJoinGraph,
            QueryPlanIndex[] indexSpecs,
            EventType[] typesPerStream,
            bool[] ishistorical,
            DependencyGraph dependencyGraph,
            HistoricalStreamIndexList[] historicalStreamIndexLists,
            ExprEvaluatorContext exprEvaluatorContext,
            TableMetadata[] tablesPerStream)
        {
            // For each stream build an array of substreams, considering required streams (inner joins) first
            // The order is relevant therefore preserving order via a LinkedHashMap.
            var substreamsPerStream = new LinkedHashMap <int, int[]>();
            var requiredPerStream   = new bool[numStreams];

            // Recursive populating the required (outer) and optional (inner) relationships
            // of this stream and the substream
            ISet <int> completedStreams = new HashSet <int>();
            // keep track of tree path as only those stream events are always available to historical streams
            var streamCallStack = new Stack <int>();

            streamCallStack.Push(streamNo);

            // For all inner-joins, the algorithm is slightly different
            if (innerJoinGraph.IsAllInnerJoin)
            {
                requiredPerStream.Fill(true);
                RecursiveBuildInnerJoin(streamNo, streamCallStack, queryGraph, completedStreams, substreamsPerStream, dependencyGraph);

                // compute a best chain to see if all streams are handled and add the remaining
                var bestChain = NStreamQueryPlanBuilder.ComputeBestPath(streamNo, queryGraph, dependencyGraph);
                AddNotYetNavigated(streamNo, numStreams, substreamsPerStream, bestChain);
            }
            else
            {
                RecursiveBuild(streamNo, streamCallStack, queryGraph, outerInnerGraph, innerJoinGraph, completedStreams, substreamsPerStream, requiredPerStream, dependencyGraph);
            }

            // verify the substreamsPerStream, all streams must exists and be linked
            VerifyJoinedPerStream(streamNo, substreamsPerStream);

            // build list of instructions for lookup
            var lookupInstructions = BuildLookupInstructions(streamNo, substreamsPerStream, requiredPerStream,
                                                             streamNames, queryGraph, indexSpecs, typesPerStream, outerJoinDescList, ishistorical, historicalStreamIndexLists, exprEvaluatorContext, tablesPerStream);

            // build strategy tree for putting the result back together
            var assemblyTopNodeFactory       = AssemblyStrategyTreeBuilder.Build(streamNo, substreamsPerStream, requiredPerStream);
            var assemblyInstructionFactories = BaseAssemblyNodeFactory.GetDescendentNodesBottomUp(assemblyTopNodeFactory);

            return(new LookupInstructionQueryPlanNode(streamNo, streamNames[streamNo], numStreams, requiredPerStream,
                                                      lookupInstructions, assemblyInstructionFactories));
        }
Пример #2
0
        public void TestComputeBestPath()
        {
            NStreamQueryPlanBuilder.BestChainResult bestChain = NStreamQueryPlanBuilder.ComputeBestPath(
                0, _queryGraph, _dependencyGraph);
            Assert.AreEqual(3, bestChain.Depth);
            Assert.IsTrue(Collections.AreEqual(bestChain.Chain, new int[] { 2, 4, 3, 1 }));

            bestChain = NStreamQueryPlanBuilder.ComputeBestPath(3, _queryGraph, _dependencyGraph);
            Assert.AreEqual(4, bestChain.Depth);
            Assert.IsTrue(Collections.AreEqual(bestChain.Chain, new int[] { 4, 2, 0, 1 }));

            // try a stream that is not connected in any way
            _queryGraph = new QueryGraph(6, null, false);
            bestChain   = NStreamQueryPlanBuilder.ComputeBestPath(5, _queryGraph, _dependencyGraph);
            Log.Debug(".testComputeBestPath bestChain=" + bestChain);
            Assert.AreEqual(0, bestChain.Depth);
            Assert.IsTrue(Collections.AreEqual(bestChain.Chain, new int[] { 0, 1, 2, 3, 4 }));
        }