changeset 2337 | 9c3d44ac39fb |
parent 2284 | 05ff57dc401d |
child 2376 | 0ed45a6c74b1 |
0:7b08652f0c58 | 1:17fec95e6617 |
---|---|
12 * express or implied, and with no claim as to its suitability for any |
12 * express or implied, and with no claim as to its suitability for any |
13 * purpose. |
13 * purpose. |
14 * |
14 * |
15 */ |
15 */ |
16 |
16 |
17 #ifndef LEMON_MIN_CUT_H |
17 #ifndef LEMON_NAGAMOCHI_IBARAKI_H |
18 #define LEMON_MIN_CUT_H |
18 #define LEMON_NAGAMOCHI_IBARAKI_H |
19 |
19 |
20 |
20 |
21 /// \ingroup topology |
21 /// \ingroup topology |
22 /// \file |
22 /// \file |
23 /// \brief Maximum cardinality search and min cut in undirected graphs. |
23 /// \brief Maximum cardinality search and minimum cut in undirected |
24 /// graphs. |
|
24 |
25 |
25 #include <lemon/list_graph.h> |
26 #include <lemon/list_graph.h> |
26 #include <lemon/bin_heap.h> |
27 #include <lemon/bin_heap.h> |
27 #include <lemon/bucket_heap.h> |
28 #include <lemon/bucket_heap.h> |
28 |
29 |
30 #include <lemon/unionfind.h> |
|
31 #include <lemon/topology.h> |
|
32 |
|
29 #include <lemon/bits/invalid.h> |
33 #include <lemon/bits/invalid.h> |
30 #include <lemon/error.h> |
34 #include <lemon/error.h> |
31 #include <lemon/maps.h> |
35 #include <lemon/maps.h> |
32 |
36 |
33 #include <functional> |
37 #include <functional> |
38 |
|
39 #include <lemon/graph_writer.h> |
|
40 #include <lemon/time_measure.h> |
|
34 |
41 |
35 namespace lemon { |
42 namespace lemon { |
36 |
43 |
37 namespace _min_cut_bits { |
44 namespace _min_cut_bits { |
38 |
45 |
143 /// \param graph is the graph, to which we would like to define the \ref |
150 /// \param graph is the graph, to which we would like to define the \ref |
144 /// CardinalityMap |
151 /// CardinalityMap |
145 static CardinalityMap *createCardinalityMap(const Graph &graph) { |
152 static CardinalityMap *createCardinalityMap(const Graph &graph) { |
146 return new CardinalityMap(graph); |
153 return new CardinalityMap(graph); |
147 } |
154 } |
155 |
|
148 |
156 |
149 }; |
157 }; |
150 |
158 |
151 /// \ingroup topology |
159 /// \ingroup topology |
152 /// |
160 /// |
663 /// \pre \ref run() must be called before using this function. |
671 /// \pre \ref run() must be called before using this function. |
664 /// \warning If node \c v in unreachable from the root the return value |
672 /// \warning If node \c v in unreachable from the root the return value |
665 /// of this funcion is undefined. |
673 /// of this funcion is undefined. |
666 Value cardinality(Node node) const { return (*_cardinality)[node]; } |
674 Value cardinality(Node node) const { return (*_cardinality)[node]; } |
667 |
675 |
676 /// \brief The current cardinality of a node. |
|
677 /// |
|
678 /// Returns the current cardinality of a node. |
|
679 /// \pre the given node should be reached but not processed |
|
680 Value currentCardinality(Node node) const { return (*_heap)[node]; } |
|
681 |
|
668 /// \brief Returns a reference to the NodeMap of cardinalities. |
682 /// \brief Returns a reference to the NodeMap of cardinalities. |
669 /// |
683 /// |
670 /// Returns a reference to the NodeMap of cardinalities. \pre \ref run() |
684 /// Returns a reference to the NodeMap of cardinalities. \pre \ref run() |
671 /// must be called before using this function. |
685 /// must be called before using this function. |
672 const CardinalityMap &cardinalityMap() const { return *_cardinality;} |
686 const CardinalityMap &cardinalityMap() const { return *_cardinality;} |
727 #endif |
741 #endif |
728 { |
742 { |
729 throw UninitializedParameter(); |
743 throw UninitializedParameter(); |
730 } |
744 } |
731 |
745 |
746 /// \brief The CutValueMap type |
|
747 /// |
|
748 /// The type of the map that stores the cut value of a node. |
|
749 typedef AuxGraph::NodeMap<Value> AuxCutValueMap; |
|
750 |
|
751 /// \brief Instantiates a AuxCutValueMap. |
|
752 /// |
|
753 /// This function instantiates a \ref AuxCutValueMap. |
|
754 static AuxCutValueMap *createAuxCutValueMap(const AuxGraph& graph) { |
|
755 return new AuxCutValueMap(graph); |
|
756 } |
|
757 |
|
732 /// \brief The AuxCapacityMap type |
758 /// \brief The AuxCapacityMap type |
733 /// |
759 /// |
734 /// The type of the map that stores the auxing edge capacities. |
760 /// The type of the map that stores the auxiliary edge capacities. |
735 typedef AuxGraph::UEdgeMap<Value> AuxCapacityMap; |
761 typedef AuxGraph::UEdgeMap<Value> AuxCapacityMap; |
736 |
762 |
737 /// \brief Instantiates a AuxCapacityMap. |
763 /// \brief Instantiates a AuxCapacityMap. |
738 /// |
764 /// |
739 /// This function instantiates a \ref AuxCapacityMap. |
765 /// This function instantiates a \ref AuxCapacityMap. |
803 return new ListRefMap(graph); |
829 return new ListRefMap(graph); |
804 } |
830 } |
805 |
831 |
806 |
832 |
807 }; |
833 }; |
808 |
|
809 namespace _min_cut_bits { |
|
810 template <typename _Key> |
|
811 class LastTwoMap { |
|
812 public: |
|
813 typedef _Key Key; |
|
814 typedef bool Value; |
|
815 |
|
816 LastTwoMap(int _num) : num(_num) {} |
|
817 void set(const Key& key, bool val) { |
|
818 if (!val) return; |
|
819 --num; |
|
820 if (num > 1) return; |
|
821 keys[num] = key; |
|
822 } |
|
823 |
|
824 Key operator[](int index) const { return keys[index]; } |
|
825 private: |
|
826 Key keys[2]; |
|
827 int num; |
|
828 }; |
|
829 } |
|
830 |
834 |
831 /// \ingroup topology |
835 /// \ingroup topology |
832 /// |
836 /// |
833 /// \brief Calculates the minimum cut in an undirected graph. |
837 /// \brief Calculates the minimum cut in an undirected graph. |
834 /// |
838 /// |
839 /// the network reliability specifically to test how many links have |
843 /// the network reliability specifically to test how many links have |
840 /// to be destroyed in the network to split it at least two |
844 /// to be destroyed in the network to split it at least two |
841 /// distinict subnetwork. |
845 /// distinict subnetwork. |
842 /// |
846 /// |
843 /// The complexity of the algorithm is \f$ O(ne\log(n)) \f$ but with |
847 /// The complexity of the algorithm is \f$ O(ne\log(n)) \f$ but with |
844 /// Fibonacci heap it can be decreased to \f$ O(ne+n^2\log(n)) |
848 /// Fibonacci heap it can be decreased to \f$ O(ne+n^2\log(n)) \f$. |
845 /// \f$. When capacity map is neutral then it uses BucketHeap which |
849 /// When capacity map is neutral then it uses BucketHeap which |
846 /// results \f$ O(ne) \f$ time complexity. |
850 /// results \f$ O(ne) \f$ time complexity. |
851 /// |
|
852 /// \warning The value type of the capacity map should be able to hold |
|
853 /// any cut value of the graph, otherwise the result can overflow. |
|
847 #ifdef DOXYGEN |
854 #ifdef DOXYGEN |
848 template <typename _Graph, typename _CapacityMap, typename _Traits> |
855 template <typename _Graph, typename _CapacityMap, typename _Traits> |
849 #else |
856 #else |
850 template <typename _Graph = ListUGraph, |
857 template <typename _Graph = ListUGraph, |
851 typename _CapacityMap = typename _Graph::template UEdgeMap<int>, |
858 typename _CapacityMap = typename _Graph::template UEdgeMap<int>, |
878 typedef typename Traits::CapacityMap CapacityMap; |
885 typedef typename Traits::CapacityMap CapacityMap; |
879 /// The type of the aux graph |
886 /// The type of the aux graph |
880 typedef typename Traits::AuxGraph AuxGraph; |
887 typedef typename Traits::AuxGraph AuxGraph; |
881 /// The type of the aux capacity map |
888 /// The type of the aux capacity map |
882 typedef typename Traits::AuxCapacityMap AuxCapacityMap; |
889 typedef typename Traits::AuxCapacityMap AuxCapacityMap; |
890 /// The type of the aux cut value map |
|
891 typedef typename Traits::AuxCutValueMap AuxCutValueMap; |
|
883 /// The cross reference type used for the current heap. |
892 /// The cross reference type used for the current heap. |
884 typedef typename Traits::HeapCrossRef HeapCrossRef; |
893 typedef typename Traits::HeapCrossRef HeapCrossRef; |
885 /// The heap type used by the max cardinality algorithm. |
894 /// The heap type used by the max cardinality algorithm. |
886 typedef typename Traits::Heap Heap; |
895 typedef typename Traits::Heap Heap; |
887 /// The node refrefernces between the original and aux graph type. |
896 /// The node refrefernces between the original and aux graph type. |
986 /// Pointer to the aux capacity map |
995 /// Pointer to the aux capacity map |
987 AuxCapacityMap *_aux_capacity; |
996 AuxCapacityMap *_aux_capacity; |
988 /// \brief Indicates if \ref _aux_capacity is locally allocated |
997 /// \brief Indicates if \ref _aux_capacity is locally allocated |
989 /// (\c true) or not. |
998 /// (\c true) or not. |
990 bool local_aux_capacity; |
999 bool local_aux_capacity; |
1000 /// Pointer to the aux cut value map |
|
1001 AuxCutValueMap *_aux_cut_value; |
|
1002 /// \brief Indicates if \ref _aux_cut_value is locally allocated |
|
1003 /// (\c true) or not. |
|
1004 bool local_aux_cut_value; |
|
991 /// Pointer to the heap cross references. |
1005 /// Pointer to the heap cross references. |
992 HeapCrossRef *_heap_cross_ref; |
1006 HeapCrossRef *_heap_cross_ref; |
993 /// \brief Indicates if \ref _heap_cross_ref is locally allocated |
1007 /// \brief Indicates if \ref _heap_cross_ref is locally allocated |
994 /// (\c true) or not. |
1008 /// (\c true) or not. |
995 bool local_heap_cross_ref; |
1009 bool local_heap_cross_ref; |
1000 |
1014 |
1001 /// The min cut value. |
1015 /// The min cut value. |
1002 Value _min_cut; |
1016 Value _min_cut; |
1003 /// The number of the nodes of the aux graph. |
1017 /// The number of the nodes of the aux graph. |
1004 int _node_num; |
1018 int _node_num; |
1005 /// The first and last node of the min cut in the next list; |
1019 /// The first and last node of the min cut in the next list. |
1006 typename Graph::Node _first_node, _last_node; |
1020 std::vector<typename Graph::Node> _cut; |
1007 |
1021 |
1008 /// \brief The first and last element in the list associated |
1022 /// \brief The first and last element in the list associated |
1009 /// to the aux graph node. |
1023 /// to the aux graph node. |
1010 NodeRefMap *_first, *_last; |
1024 NodeRefMap *_first, *_last; |
1011 /// \brief The next node in the node lists. |
1025 /// \brief The next node in the node lists. |
1012 ListRefMap *_next; |
1026 ListRefMap *_next; |
1013 |
1027 |
1014 void create_structures() { |
1028 void createStructures() { |
1015 if (!_capacity) { |
1029 if (!_capacity) { |
1016 local_capacity = true; |
1030 local_capacity = true; |
1017 _capacity = Traits::createCapacityMap(*_graph); |
1031 _capacity = Traits::createCapacityMap(*_graph); |
1018 } |
1032 } |
1019 if(!_aux_graph) { |
1033 if(!_aux_graph) { |
1022 } |
1036 } |
1023 if(!_aux_capacity) { |
1037 if(!_aux_capacity) { |
1024 local_aux_capacity = true; |
1038 local_aux_capacity = true; |
1025 _aux_capacity = Traits::createAuxCapacityMap(*_aux_graph); |
1039 _aux_capacity = Traits::createAuxCapacityMap(*_aux_graph); |
1026 } |
1040 } |
1041 if(!_aux_cut_value) { |
|
1042 local_aux_cut_value = true; |
|
1043 _aux_cut_value = Traits::createAuxCutValueMap(*_aux_graph); |
|
1044 } |
|
1027 |
1045 |
1028 _first = Traits::createNodeRefMap(*_aux_graph); |
1046 _first = Traits::createNodeRefMap(*_aux_graph); |
1029 _last = Traits::createNodeRefMap(*_aux_graph); |
1047 _last = Traits::createNodeRefMap(*_aux_graph); |
1030 |
1048 |
1031 _next = Traits::createListRefMap(*_graph); |
1049 _next = Traits::createListRefMap(*_graph); |
1032 |
|
1033 typename Graph::template NodeMap<typename AuxGraph::Node> ref(*_graph); |
|
1034 |
|
1035 for (typename Graph::NodeIt it(*_graph); it != INVALID; ++it) { |
|
1036 _next->set(it, INVALID); |
|
1037 typename AuxGraph::Node node = _aux_graph->addNode(); |
|
1038 _first->set(node, it); |
|
1039 _last->set(node, it); |
|
1040 ref.set(it, node); |
|
1041 } |
|
1042 |
|
1043 for (typename Graph::UEdgeIt it(*_graph); it != INVALID; ++it) { |
|
1044 if (_graph->source(it) == _graph->target(it)) continue; |
|
1045 typename AuxGraph::UEdge uedge = |
|
1046 _aux_graph->addEdge(ref[_graph->source(it)], |
|
1047 ref[_graph->target(it)]); |
|
1048 _aux_capacity->set(uedge, (*_capacity)[it]); |
|
1049 |
|
1050 } |
|
1051 |
1050 |
1052 if (!_heap_cross_ref) { |
1051 if (!_heap_cross_ref) { |
1053 local_heap_cross_ref = true; |
1052 local_heap_cross_ref = true; |
1054 _heap_cross_ref = Traits::createHeapCrossRef(*_aux_graph); |
1053 _heap_cross_ref = Traits::createHeapCrossRef(*_aux_graph); |
1055 } |
1054 } |
1056 if (!_heap) { |
1055 if (!_heap) { |
1057 local_heap = true; |
1056 local_heap = true; |
1058 _heap = Traits::createHeap(*_heap_cross_ref); |
1057 _heap = Traits::createHeap(*_heap_cross_ref); |
1059 } |
1058 } |
1060 } |
1059 } |
1060 |
|
1061 void createAuxGraph() { |
|
1062 typename Graph::template NodeMap<typename AuxGraph::Node> ref(*_graph); |
|
1063 |
|
1064 for (typename Graph::NodeIt n(*_graph); n != INVALID; ++n) { |
|
1065 _next->set(n, INVALID); |
|
1066 typename AuxGraph::Node node = _aux_graph->addNode(); |
|
1067 _first->set(node, n); |
|
1068 _last->set(node, n); |
|
1069 ref.set(n, node); |
|
1070 } |
|
1071 |
|
1072 typename AuxGraph::template NodeMap<typename AuxGraph::UEdge> |
|
1073 edges(*_aux_graph, INVALID); |
|
1074 |
|
1075 for (typename Graph::NodeIt n(*_graph); n != INVALID; ++n) { |
|
1076 for (typename Graph::IncEdgeIt e(*_graph, n); e != INVALID; ++e) { |
|
1077 typename Graph::Node tn = _graph->runningNode(e); |
|
1078 if (n < tn || n == tn) continue; |
|
1079 if (edges[ref[tn]] != INVALID) { |
|
1080 Value value = |
|
1081 (*_aux_capacity)[edges[ref[tn]]] + (*_capacity)[e]; |
|
1082 _aux_capacity->set(edges[ref[tn]], value); |
|
1083 } else { |
|
1084 edges.set(ref[tn], _aux_graph->addEdge(ref[n], ref[tn])); |
|
1085 Value value = (*_capacity)[e]; |
|
1086 _aux_capacity->set(edges[ref[tn]], value); |
|
1087 } |
|
1088 } |
|
1089 for (typename Graph::IncEdgeIt e(*_graph, n); e != INVALID; ++e) { |
|
1090 typename Graph::Node tn = _graph->runningNode(e); |
|
1091 edges.set(ref[tn], INVALID); |
|
1092 } |
|
1093 } |
|
1094 |
|
1095 _cut.resize(1, INVALID); |
|
1096 _min_cut = std::numeric_limits<Value>::max(); |
|
1097 for (typename AuxGraph::NodeIt n(*_aux_graph); n != INVALID; ++n) { |
|
1098 Value value = 0; |
|
1099 for (typename AuxGraph::IncEdgeIt e(*_aux_graph, n); |
|
1100 e != INVALID; ++e) { |
|
1101 value += (*_aux_capacity)[e]; |
|
1102 } |
|
1103 if (_min_cut > value) { |
|
1104 _min_cut = value; |
|
1105 _cut[0] = (*_first)[n]; |
|
1106 } |
|
1107 (*_aux_cut_value)[n] = value; |
|
1108 } |
|
1109 } |
|
1110 |
|
1061 |
1111 |
1062 public : |
1112 public : |
1063 |
1113 |
1064 typedef NagamochiIbaraki Create; |
1114 typedef NagamochiIbaraki Create; |
1065 |
1115 |
1071 NagamochiIbaraki(const Graph& graph, const CapacityMap& capacity) |
1121 NagamochiIbaraki(const Graph& graph, const CapacityMap& capacity) |
1072 : _graph(&graph), |
1122 : _graph(&graph), |
1073 _capacity(&capacity), local_capacity(false), |
1123 _capacity(&capacity), local_capacity(false), |
1074 _aux_graph(0), local_aux_graph(false), |
1124 _aux_graph(0), local_aux_graph(false), |
1075 _aux_capacity(0), local_aux_capacity(false), |
1125 _aux_capacity(0), local_aux_capacity(false), |
1126 _aux_cut_value(0), local_aux_cut_value(false), |
|
1076 _heap_cross_ref(0), local_heap_cross_ref(false), |
1127 _heap_cross_ref(0), local_heap_cross_ref(false), |
1077 _heap(0), local_heap(false), |
1128 _heap(0), local_heap(false), |
1078 _first(0), _last(0), _next(0) {} |
1129 _first(0), _last(0), _next(0) {} |
1079 |
1130 |
1080 /// \brief Constructor. |
1131 /// \brief Constructor. |
1088 NagamochiIbaraki(const Graph& graph) |
1139 NagamochiIbaraki(const Graph& graph) |
1089 : _graph(&graph), |
1140 : _graph(&graph), |
1090 _capacity(0), local_capacity(false), |
1141 _capacity(0), local_capacity(false), |
1091 _aux_graph(0), local_aux_graph(false), |
1142 _aux_graph(0), local_aux_graph(false), |
1092 _aux_capacity(0), local_aux_capacity(false), |
1143 _aux_capacity(0), local_aux_capacity(false), |
1144 _aux_cut_value(0), local_aux_cut_value(false), |
|
1093 _heap_cross_ref(0), local_heap_cross_ref(false), |
1145 _heap_cross_ref(0), local_heap_cross_ref(false), |
1094 _heap(0), local_heap(false), |
1146 _heap(0), local_heap(false), |
1095 _first(0), _last(0), _next(0) {} |
1147 _first(0), _last(0), _next(0) {} |
1096 |
1148 |
1097 /// \brief Destructor. |
1149 /// \brief Destructor. |
1102 if (local_heap_cross_ref) delete _heap_cross_ref; |
1154 if (local_heap_cross_ref) delete _heap_cross_ref; |
1103 if (_first) delete _first; |
1155 if (_first) delete _first; |
1104 if (_last) delete _last; |
1156 if (_last) delete _last; |
1105 if (_next) delete _next; |
1157 if (_next) delete _next; |
1106 if (local_aux_capacity) delete _aux_capacity; |
1158 if (local_aux_capacity) delete _aux_capacity; |
1159 if (local_aux_cut_value) delete _aux_cut_value; |
|
1107 if (local_aux_graph) delete _aux_graph; |
1160 if (local_aux_graph) delete _aux_graph; |
1108 if (local_capacity) delete _capacity; |
1161 if (local_capacity) delete _capacity; |
1109 } |
1162 } |
1110 |
1163 |
1111 /// \brief Sets the heap and the cross reference used by algorithm. |
1164 /// \brief Sets the heap and the cross reference used by algorithm. |
1176 |
1229 |
1177 /// \brief Initializes the internal data structures. |
1230 /// \brief Initializes the internal data structures. |
1178 /// |
1231 /// |
1179 /// Initializes the internal data structures. |
1232 /// Initializes the internal data structures. |
1180 void init() { |
1233 void init() { |
1181 create_structures(); |
|
1182 _first_node = _last_node = INVALID; |
|
1183 _node_num = countNodes(*_graph); |
1234 _node_num = countNodes(*_graph); |
1184 } |
1235 createStructures(); |
1236 createAuxGraph(); |
|
1237 } |
|
1238 |
|
1239 private: |
|
1240 |
|
1241 struct EdgeInfo { |
|
1242 typename AuxGraph::Node source, target; |
|
1243 Value capacity; |
|
1244 }; |
|
1245 |
|
1246 struct EdgeInfoLess { |
|
1247 bool operator()(const EdgeInfo& left, const EdgeInfo& right) const { |
|
1248 return (left.source < right.source) || |
|
1249 (left.source == right.source && left.target < right.target); |
|
1250 } |
|
1251 }; |
|
1252 |
|
1253 public: |
|
1254 |
|
1185 |
1255 |
1186 /// \brief Processes the next phase |
1256 /// \brief Processes the next phase |
1187 /// |
1257 /// |
1188 /// Processes the next phase in the algorithm. The function |
1258 /// Processes the next phase in the algorithm. The function should |
1189 /// should be called countNodes(graph) - 1 times to get |
1259 /// be called at most countNodes(graph) - 1 times to get surely |
1190 /// surely the min cut in the graph. The |
1260 /// the min cut in the graph. |
1191 /// |
1261 /// |
1192 ///\return %True when the algorithm finished. |
1262 ///\return %True when the algorithm finished. |
1193 bool processNextPhase() { |
1263 bool processNextPhase() { |
1194 if (_node_num <= 1) return true; |
1264 if (_node_num <= 1) return true; |
1195 using namespace _min_cut_bits; |
|
1196 |
1265 |
1197 typedef typename AuxGraph::Node Node; |
1266 typedef typename AuxGraph::Node Node; |
1198 typedef typename AuxGraph::NodeIt NodeIt; |
1267 typedef typename AuxGraph::NodeIt NodeIt; |
1199 typedef typename AuxGraph::UEdge UEdge; |
1268 typedef typename AuxGraph::UEdge UEdge; |
1269 typedef typename AuxGraph::UEdgeIt UEdgeIt; |
|
1200 typedef typename AuxGraph::IncEdgeIt IncEdgeIt; |
1270 typedef typename AuxGraph::IncEdgeIt IncEdgeIt; |
1201 |
1271 |
1202 typedef typename MaxCardinalitySearch<AuxGraph, AuxCapacityMap>:: |
1272 typename AuxGraph::template UEdgeMap<Value> _edge_cut(*_aux_graph); |
1203 template DefHeap<Heap, HeapCrossRef>:: |
1273 |
1204 template DefCardinalityMap<NullMap<Node, Value> >:: |
1274 |
1205 template DefProcessedMap<LastTwoMap<Node> >:: |
1275 for (NodeIt n(*_aux_graph); n != INVALID; ++n) { |
1206 Create MaxCardinalitySearch; |
1276 _heap_cross_ref->set(n, Heap::PRE_HEAP); |
1277 } |
|
1278 |
|
1279 std::vector<Node> nodes; |
|
1280 nodes.reserve(_node_num); |
|
1281 int sep = 0; |
|
1282 |
|
1283 Value alpha = 0; |
|
1284 Value emc = std::numeric_limits<Value>::max(); |
|
1285 |
|
1286 _heap->push(typename AuxGraph::NodeIt(*_aux_graph), 0); |
|
1287 while (!_heap->empty()) { |
|
1288 Node node = _heap->top(); |
|
1289 Value value = _heap->prio(); |
|
1290 |
|
1291 _heap->pop(); |
|
1292 for (typename AuxGraph::IncEdgeIt e(*_aux_graph, node); |
|
1293 e != INVALID; ++e) { |
|
1294 Node tn = _aux_graph->runningNode(e); |
|
1295 switch (_heap->state(tn)) { |
|
1296 case Heap::PRE_HEAP: |
|
1297 _heap->push(tn, (*_aux_capacity)[e]); |
|
1298 _edge_cut[e] = (*_heap)[tn]; |
|
1299 break; |
|
1300 case Heap::IN_HEAP: |
|
1301 _heap->decrease(tn, (*_aux_capacity)[e] + (*_heap)[tn]); |
|
1302 _edge_cut[e] = (*_heap)[tn]; |
|
1303 break; |
|
1304 case Heap::POST_HEAP: |
|
1305 break; |
|
1306 } |
|
1307 } |
|
1308 |
|
1309 alpha += (*_aux_cut_value)[node]; |
|
1310 alpha -= 2 * value; |
|
1311 |
|
1312 nodes.push_back(node); |
|
1313 if (!_heap->empty()) { |
|
1314 if (alpha < emc) { |
|
1315 emc = alpha; |
|
1316 sep = nodes.size(); |
|
1317 } |
|
1318 } |
|
1319 } |
|
1320 |
|
1321 if ((int)nodes.size() < _node_num) { |
|
1322 _aux_graph->clear(); |
|
1323 _node_num = 1; |
|
1324 _cut.clear(); |
|
1325 for (int i = 0; i < (int)nodes.size(); ++i) { |
|
1326 typename Graph::Node n = (*_first)[nodes[i]]; |
|
1327 while (n != INVALID) { |
|
1328 _cut.push_back(n); |
|
1329 n = (*_next)[n]; |
|
1330 } |
|
1331 } |
|
1332 _min_cut = 0; |
|
1333 return true; |
|
1334 } |
|
1335 |
|
1336 if (emc < _min_cut) { |
|
1337 _cut.clear(); |
|
1338 for (int i = 0; i < sep; ++i) { |
|
1339 typename Graph::Node n = (*_first)[nodes[i]]; |
|
1340 while (n != INVALID) { |
|
1341 _cut.push_back(n); |
|
1342 n = (*_next)[n]; |
|
1343 } |
|
1344 } |
|
1345 _min_cut = emc; |
|
1346 } |
|
1347 |
|
1348 typedef typename AuxGraph::template NodeMap<int> UfeCr; |
|
1349 UfeCr ufecr(*_aux_graph); |
|
1350 typedef UnionFindEnum<UfeCr> Ufe; |
|
1351 Ufe ufe(ufecr); |
|
1352 |
|
1353 for (typename AuxGraph::NodeIt n(*_aux_graph); n != INVALID; ++n) { |
|
1354 ufe.insert(n); |
|
1355 } |
|
1356 |
|
1357 for (typename AuxGraph::UEdgeIt e(*_aux_graph); e != INVALID; ++e) { |
|
1358 if (_edge_cut[e] >= emc) { |
|
1359 ufe.join(_aux_graph->source(e), _aux_graph->target(e)); |
|
1360 } |
|
1361 } |
|
1362 |
|
1363 if (ufe.size((typename Ufe::ClassIt)(ufe)) == _node_num) { |
|
1364 _aux_graph->clear(); |
|
1365 _node_num = 1; |
|
1366 return true; |
|
1367 } |
|
1207 |
1368 |
1208 MaxCardinalitySearch mcs(*_aux_graph, *_aux_capacity); |
1369 std::vector<typename AuxGraph::Node> remnodes; |
1209 for (NodeIt it(*_aux_graph); it != INVALID; ++it) { |
|
1210 _heap_cross_ref->set(it, Heap::PRE_HEAP); |
|
1211 } |
|
1212 mcs.heap(*_heap, *_heap_cross_ref); |
|
1213 |
|
1214 LastTwoMap<Node> last_two_nodes(_node_num); |
|
1215 mcs.processedMap(last_two_nodes); |
|
1216 |
|
1217 NullMap<Node, Value> cardinality; |
|
1218 mcs.cardinalityMap(cardinality); |
|
1219 |
|
1220 mcs.run(); |
|
1221 |
|
1222 Node new_node = _aux_graph->addNode(); |
|
1223 |
1370 |
1224 typename AuxGraph::template NodeMap<UEdge> edges(*_aux_graph, INVALID); |
1371 typename AuxGraph::template NodeMap<UEdge> edges(*_aux_graph, INVALID); |
1225 |
1372 for (typename Ufe::ClassIt c(ufe); c != INVALID; ++c) { |
1226 Node first_node = last_two_nodes[0]; |
1373 if (ufe.size(c) == 1) continue; |
1227 Node second_node = last_two_nodes[1]; |
1374 for (typename Ufe::ItemIt r(ufe, c); r != INVALID; ++r) { |
1228 |
1375 if ((Node)r == (Node)c) continue; |
1229 _next->set((*_last)[first_node], (*_first)[second_node]); |
1376 _next->set((*_last)[c], (*_first)[r]); |
1230 _first->set(new_node, (*_first)[first_node]); |
1377 _last->set(c, (*_last)[r]); |
1231 _last->set(new_node, (*_last)[second_node]); |
1378 remnodes.push_back(r); |
1232 |
1379 --_node_num; |
1233 Value current_cut = 0; |
1380 } |
1234 for (IncEdgeIt it(*_aux_graph, first_node); it != INVALID; ++it) { |
1381 } |
1235 Node node = _aux_graph->runningNode(it); |
1382 |
1236 current_cut += (*_aux_capacity)[it]; |
1383 std::vector<EdgeInfo> addedges; |
1237 if (node == second_node) continue; |
1384 std::vector<UEdge> remedges; |
1238 if (edges[node] == INVALID) { |
1385 |
1239 edges[node] = _aux_graph->addEdge(new_node, node); |
1386 for (typename AuxGraph::UEdgeIt e(*_aux_graph); |
1240 (*_aux_capacity)[edges[node]] = (*_aux_capacity)[it]; |
1387 e != INVALID; ++e) { |
1388 Node sn = ufe.find(_aux_graph->source(e)); |
|
1389 Node tn = ufe.find(_aux_graph->target(e)); |
|
1390 if ((ufe.size(sn) == 1 && ufe.size(tn) == 1)) { |
|
1391 continue; |
|
1392 } |
|
1393 if (sn == tn) { |
|
1394 remedges.push_back(e); |
|
1395 continue; |
|
1396 } |
|
1397 EdgeInfo info; |
|
1398 if (sn < tn) { |
|
1399 info.source = sn; |
|
1400 info.target = tn; |
|
1241 } else { |
1401 } else { |
1242 (*_aux_capacity)[edges[node]] += (*_aux_capacity)[it]; |
1402 info.source = tn; |
1403 info.target = sn; |
|
1243 } |
1404 } |
1244 } |
1405 info.capacity = (*_aux_capacity)[e]; |
1245 |
1406 addedges.push_back(info); |
1246 if (_first_node == INVALID || current_cut < _min_cut) { |
1407 remedges.push_back(e); |
1247 _first_node = (*_first)[first_node]; |
1408 } |
1248 _last_node = (*_last)[first_node]; |
1409 |
1249 _min_cut = current_cut; |
1410 for (int i = 0; i < (int)remedges.size(); ++i) { |
1250 } |
1411 _aux_graph->erase(remedges[i]); |
1251 |
1412 } |
1252 _aux_graph->erase(first_node); |
1413 |
1253 |
1414 sort(addedges.begin(), addedges.end(), EdgeInfoLess()); |
1254 for (IncEdgeIt it(*_aux_graph, second_node); it != INVALID; ++it) { |
1415 |
1255 Node node = _aux_graph->runningNode(it); |
1416 { |
1256 if (edges[node] == INVALID) { |
1417 int i = 0; |
1257 edges[node] = _aux_graph->addEdge(new_node, node); |
1418 while (i < (int)addedges.size()) { |
1258 (*_aux_capacity)[edges[node]] = (*_aux_capacity)[it]; |
1419 Node sn = addedges[i].source; |
1259 } else { |
1420 Node tn = addedges[i].target; |
1260 (*_aux_capacity)[edges[node]] += (*_aux_capacity)[it]; |
1421 Value ec = addedges[i].capacity; |
1422 ++i; |
|
1423 while (i < (int)addedges.size() && |
|
1424 sn == addedges[i].source && tn == addedges[i].target) { |
|
1425 ec += addedges[i].capacity; |
|
1426 ++i; |
|
1427 } |
|
1428 typename AuxGraph::UEdge ne = _aux_graph->addEdge(sn, tn); |
|
1429 (*_aux_capacity)[ne] = ec; |
|
1261 } |
1430 } |
1262 } |
1431 } |
1263 _aux_graph->erase(second_node); |
1432 |
1264 |
1433 for (typename Ufe::ClassIt c(ufe); c != INVALID; ++c) { |
1265 --_node_num; |
1434 if (ufe.size(c) == 1) continue; |
1435 Value cutvalue = 0; |
|
1436 for (typename AuxGraph::IncEdgeIt e(*_aux_graph, c); |
|
1437 e != INVALID; ++e) { |
|
1438 cutvalue += (*_aux_capacity)[e]; |
|
1439 } |
|
1440 |
|
1441 (*_aux_cut_value)[c] = cutvalue; |
|
1442 |
|
1443 } |
|
1444 |
|
1445 for (int i = 0; i < (int)remnodes.size(); ++i) { |
|
1446 _aux_graph->erase(remnodes[i]); |
|
1447 } |
|
1448 |
|
1266 return _node_num == 1; |
1449 return _node_num == 1; |
1267 } |
1450 } |
1268 |
1451 |
1269 /// \brief Executes the algorithm. |
1452 /// \brief Executes the algorithm. |
1270 /// |
1453 /// |
1315 /// It sets the nodes of one of the two partitions to true in |
1498 /// It sets the nodes of one of the two partitions to true in |
1316 /// the given BoolNodeMap. The map contains a valid cut if the |
1499 /// the given BoolNodeMap. The map contains a valid cut if the |
1317 /// map have been set false previously. |
1500 /// map have been set false previously. |
1318 template <typename NodeMap> |
1501 template <typename NodeMap> |
1319 Value quickMinCut(NodeMap& nodeMap) const { |
1502 Value quickMinCut(NodeMap& nodeMap) const { |
1320 for (typename Graph::Node it = _first_node; |
1503 for (int i = 0; i < (int)_cut.size(); ++i) { |
1321 it != _last_node; it = (*_next)[it]) { |
1504 nodeMap.set(_cut[i], true); |
1322 nodeMap.set(it, true); |
1505 } |
1323 } |
|
1324 nodeMap.set(_last_node, true); |
|
1325 return minCut(); |
1506 return minCut(); |
1326 } |
1507 } |
1327 |
1508 |
1328 /// \brief Returns a min cut in a NodeMap. |
1509 /// \brief Returns a min cut in a NodeMap. |
1329 /// |
1510 /// |
1353 return minCut(); |
1534 return minCut(); |
1354 } |
1535 } |
1355 |
1536 |
1356 ///@} |
1537 ///@} |
1357 |
1538 |
1539 private: |
|
1540 |
|
1541 |
|
1358 }; |
1542 }; |
1359 } |
1543 } |
1360 |
1544 |
1361 #endif |
1545 #endif |