コード例 #1
0
        private PartialDecomposition GetFirstComponent(PartialDecomposition decomposition)
        {
            var faces = decomposition.GetRemainingFaces();

            if (Faces.Count != 0)
            {
                List <TNode> firstFace;

                if (preferSmallCycles)
                {
                    var smallestFaceIndex = faces.MinBy(x => x.Count);
                    firstFace = faces[smallestFaceIndex];
                }
                else
                {
                    var largestFaceIndex = faces.MaxBy(x => x.Count);
                    firstFace = faces[largestFaceIndex];
                }

                var cycleComponent = new GraphComponent()
                {
                    Nodes      = firstFace,
                    IsFromFace = true,
                    MinimumNeighborChainNumber = 0,
                };

                logger.WriteLine("Starting with cycle");
                logger.WriteLine(cycleComponent);

                return(decomposition.AddChain(cycleComponent.Nodes, true));
            }

            var startingNode  = Graph.Vertices.First(x => Graph.GetNeighbours(x).Count() == 1);
            var treeComponent = GetTreeComponent(decomposition, startingNode);

            logger.WriteLine("Starting with tree");
            logger.WriteLine(treeComponent);

            return(decomposition.AddChain(treeComponent.Nodes, false));
        }
コード例 #2
0
        private PartialDecomposition ExtendDecomposition(PartialDecomposition decomposition)
        {
            var remainingFace = decomposition.GetRemainingFaces();
            var blacklist     = new List <TNode>();
            var components    = new List <GraphComponent>();

            foreach (var node in decomposition.GetAllCoveredVertices())
            {
                var neighbors           = Graph.GetNeighbours(node);
                var notCoveredNeighbors = neighbors.Where(x => !decomposition.IsCovered(x));
                var treeStartingNodes   = new List <TNode>();

                foreach (var neighbor in notCoveredNeighbors)
                {
                    if (blacklist.Contains(neighbor))
                    {
                        continue;
                    }

                    var foundFace = false;
                    foreach (var face in remainingFace)
                    {
                        if (!face.Contains(neighbor))
                        {
                            continue;
                        }

                        var cycleComponent = GetCycleComponent(decomposition, face);
                        components.Add(cycleComponent);
                        blacklist.AddRange(cycleComponent.Nodes);
                        foundFace = true;

                        break;
                    }

                    if (foundFace)
                    {
                        continue;
                    }

                    treeStartingNodes.Add(neighbor);
                }

                if (treeStartingNodes.Count != 0)
                {
                    if (startTreeWithMultipleVertices)
                    {
                        var treeComponent = GetTreeComponent(decomposition, treeStartingNodes);
                        components.Add(treeComponent);
                        blacklist.AddRange(treeComponent.Nodes);
                    }
                    else
                    {
                        foreach (var startingNode in treeStartingNodes)
                        {
                            var treeComponent = GetTreeComponent(decomposition, startingNode);
                            components.Add(treeComponent);
                            blacklist.AddRange(treeComponent.Nodes);
                        }
                    }
                }
            }

            logger.WriteLine();
            logger.WriteLine("Extending decomposition");
            logger.WriteLine("Candidates:");

            foreach (var component in components)
            {
                logger.WriteLine(component);
            }

            logger.WriteLine();

            var cycleComponents = components.Where(x => x.IsFromFace).ToList();

            if (cycleComponents.Count != 0)
            {
                var nextCycleIndex = preferSmallCycles ? cycleComponents.MinBy(x => x.Nodes.Count) : cycleComponents.MaxBy(x => x.Nodes.Count);
                var nextCycle      = cycleComponents[nextCycleIndex];

                logger.WriteLine("Adding smallest cycle component");
                logger.WriteLine(nextCycle);

                return(decomposition.AddChain(nextCycle.Nodes, true));
            }

            var treeComponents = components
                                 .Where(x => !x.IsFromFace)
                                 .OrderBy(x => x.MinimumNeighborChainNumber)
                                 .ThenByDescending(x => x.Nodes.Count)
                                 .ToList();

            var biggestTree = treeComponents[0];

            if (mergeSmallChains)
            {
                if (biggestTree.Nodes.Count < maxTreeSize)
                {
                    for (var i = 1; i < treeComponents.Count; i++)
                    {
                        var component = treeComponents[i];

                        if (component.Nodes.Count + biggestTree.Nodes.Count <= maxTreeSize)
                        {
                            biggestTree.Nodes.AddRange(component.Nodes);
                        }
                    }
                }
            }

            logger.WriteLine("Adding biggest oldest tree component");
            logger.WriteLine(biggestTree);

            return(decomposition.AddChain(biggestTree.Nodes, false));
        }