686 bool processed(Node v) { return (*_heap_cross_ref)[v] == Heap::POST_HEAP; } |
686 bool processed(Node v) { return (*_heap_cross_ref)[v] == Heap::POST_HEAP; } |
687 |
687 |
688 ///@} |
688 ///@} |
689 }; |
689 }; |
690 |
690 |
691 /// \brief Default traits class of MinimumCut class. |
691 /// \brief Default traits class of MinCut class. |
692 /// |
692 /// |
693 /// Default traits class of MinimumCut class. |
693 /// Default traits class of MinCut class. |
694 /// \param Graph Graph type. |
694 /// \param Graph Graph type. |
695 /// \param CapacityMap Type of length map. |
695 /// \param CapacityMap Type of length map. |
696 template <typename _Graph, typename _CapacityMap> |
696 template <typename _Graph, typename _CapacityMap> |
697 struct MinimumCutDefaultTraits { |
697 struct MinCutDefaultTraits { |
698 /// \brief The type of the capacity of the edges. |
698 /// \brief The type of the capacity of the edges. |
699 typedef typename _CapacityMap::Value Value; |
699 typedef typename _CapacityMap::Value Value; |
700 |
700 |
701 /// The graph type the algorithm runs on. |
701 /// The graph type the algorithm runs on. |
702 typedef _Graph Graph; |
702 typedef _Graph Graph; |
703 |
703 |
704 /// The WorkGraph type which is an EraseableGraph |
704 /// The AuxGraph type which is an EraseableGraph |
705 typedef ListUGraph WorkGraph; |
705 typedef ListUGraph AuxGraph; |
706 |
706 |
707 /// \brief Instantiates a WorkGraph. |
707 /// \brief Instantiates a AuxGraph. |
708 /// |
708 /// |
709 /// This function instantiates a \ref WorkGraph. |
709 /// This function instantiates a \ref AuxGraph. |
710 static WorkGraph *createWorkGraph() { |
710 static AuxGraph *createAuxGraph() { |
711 return new WorkGraph(); |
711 return new AuxGraph(); |
712 } |
712 } |
713 |
713 |
714 /// \brief The type of the map that stores the edge capacities. |
714 /// \brief The type of the map that stores the edge capacities. |
715 /// |
715 /// |
716 /// The type of the map that stores the edge capacities. |
716 /// The type of the map that stores the edge capacities. |
727 #endif |
727 #endif |
728 { |
728 { |
729 throw UninitializedParameter(); |
729 throw UninitializedParameter(); |
730 } |
730 } |
731 |
731 |
732 /// \brief The WorkCapacityMap type |
732 /// \brief The AuxCapacityMap type |
733 /// |
733 /// |
734 /// The type of the map that stores the working edge capacities. |
734 /// The type of the map that stores the auxing edge capacities. |
735 typedef WorkGraph::UEdgeMap<Value> WorkCapacityMap; |
735 typedef AuxGraph::UEdgeMap<Value> AuxCapacityMap; |
736 |
736 |
737 /// \brief Instantiates a WorkCapacityMap. |
737 /// \brief Instantiates a AuxCapacityMap. |
738 /// |
738 /// |
739 /// This function instantiates a \ref WorkCapacityMap. |
739 /// This function instantiates a \ref AuxCapacityMap. |
740 static WorkCapacityMap *createWorkCapacityMap(const WorkGraph& graph) { |
740 static AuxCapacityMap *createAuxCapacityMap(const AuxGraph& graph) { |
741 return new WorkCapacityMap(graph); |
741 return new AuxCapacityMap(graph); |
742 } |
742 } |
743 |
743 |
744 /// \brief The cross reference type used by heap. |
744 /// \brief The cross reference type used by heap. |
745 /// |
745 /// |
746 /// The cross reference type used by heap. |
746 /// The cross reference type used by heap. |
747 /// Usually it is \c Graph::NodeMap<int>. |
747 /// Usually it is \c Graph::NodeMap<int>. |
748 typedef WorkGraph::NodeMap<int> HeapCrossRef; |
748 typedef AuxGraph::NodeMap<int> HeapCrossRef; |
749 |
749 |
750 /// \brief Instantiates a HeapCrossRef. |
750 /// \brief Instantiates a HeapCrossRef. |
751 /// |
751 /// |
752 /// This function instantiates a \ref HeapCrossRef. |
752 /// This function instantiates a \ref HeapCrossRef. |
753 /// \param graph is the graph, to which we would like to define the |
753 /// \param graph is the graph, to which we would like to define the |
754 /// HeapCrossRef. |
754 /// HeapCrossRef. |
755 static HeapCrossRef *createHeapCrossRef(const WorkGraph &graph) { |
755 static HeapCrossRef *createHeapCrossRef(const AuxGraph &graph) { |
756 return new HeapCrossRef(graph); |
756 return new HeapCrossRef(graph); |
757 } |
757 } |
758 |
758 |
759 /// \brief The heap type used by MinimumCut algorithm. |
759 /// \brief The heap type used by MinCut algorithm. |
760 /// |
760 /// |
761 /// The heap type used by MinimumCut algorithm. It should |
761 /// The heap type used by MinCut algorithm. It should |
762 /// maximalize the priorities and the heap's key type is |
762 /// maximalize the priorities and the heap's key type is |
763 /// the work graph's node. |
763 /// the aux graph's node. |
764 /// |
764 /// |
765 /// \sa BinHeap |
765 /// \sa BinHeap |
766 /// \sa MinimumCut |
766 /// \sa MinCut |
767 typedef typename _minimum_cut_bits |
767 typedef typename _min_cut_bits |
768 ::HeapSelector<CapacityMap> |
768 ::HeapSelector<CapacityMap> |
769 ::template Selector<typename WorkGraph::Node, Value, HeapCrossRef> |
769 ::template Selector<typename AuxGraph::Node, Value, HeapCrossRef> |
770 ::Heap Heap; |
770 ::Heap Heap; |
771 |
771 |
772 /// \brief Instantiates a Heap. |
772 /// \brief Instantiates a Heap. |
773 /// |
773 /// |
774 /// This function instantiates a \ref Heap. |
774 /// This function instantiates a \ref Heap. |
775 /// \param crossref The cross reference of the heap. |
775 /// \param crossref The cross reference of the heap. |
776 static Heap *createHeap(HeapCrossRef& crossref) { |
776 static Heap *createHeap(HeapCrossRef& crossref) { |
777 return new Heap(crossref); |
777 return new Heap(crossref); |
778 } |
778 } |
779 |
779 |
780 /// \brief Map from the WorkGraph's node type to the Graph's node type. |
780 /// \brief Map from the AuxGraph's node type to the Graph's node type. |
781 /// |
781 /// |
782 /// Map from the WorkGraph's node type to the Graph's node type. |
782 /// Map from the AuxGraph's node type to the Graph's node type. |
783 typedef typename WorkGraph |
783 typedef typename AuxGraph |
784 ::template NodeMap<typename Graph::Node> NodeRefMap; |
784 ::template NodeMap<typename Graph::Node> NodeRefMap; |
785 |
785 |
786 /// \brief Instantiates a NodeRefMap. |
786 /// \brief Instantiates a NodeRefMap. |
787 /// |
787 /// |
788 /// This function instantiates a \ref NodeRefMap. |
788 /// This function instantiates a \ref NodeRefMap. |
789 static NodeRefMap *createNodeRefMap(const WorkGraph& graph) { |
789 static NodeRefMap *createNodeRefMap(const AuxGraph& graph) { |
790 return new NodeRefMap(graph); |
790 return new NodeRefMap(graph); |
791 } |
791 } |
792 |
792 |
793 /// \brief Map from the Graph's node type to the Graph's node type. |
793 /// \brief Map from the Graph's node type to the Graph's node type. |
794 /// |
794 /// |
828 }; |
828 }; |
829 } |
829 } |
830 |
830 |
831 /// \ingroup topology |
831 /// \ingroup topology |
832 /// |
832 /// |
833 /// \brief Calculates the minimum cut in an undirected graph. |
833 /// \brief Calculates the min cut in an undirected graph. |
834 /// |
834 /// |
835 /// Calculates the minimum cut in an undirected graph. |
835 /// Calculates the min cut in an undirected graph. |
836 /// The algorithm separates the graph's nodes to two partitions with the |
836 /// The algorithm separates the graph's nodes to two partitions with the |
837 /// minimum sum of edge capacities between the two partitions. The |
837 /// min sum of edge capacities between the two partitions. The |
838 /// algorithm can be used to test the network reliability specifically |
838 /// algorithm can be used to test the netaux reliability specifically |
839 /// to test how many links have to be destroyed in the network to split it |
839 /// to test how many links have to be destroyed in the netaux to split it |
840 /// at least two distinict subnetwork. |
840 /// at least two distinict subnetaux. |
841 /// |
841 /// |
842 /// The complexity of the algorithm is O(n*e*log(n)) but with Fibonacci |
842 /// The complexity of the algorithm is O(n*e*log(n)) but with Fibonacci |
843 /// heap it can be decreased to O(n*e+n^2*log(n)). When the neutral capacity |
843 /// heap it can be decreased to O(n*e+n^2*log(n)). When the neutral capacity |
844 /// map is used then it uses LinearHeap which results O(n*e) time complexity. |
844 /// map is used then it uses LinearHeap which results O(n*e) time complexity. |
845 #ifdef DOXYGEN |
845 #ifdef DOXYGEN |
846 template <typename _Graph, typename _CapacityMap, typename _Traits> |
846 template <typename _Graph, typename _CapacityMap, typename _Traits> |
847 #else |
847 #else |
848 template <typename _Graph = ListUGraph, |
848 template <typename _Graph = ListUGraph, |
849 typename _CapacityMap = typename _Graph::template UEdgeMap<int>, |
849 typename _CapacityMap = typename _Graph::template UEdgeMap<int>, |
850 typename _Traits = MinimumCutDefaultTraits<_Graph, _CapacityMap> > |
850 typename _Traits = MinCutDefaultTraits<_Graph, _CapacityMap> > |
851 #endif |
851 #endif |
852 class MinimumCut { |
852 class MinCut { |
853 public: |
853 public: |
854 /// \brief \ref Exception for uninitialized parameters. |
854 /// \brief \ref Exception for uninitialized parameters. |
855 /// |
855 /// |
856 /// This error represents problems in the initialization |
856 /// This error represents problems in the initialization |
857 /// of the parameters of the algorithms. |
857 /// of the parameters of the algorithms. |
858 class UninitializedParameter : public lemon::UninitializedParameter { |
858 class UninitializedParameter : public lemon::UninitializedParameter { |
859 public: |
859 public: |
860 virtual const char* exceptionName() const { |
860 virtual const char* exceptionName() const { |
861 return "lemon::MinimumCut::UninitializedParameter"; |
861 return "lemon::MinCut::UninitializedParameter"; |
862 } |
862 } |
863 }; |
863 }; |
864 |
864 |
865 |
865 |
866 private: |
866 private: |
871 |
871 |
872 /// The type of the capacity of the edges. |
872 /// The type of the capacity of the edges. |
873 typedef typename Traits::CapacityMap::Value Value; |
873 typedef typename Traits::CapacityMap::Value Value; |
874 /// The type of the map that stores the edge capacities. |
874 /// The type of the map that stores the edge capacities. |
875 typedef typename Traits::CapacityMap CapacityMap; |
875 typedef typename Traits::CapacityMap CapacityMap; |
876 /// The type of the work graph |
876 /// The type of the aux graph |
877 typedef typename Traits::WorkGraph WorkGraph; |
877 typedef typename Traits::AuxGraph AuxGraph; |
878 /// The type of the work capacity map |
878 /// The type of the aux capacity map |
879 typedef typename Traits::WorkCapacityMap WorkCapacityMap; |
879 typedef typename Traits::AuxCapacityMap AuxCapacityMap; |
880 /// The cross reference type used for the current heap. |
880 /// The cross reference type used for the current heap. |
881 typedef typename Traits::HeapCrossRef HeapCrossRef; |
881 typedef typename Traits::HeapCrossRef HeapCrossRef; |
882 /// The heap type used by the max cardinality algorithm. |
882 /// The heap type used by the max cardinality algorithm. |
883 typedef typename Traits::Heap Heap; |
883 typedef typename Traits::Heap Heap; |
884 /// The node refrefernces between the original and work graph type. |
884 /// The node refrefernces between the original and aux graph type. |
885 typedef typename Traits::NodeRefMap NodeRefMap; |
885 typedef typename Traits::NodeRefMap NodeRefMap; |
886 /// The list node refrefernces in the original graph type. |
886 /// The list node refrefernces in the original graph type. |
887 typedef typename Traits::ListRefMap ListRefMap; |
887 typedef typename Traits::ListRefMap ListRefMap; |
888 |
888 |
889 public: |
889 public: |
902 /// the capacity type to constMap<UEdge, int, 1>() |
902 /// the capacity type to constMap<UEdge, int, 1>() |
903 /// |
903 /// |
904 /// \ref named-templ-param "Named parameter" for setting |
904 /// \ref named-templ-param "Named parameter" for setting |
905 /// the capacity type to constMap<UEdge, int, 1>() |
905 /// the capacity type to constMap<UEdge, int, 1>() |
906 struct DefNeutralCapacity |
906 struct DefNeutralCapacity |
907 : public MinimumCut<Graph, CapacityMap, DefNeutralCapacityTraits> { |
907 : public MinCut<Graph, CapacityMap, DefNeutralCapacityTraits> { |
908 typedef MinimumCut<Graph, CapacityMap, DefNeutralCapacityTraits> Create; |
908 typedef MinCut<Graph, CapacityMap, DefNeutralCapacityTraits> Create; |
909 }; |
909 }; |
910 |
910 |
911 |
911 |
912 template <class H, class CR> |
912 template <class H, class CR> |
913 struct DefHeapTraits : public Traits { |
913 struct DefHeapTraits : public Traits { |
914 typedef CR HeapCrossRef; |
914 typedef CR HeapCrossRef; |
915 typedef H Heap; |
915 typedef H Heap; |
916 static HeapCrossRef *createHeapCrossRef(const WorkGraph &) { |
916 static HeapCrossRef *createHeapCrossRef(const AuxGraph &) { |
917 throw UninitializedParameter(); |
917 throw UninitializedParameter(); |
918 } |
918 } |
919 static Heap *createHeap(HeapCrossRef &) { |
919 static Heap *createHeap(HeapCrossRef &) { |
920 throw UninitializedParameter(); |
920 throw UninitializedParameter(); |
921 } |
921 } |
925 /// |
925 /// |
926 /// \ref named-templ-param "Named parameter" for setting heap and cross |
926 /// \ref named-templ-param "Named parameter" for setting heap and cross |
927 /// reference type |
927 /// reference type |
928 template <class H, class CR = typename Graph::template NodeMap<int> > |
928 template <class H, class CR = typename Graph::template NodeMap<int> > |
929 struct DefHeap |
929 struct DefHeap |
930 : public MinimumCut<Graph, CapacityMap, DefHeapTraits<H, CR> > { |
930 : public MinCut<Graph, CapacityMap, DefHeapTraits<H, CR> > { |
931 typedef MinimumCut< Graph, CapacityMap, DefHeapTraits<H, CR> > Create; |
931 typedef MinCut< Graph, CapacityMap, DefHeapTraits<H, CR> > Create; |
932 }; |
932 }; |
933 |
933 |
934 template <class H, class CR> |
934 template <class H, class CR> |
935 struct DefStandardHeapTraits : public Traits { |
935 struct DefStandardHeapTraits : public Traits { |
936 typedef CR HeapCrossRef; |
936 typedef CR HeapCrossRef; |
937 typedef H Heap; |
937 typedef H Heap; |
938 static HeapCrossRef *createHeapCrossRef(const WorkGraph &graph) { |
938 static HeapCrossRef *createHeapCrossRef(const AuxGraph &graph) { |
939 return new HeapCrossRef(graph); |
939 return new HeapCrossRef(graph); |
940 } |
940 } |
941 static Heap *createHeap(HeapCrossRef &crossref) { |
941 static Heap *createHeap(HeapCrossRef &crossref) { |
942 return new Heap(crossref); |
942 return new Heap(crossref); |
943 } |
943 } |
967 const CapacityMap *_capacity; |
967 const CapacityMap *_capacity; |
968 /// \brief Indicates if \ref _capacity is locally allocated |
968 /// \brief Indicates if \ref _capacity is locally allocated |
969 /// (\c true) or not. |
969 /// (\c true) or not. |
970 bool local_capacity; |
970 bool local_capacity; |
971 |
971 |
972 /// Pointer to the work graph. |
972 /// Pointer to the aux graph. |
973 WorkGraph *_work_graph; |
973 AuxGraph *_aux_graph; |
974 /// \brief Indicates if \ref _work_graph is locally allocated |
974 /// \brief Indicates if \ref _aux_graph is locally allocated |
975 /// (\c true) or not. |
975 /// (\c true) or not. |
976 bool local_work_graph; |
976 bool local_aux_graph; |
977 /// Pointer to the work capacity map |
977 /// Pointer to the aux capacity map |
978 WorkCapacityMap *_work_capacity; |
978 AuxCapacityMap *_aux_capacity; |
979 /// \brief Indicates if \ref _work_capacity is locally allocated |
979 /// \brief Indicates if \ref _aux_capacity is locally allocated |
980 /// (\c true) or not. |
980 /// (\c true) or not. |
981 bool local_work_capacity; |
981 bool local_aux_capacity; |
982 /// Pointer to the heap cross references. |
982 /// Pointer to the heap cross references. |
983 HeapCrossRef *_heap_cross_ref; |
983 HeapCrossRef *_heap_cross_ref; |
984 /// \brief Indicates if \ref _heap_cross_ref is locally allocated |
984 /// \brief Indicates if \ref _heap_cross_ref is locally allocated |
985 /// (\c true) or not. |
985 /// (\c true) or not. |
986 bool local_heap_cross_ref; |
986 bool local_heap_cross_ref; |
987 /// Pointer to the heap. |
987 /// Pointer to the heap. |
988 Heap *_heap; |
988 Heap *_heap; |
989 /// Indicates if \ref _heap is locally allocated (\c true) or not. |
989 /// Indicates if \ref _heap is locally allocated (\c true) or not. |
990 bool local_heap; |
990 bool local_heap; |
991 |
991 |
992 /// The minimum cut value. |
992 /// The min cut value. |
993 Value _minimum_cut; |
993 Value _min_cut; |
994 /// The number of the nodes of the work graph. |
994 /// The number of the nodes of the aux graph. |
995 int _node_num; |
995 int _node_num; |
996 /// The first and last node of the min cut in the next list; |
996 /// The first and last node of the min cut in the next list; |
997 typename Graph::Node _first_node, _last_node; |
997 typename Graph::Node _first_node, _last_node; |
998 |
998 |
999 /// \brief The first and last element in the list associated |
999 /// \brief The first and last element in the list associated |
1000 /// to the work graph node. |
1000 /// to the aux graph node. |
1001 NodeRefMap *_first, *_last; |
1001 NodeRefMap *_first, *_last; |
1002 /// \brief The next node in the node lists. |
1002 /// \brief The next node in the node lists. |
1003 ListRefMap *_next; |
1003 ListRefMap *_next; |
1004 |
1004 |
1005 void create_structures() { |
1005 void create_structures() { |
1006 if (!_capacity) { |
1006 if (!_capacity) { |
1007 local_capacity = true; |
1007 local_capacity = true; |
1008 _capacity = Traits::createCapacityMap(*_graph); |
1008 _capacity = Traits::createCapacityMap(*_graph); |
1009 } |
1009 } |
1010 if(!_work_graph) { |
1010 if(!_aux_graph) { |
1011 local_work_graph = true; |
1011 local_aux_graph = true; |
1012 _work_graph = Traits::createWorkGraph(); |
1012 _aux_graph = Traits::createAuxGraph(); |
1013 } |
1013 } |
1014 if(!_work_capacity) { |
1014 if(!_aux_capacity) { |
1015 local_work_capacity = true; |
1015 local_aux_capacity = true; |
1016 _work_capacity = Traits::createWorkCapacityMap(*_work_graph); |
1016 _aux_capacity = Traits::createAuxCapacityMap(*_aux_graph); |
1017 } |
1017 } |
1018 |
1018 |
1019 _first = Traits::createNodeRefMap(*_work_graph); |
1019 _first = Traits::createNodeRefMap(*_aux_graph); |
1020 _last = Traits::createNodeRefMap(*_work_graph); |
1020 _last = Traits::createNodeRefMap(*_aux_graph); |
1021 |
1021 |
1022 _next = Traits::createListRefMap(*_graph); |
1022 _next = Traits::createListRefMap(*_graph); |
1023 |
1023 |
1024 typename Graph::template NodeMap<typename WorkGraph::Node> ref(*_graph); |
1024 typename Graph::template NodeMap<typename AuxGraph::Node> ref(*_graph); |
1025 |
1025 |
1026 for (typename Graph::NodeIt it(*_graph); it != INVALID; ++it) { |
1026 for (typename Graph::NodeIt it(*_graph); it != INVALID; ++it) { |
1027 _next->set(it, INVALID); |
1027 _next->set(it, INVALID); |
1028 typename WorkGraph::Node node = _work_graph->addNode(); |
1028 typename AuxGraph::Node node = _aux_graph->addNode(); |
1029 _first->set(node, it); |
1029 _first->set(node, it); |
1030 _last->set(node, it); |
1030 _last->set(node, it); |
1031 ref.set(it, node); |
1031 ref.set(it, node); |
1032 } |
1032 } |
1033 |
1033 |
1034 for (typename Graph::UEdgeIt it(*_graph); it != INVALID; ++it) { |
1034 for (typename Graph::UEdgeIt it(*_graph); it != INVALID; ++it) { |
1035 if (_graph->source(it) == _graph->target(it)) continue; |
1035 if (_graph->source(it) == _graph->target(it)) continue; |
1036 typename WorkGraph::UEdge uedge = |
1036 typename AuxGraph::UEdge uedge = |
1037 _work_graph->addEdge(ref[_graph->source(it)], |
1037 _aux_graph->addEdge(ref[_graph->source(it)], |
1038 ref[_graph->target(it)]); |
1038 ref[_graph->target(it)]); |
1039 _work_capacity->set(uedge, (*_capacity)[it]); |
1039 _aux_capacity->set(uedge, (*_capacity)[it]); |
1040 |
1040 |
1041 } |
1041 } |
1042 |
1042 |
1043 if (!_heap_cross_ref) { |
1043 if (!_heap_cross_ref) { |
1044 local_heap_cross_ref = true; |
1044 local_heap_cross_ref = true; |
1045 _heap_cross_ref = Traits::createHeapCrossRef(*_work_graph); |
1045 _heap_cross_ref = Traits::createHeapCrossRef(*_aux_graph); |
1046 } |
1046 } |
1047 if (!_heap) { |
1047 if (!_heap) { |
1048 local_heap = true; |
1048 local_heap = true; |
1049 _heap = Traits::createHeap(*_heap_cross_ref); |
1049 _heap = Traits::createHeap(*_heap_cross_ref); |
1050 } |
1050 } |
1051 } |
1051 } |
1052 |
1052 |
1053 public : |
1053 public : |
1054 |
1054 |
1055 typedef MinimumCut Create; |
1055 typedef MinCut Create; |
1056 |
1056 |
1057 |
1057 |
1058 /// \brief Constructor. |
1058 /// \brief Constructor. |
1059 /// |
1059 /// |
1060 ///\param graph the graph the algorithm will run on. |
1060 ///\param graph the graph the algorithm will run on. |
1061 ///\param capacity the capacity map used by the algorithm. |
1061 ///\param capacity the capacity map used by the algorithm. |
1062 MinimumCut(const Graph& graph, const CapacityMap& capacity) |
1062 MinCut(const Graph& graph, const CapacityMap& capacity) |
1063 : _graph(&graph), |
1063 : _graph(&graph), |
1064 _capacity(&capacity), local_capacity(false), |
1064 _capacity(&capacity), local_capacity(false), |
1065 _work_graph(0), local_work_graph(false), |
1065 _aux_graph(0), local_aux_graph(false), |
1066 _work_capacity(0), local_work_capacity(false), |
1066 _aux_capacity(0), local_aux_capacity(false), |
1067 _heap_cross_ref(0), local_heap_cross_ref(false), |
1067 _heap_cross_ref(0), local_heap_cross_ref(false), |
1068 _heap(0), local_heap(false), |
1068 _heap(0), local_heap(false), |
1069 _first(0), _last(0), _next(0) {} |
1069 _first(0), _last(0), _next(0) {} |
1070 |
1070 |
1071 /// \brief Constructor. |
1071 /// \brief Constructor. |
1074 /// defines how can we instantiate a local capacity map. |
1074 /// defines how can we instantiate a local capacity map. |
1075 /// If the DefNeutralCapacity used the algorithm automatically |
1075 /// If the DefNeutralCapacity used the algorithm automatically |
1076 /// construct the capacity map. |
1076 /// construct the capacity map. |
1077 /// |
1077 /// |
1078 ///\param graph the graph the algorithm will run on. |
1078 ///\param graph the graph the algorithm will run on. |
1079 MinimumCut(const Graph& graph) |
1079 MinCut(const Graph& graph) |
1080 : _graph(&graph), |
1080 : _graph(&graph), |
1081 _capacity(0), local_capacity(false), |
1081 _capacity(0), local_capacity(false), |
1082 _work_graph(0), local_work_graph(false), |
1082 _aux_graph(0), local_aux_graph(false), |
1083 _work_capacity(0), local_work_capacity(false), |
1083 _aux_capacity(0), local_aux_capacity(false), |
1084 _heap_cross_ref(0), local_heap_cross_ref(false), |
1084 _heap_cross_ref(0), local_heap_cross_ref(false), |
1085 _heap(0), local_heap(false), |
1085 _heap(0), local_heap(false), |
1086 _first(0), _last(0), _next(0) {} |
1086 _first(0), _last(0), _next(0) {} |
1087 |
1087 |
1088 /// \brief Destructor. |
1088 /// \brief Destructor. |
1089 /// |
1089 /// |
1090 /// Destructor. |
1090 /// Destructor. |
1091 ~MinimumCut() { |
1091 ~MinCut() { |
1092 if (local_heap) delete _heap; |
1092 if (local_heap) delete _heap; |
1093 if (local_heap_cross_ref) delete _heap_cross_ref; |
1093 if (local_heap_cross_ref) delete _heap_cross_ref; |
1094 if (_first) delete _first; |
1094 if (_first) delete _first; |
1095 if (_last) delete _last; |
1095 if (_last) delete _last; |
1096 if (_next) delete _next; |
1096 if (_next) delete _next; |
1097 if (local_work_capacity) delete _work_capacity; |
1097 if (local_aux_capacity) delete _aux_capacity; |
1098 if (local_work_graph) delete _work_graph; |
1098 if (local_aux_graph) delete _aux_graph; |
1099 if (local_capacity) delete _capacity; |
1099 if (local_capacity) delete _capacity; |
1100 } |
1100 } |
1101 |
1101 |
1102 /// \brief Sets the heap and the cross reference used by algorithm. |
1102 /// \brief Sets the heap and the cross reference used by algorithm. |
1103 /// |
1103 /// |
1104 /// Sets the heap and the cross reference used by algorithm. |
1104 /// Sets the heap and the cross reference used by algorithm. |
1105 /// If you don't use this function before calling \ref run(), |
1105 /// If you don't use this function before calling \ref run(), |
1106 /// it will allocate one. The destuctor deallocates this |
1106 /// it will allocate one. The destuctor deallocates this |
1107 /// automatically allocated heap and cross reference, of course. |
1107 /// automatically allocated heap and cross reference, of course. |
1108 /// \return <tt> (*this) </tt> |
1108 /// \return <tt> (*this) </tt> |
1109 MinimumCut &heap(Heap& heap, HeapCrossRef &crossRef) |
1109 MinCut &heap(Heap& heap, HeapCrossRef &crossRef) |
1110 { |
1110 { |
1111 if (local_heap_cross_ref) { |
1111 if (local_heap_cross_ref) { |
1112 delete _heap_cross_ref; |
1112 delete _heap_cross_ref; |
1113 local_heap_cross_ref=false; |
1113 local_heap_cross_ref=false; |
1114 } |
1114 } |
1119 } |
1119 } |
1120 _heap = &heap; |
1120 _heap = &heap; |
1121 return *this; |
1121 return *this; |
1122 } |
1122 } |
1123 |
1123 |
1124 /// \brief Sets the work graph. |
1124 /// \brief Sets the aux graph. |
1125 /// |
1125 /// |
1126 /// Sets the work graph used by algorithm. |
1126 /// Sets the aux graph used by algorithm. |
1127 /// If you don't use this function before calling \ref run(), |
1127 /// If you don't use this function before calling \ref run(), |
1128 /// it will allocate one. The destuctor deallocates this |
1128 /// it will allocate one. The destuctor deallocates this |
1129 /// automatically allocated graph, of course. |
1129 /// automatically allocated graph, of course. |
1130 /// \return <tt> (*this) </tt> |
1130 /// \return <tt> (*this) </tt> |
1131 MinimumCut &workGraph(WorkGraph& work_graph) |
1131 MinCut &auxGraph(AuxGraph& aux_graph) |
1132 { |
1132 { |
1133 if(local_work_graph) { |
1133 if(local_aux_graph) { |
1134 delete _work_graph; |
1134 delete _aux_graph; |
1135 local_work_graph=false; |
1135 local_aux_graph=false; |
1136 } |
1136 } |
1137 _work_graph = &work_graph; |
1137 _aux_graph = &aux_graph; |
1138 return *this; |
1138 return *this; |
1139 } |
1139 } |
1140 |
1140 |
1141 /// \brief Sets the work capacity map. |
1141 /// \brief Sets the aux capacity map. |
1142 /// |
1142 /// |
1143 /// Sets the work capacity map used by algorithm. |
1143 /// Sets the aux capacity map used by algorithm. |
1144 /// If you don't use this function before calling \ref run(), |
1144 /// If you don't use this function before calling \ref run(), |
1145 /// it will allocate one. The destuctor deallocates this |
1145 /// it will allocate one. The destuctor deallocates this |
1146 /// automatically allocated graph, of course. |
1146 /// automatically allocated graph, of course. |
1147 /// \return <tt> (*this) </tt> |
1147 /// \return <tt> (*this) </tt> |
1148 MinimumCut &workCapacityMap(WorkCapacityMap& work_capacity_map) |
1148 MinCut &auxCapacityMap(AuxCapacityMap& aux_capacity_map) |
1149 { |
1149 { |
1150 if(local_work_capacity) { |
1150 if(local_aux_capacity) { |
1151 delete _work_capacity; |
1151 delete _aux_capacity; |
1152 local_work_capacity=false; |
1152 local_aux_capacity=false; |
1153 } |
1153 } |
1154 _work_capacity = &work_capacity_map; |
1154 _aux_capacity = &aux_capacity_map; |
1155 return *this; |
1155 return *this; |
1156 } |
1156 } |
1157 |
1157 |
1158 /// \name Execution control |
1158 /// \name Execution control |
1159 /// The simplest way to execute the algorithm is to use |
1159 /// The simplest way to execute the algorithm is to use |
1176 |
1176 |
1177 /// \brief Processes the next phase |
1177 /// \brief Processes the next phase |
1178 /// |
1178 /// |
1179 /// Processes the next phase in the algorithm. The function |
1179 /// Processes the next phase in the algorithm. The function |
1180 /// should be called countNodes(graph) - 1 times to get |
1180 /// should be called countNodes(graph) - 1 times to get |
1181 /// surely the minimum cut in the graph. The |
1181 /// surely the min cut in the graph. The |
1182 /// |
1182 /// |
1183 ///\return %True when the algorithm finished. |
1183 ///\return %True when the algorithm finished. |
1184 bool processNextPhase() { |
1184 bool processNextPhase() { |
1185 if (_node_num <= 1) return true; |
1185 if (_node_num <= 1) return true; |
1186 using namespace _minimum_cut_bits; |
1186 using namespace _min_cut_bits; |
1187 |
1187 |
1188 typedef typename WorkGraph::Node Node; |
1188 typedef typename AuxGraph::Node Node; |
1189 typedef typename WorkGraph::NodeIt NodeIt; |
1189 typedef typename AuxGraph::NodeIt NodeIt; |
1190 typedef typename WorkGraph::UEdge UEdge; |
1190 typedef typename AuxGraph::UEdge UEdge; |
1191 typedef typename WorkGraph::IncEdgeIt IncEdgeIt; |
1191 typedef typename AuxGraph::IncEdgeIt IncEdgeIt; |
1192 |
1192 |
1193 typedef typename MaxCardinalitySearch<WorkGraph, WorkCapacityMap>:: |
1193 typedef typename MaxCardinalitySearch<AuxGraph, AuxCapacityMap>:: |
1194 template DefHeap<Heap, HeapCrossRef>:: |
1194 template DefHeap<Heap, HeapCrossRef>:: |
1195 template DefCardinalityMap<NullMap<Node, Value> >:: |
1195 template DefCardinalityMap<NullMap<Node, Value> >:: |
1196 template DefProcessedMap<LastTwoMap<Node> >:: |
1196 template DefProcessedMap<LastTwoMap<Node> >:: |
1197 Create MaxCardinalitySearch; |
1197 Create MaxCardinalitySearch; |
1198 |
1198 |
1199 MaxCardinalitySearch mcs(*_work_graph, *_work_capacity); |
1199 MaxCardinalitySearch mcs(*_aux_graph, *_aux_capacity); |
1200 for (NodeIt it(*_work_graph); it != INVALID; ++it) { |
1200 for (NodeIt it(*_aux_graph); it != INVALID; ++it) { |
1201 _heap_cross_ref->set(it, Heap::PRE_HEAP); |
1201 _heap_cross_ref->set(it, Heap::PRE_HEAP); |
1202 } |
1202 } |
1203 mcs.heap(*_heap, *_heap_cross_ref); |
1203 mcs.heap(*_heap, *_heap_cross_ref); |
1204 |
1204 |
1205 LastTwoMap<Node> last_two_nodes(_node_num); |
1205 LastTwoMap<Node> last_two_nodes(_node_num); |
1208 NullMap<Node, Value> cardinality; |
1208 NullMap<Node, Value> cardinality; |
1209 mcs.cardinalityMap(cardinality); |
1209 mcs.cardinalityMap(cardinality); |
1210 |
1210 |
1211 mcs.run(); |
1211 mcs.run(); |
1212 |
1212 |
1213 Node new_node = _work_graph->addNode(); |
1213 Node new_node = _aux_graph->addNode(); |
1214 |
1214 |
1215 typename WorkGraph::template NodeMap<UEdge> edges(*_work_graph, INVALID); |
1215 typename AuxGraph::template NodeMap<UEdge> edges(*_aux_graph, INVALID); |
1216 |
1216 |
1217 Node first_node = last_two_nodes[0]; |
1217 Node first_node = last_two_nodes[0]; |
1218 Node second_node = last_two_nodes[1]; |
1218 Node second_node = last_two_nodes[1]; |
1219 |
1219 |
1220 _next->set((*_last)[first_node], (*_first)[second_node]); |
1220 _next->set((*_last)[first_node], (*_first)[second_node]); |
1221 _first->set(new_node, (*_first)[first_node]); |
1221 _first->set(new_node, (*_first)[first_node]); |
1222 _last->set(new_node, (*_last)[second_node]); |
1222 _last->set(new_node, (*_last)[second_node]); |
1223 |
1223 |
1224 Value current_cut = 0; |
1224 Value current_cut = 0; |
1225 for (IncEdgeIt it(*_work_graph, first_node); it != INVALID; ++it) { |
1225 for (IncEdgeIt it(*_aux_graph, first_node); it != INVALID; ++it) { |
1226 Node node = _work_graph->runningNode(it); |
1226 Node node = _aux_graph->runningNode(it); |
1227 current_cut += (*_work_capacity)[it]; |
1227 current_cut += (*_aux_capacity)[it]; |
1228 if (node == second_node) continue; |
1228 if (node == second_node) continue; |
1229 if (edges[node] == INVALID) { |
1229 if (edges[node] == INVALID) { |
1230 edges[node] = _work_graph->addEdge(new_node, node); |
1230 edges[node] = _aux_graph->addEdge(new_node, node); |
1231 (*_work_capacity)[edges[node]] = (*_work_capacity)[it]; |
1231 (*_aux_capacity)[edges[node]] = (*_aux_capacity)[it]; |
1232 } else { |
1232 } else { |
1233 (*_work_capacity)[edges[node]] += (*_work_capacity)[it]; |
1233 (*_aux_capacity)[edges[node]] += (*_aux_capacity)[it]; |
1234 } |
1234 } |
1235 } |
1235 } |
1236 |
1236 |
1237 if (_first_node == INVALID || current_cut < _minimum_cut) { |
1237 if (_first_node == INVALID || current_cut < _min_cut) { |
1238 _first_node = (*_first)[first_node]; |
1238 _first_node = (*_first)[first_node]; |
1239 _last_node = (*_last)[first_node]; |
1239 _last_node = (*_last)[first_node]; |
1240 _minimum_cut = current_cut; |
1240 _min_cut = current_cut; |
1241 } |
1241 } |
1242 |
1242 |
1243 _work_graph->erase(first_node); |
1243 _aux_graph->erase(first_node); |
1244 |
1244 |
1245 for (IncEdgeIt it(*_work_graph, second_node); it != INVALID; ++it) { |
1245 for (IncEdgeIt it(*_aux_graph, second_node); it != INVALID; ++it) { |
1246 Node node = _work_graph->runningNode(it); |
1246 Node node = _aux_graph->runningNode(it); |
1247 if (edges[node] == INVALID) { |
1247 if (edges[node] == INVALID) { |
1248 edges[node] = _work_graph->addEdge(new_node, node); |
1248 edges[node] = _aux_graph->addEdge(new_node, node); |
1249 (*_work_capacity)[edges[node]] = (*_work_capacity)[it]; |
1249 (*_aux_capacity)[edges[node]] = (*_aux_capacity)[it]; |
1250 } else { |
1250 } else { |
1251 (*_work_capacity)[edges[node]] += (*_work_capacity)[it]; |
1251 (*_aux_capacity)[edges[node]] += (*_aux_capacity)[it]; |
1252 } |
1252 } |
1253 } |
1253 } |
1254 _work_graph->erase(second_node); |
1254 _aux_graph->erase(second_node); |
1255 |
1255 |
1256 --_node_num; |
1256 --_node_num; |
1257 return _node_num == 1; |
1257 return _node_num == 1; |
1258 } |
1258 } |
1259 |
1259 |