# HG changeset patch
# User Daniel Poroszkai <poroszd@inf.elte.hu>
# Date 1328397120 -3600
# Node ID d6df00b92912ec0c3f5863f7abc7a6f36cc2c2b9
# Parent a4a945914af3e7c3c798b763899229b9e1d05009
Update weighted bp matching to work with typesafe bipartite node sets
diff --git a/lemon/bp_matching.h b/lemon/bp_matching.h
a
|
b
|
|
45 | 45 | /// The graph type of the algorithm |
46 | 46 | typedef BGR BpGraph; |
47 | 47 | /// The type of the matching map on the red nodes |
48 | | typedef typename BpGraph::template RedMap<typename BpGraph::Edge> |
| 48 | typedef typename BpGraph::template RedNodeMap<typename BpGraph::Edge> |
49 | 49 | RedMatchingMap; |
50 | 50 | /// The type of the matching map on the blue nodes |
51 | | typedef typename BpGraph::template BlueMap<typename BpGraph::Edge> |
| 51 | typedef typename BpGraph::template BlueNodeMap<typename BpGraph::Edge> |
52 | 52 | BlueMatchingMap; |
53 | 53 | |
54 | 54 | private: |
… |
… |
|
118 | 118 | RM = new RedMatchingMap(*G, INVALID); |
119 | 119 | BM = new BlueMatchingMap(*G, INVALID); |
120 | 120 | |
121 | | for( RedIt n(*G); n != INVALID; ++n ){ |
| 121 | for( RedNodeIt n(*G); n != INVALID; ++n ){ |
122 | 122 | for( IncEdgeIt eit(*G, n); eit != INVALID; ++eit ) { |
123 | 123 | if( (*BM)[ G->blueNode(eit) ] == INVALID ){ |
124 | 124 | (*BM)[G->blueNode(eit) ] = eit; |
… |
… |
|
164 | 164 | /// called before using this function. |
165 | 165 | bool step() |
166 | 166 | { |
167 | | queue<Node> sources; |
| 167 | queue<RedNode> sources; |
168 | 168 | BoolNodeMap _processed(*G, false); |
169 | 169 | EdgeNodeMap _pred(*G, INVALID); |
170 | 170 | BoolNodeMap _reached(*G, false); |
171 | | vector<Node> H; |
| 171 | vector<RedNode> H; |
172 | 172 | bool isAlternatePath = false; |
173 | | for( RedIt n(*G); n != INVALID; ++n ){ |
| 173 | for( RedNodeIt n(*G); n != INVALID; ++n ){ |
174 | 174 | if( (*RM)[n] == INVALID ){ |
175 | 175 | sources.push( n ); |
176 | 176 | } |
177 | 177 | } |
178 | 178 | |
179 | 179 | while ( !sources.empty() && !isAlternatePath ){ |
180 | | Node s = sources.front(); |
| 180 | RedNode s = sources.front(); |
181 | 181 | if(_processed[s]) {sources.pop(); continue;} |
182 | 182 | _processed[s] = true; |
183 | 183 | _reached[s] = true; |
184 | 184 | H.push_back( s ); |
185 | | Node m; |
| 185 | BlueNode m; |
186 | 186 | for(IncEdgeIt e(*G,s);e!=INVALID;++e) { |
187 | 187 | if(!_reached[m=G->blueNode(e)]) { |
188 | 188 | _reached[m]=true; |
189 | 189 | _pred[m]=e; |
190 | 190 | if( (*BM)[m] != INVALID ) { |
191 | | Node n; |
| 191 | RedNode n; |
192 | 192 | if (!_reached[n = G->redNode((*BM)[m])] ) { |
193 | 193 | sources.push( n ); |
194 | 194 | _pred[n] = (*BM)[m]; |
… |
… |
|
257 | 257 | int matchingSize() const |
258 | 258 | { |
259 | 259 | int size = 0; |
260 | | for ( BlueIt n(*G); n != INVALID; ++n) { |
| 260 | for ( BlueNodeIt n(*G); n != INVALID; ++n) { |
261 | 261 | if ( (*BM)[n] != INVALID) { |
262 | 262 | ++size; |
263 | 263 | } |
… |
… |
|
281 | 281 | /// not covered by the matching. |
282 | 282 | Edge matching(const Node& n) const |
283 | 283 | { |
284 | | return G->blue(n) ? (*BM)[n] : (*RM)[n]; |
| 284 | return G->blue(n) ? (*BM)[G->asBlueNodeUnsafe(n)] : (*RM)[G->asRedNodeUnsafe(n)]; |
285 | 285 | } |
286 | 286 | |
287 | 287 | /// \brief Return a const reference to the blue matching map. |
… |
… |
|
310 | 310 | { |
311 | 311 | Edge e; |
312 | 312 | if( G->blue(node) ){ |
313 | | if( ( e = (*BM)[node]) != INVALID ) return G->redNode(e); |
| 313 | if( ( e = (*BM)[G->asBlueNodeUnsafe(node)]) != INVALID ) return G->redNode(e); |
314 | 314 | else return INVALID; |
315 | 315 | } |
316 | 316 | else { |
317 | | if( ( e = (*RM)[node]) != INVALID ) return G->blueNode(e); |
| 317 | if( ( e = (*RM)[G->asRedNodeUnsafe(node)]) != INVALID ) return G->blueNode(e); |
318 | 318 | else return INVALID; |
319 | 319 | } |
320 | 320 | } |
… |
… |
|
351 | 351 | typedef typename WeightMap::Value Value; |
352 | 352 | |
353 | 353 | /// The type of the red matching map |
354 | | typedef typename BpGraph::template RedMap<typename BpGraph::Edge> |
| 354 | typedef typename BpGraph::template RedNodeMap<typename BpGraph::Edge> |
355 | 355 | RedMatchingMap; |
356 | 356 | /// The type of the blue matching map |
357 | | typedef typename BpGraph::template BlueMap<typename BpGraph::Edge> |
| 357 | typedef typename BpGraph::template BlueNodeMap<typename BpGraph::Edge> |
358 | 358 | BlueMatchingMap; |
359 | 359 | |
360 | 360 | private: |
… |
… |
|
420 | 420 | BM = new BlueMatchingMap(*G, INVALID); |
421 | 421 | |
422 | 422 | int nodeCount = 0; |
423 | | for( RedIt n(*G); n != INVALID; ++n ){ |
| 423 | for( RedNodeIt n(*G); n != INVALID; ++n ){ |
424 | 424 | Value max_C = 0; |
425 | 425 | bool start = true; |
426 | 426 | vector<Edge> maxEdges; |
… |
… |
|
446 | 446 | } |
447 | 447 | nodeCount++; |
448 | 448 | } |
449 | | for( BlueIt n(*G); n != INVALID; ++n ){ |
| 449 | for( BlueNodeIt n(*G); n != INVALID; ++n ){ |
450 | 450 | Value minDif = 0; |
451 | 451 | bool start = true; |
452 | 452 | vector<Edge> minEdges; |
… |
… |
|
482 | 482 | HungAlgStatus step() |
483 | 483 | { |
484 | 484 | bool perfect = true; |
485 | | for( BlueIt n(*G); n != INVALID; ++n ){ |
| 485 | for( BlueNodeIt n(*G); n != INVALID; ++n ){ |
486 | 486 | if( (*BM)[n] == INVALID ) { |
487 | 487 | perfect = false; |
488 | 488 | break; |
489 | 489 | } |
490 | 490 | } |
491 | | for( RedIt n(*G); n != INVALID; ++n ){ |
| 491 | for( RedNodeIt n(*G); n != INVALID; ++n ){ |
492 | 492 | if( (*RM)[n] == INVALID ) { |
493 | 493 | perfect = false; |
494 | 494 | break; |
495 | 495 | } |
496 | 496 | } |
497 | 497 | if( perfect ) return HUNGALG_SUCCESS; |
498 | | queue<Node> sources; |
| 498 | queue<RedNode> sources; |
499 | 499 | BoolNodeMap _processed(*G, false); |
500 | 500 | EdgeNodeMap _pred(*G, INVALID); |
501 | 501 | BoolNodeMap _reached(*G, false); |
502 | | vector<Node> H; |
| 502 | vector<RedNode> H; |
503 | 503 | bool isAlternatePath = false; |
504 | | for( RedIt n(*G); n != INVALID; ++n ){ |
| 504 | for( RedNodeIt n(*G); n != INVALID; ++n ){ |
505 | 505 | if( (*RM)[n] == INVALID ){ |
506 | 506 | sources.push( n ); |
507 | 507 | } |
508 | 508 | } |
509 | 509 | |
510 | 510 | while ( !sources.empty() && !isAlternatePath ){ |
511 | | Node s = sources.front(); |
| 511 | RedNode s = sources.front(); |
512 | 512 | if(_processed[s]) {sources.pop(); continue;} |
513 | 513 | _processed[s] = true; |
514 | 514 | _reached[s] = true; |
515 | 515 | H.push_back( s ); |
516 | | Node m; |
| 516 | BlueNode m; |
517 | 517 | for(IncEdgeIt e(*G,s);e!=INVALID;++e) { |
518 | 518 | if( (*c)[e] != PI[G->blueNode(e)] + PI[G->redNode(e)] ) continue; |
519 | 519 | if(!_reached[m=G->blueNode(e)]) { |
520 | 520 | _reached[m]=true; |
521 | 521 | _pred[m]=e; |
522 | 522 | if( (*BM)[m] != INVALID ) { |
523 | | Node n; |
| 523 | RedNode n; |
524 | 524 | if (!_reached[n = G->redNode((*BM)[m])] ) { |
525 | 525 | sources.push( n ); |
526 | 526 | _pred[n] = (*BM)[m]; |
… |
… |
|
537 | 537 | } |
538 | 538 | |
539 | 539 | if( !isAlternatePath ) { |
540 | | vector<Node> GammaH; |
541 | | BoolBlueMap GammaH_map( *G, false ); |
542 | | for (typename vector<Node>::iterator nit = H.begin(); |
| 540 | vector<BlueNode> GammaH; |
| 541 | BoolBlueNodeMap GammaH_map( *G, false ); |
| 542 | for (typename vector<RedNode>::iterator nit = H.begin(); |
543 | 543 | nit!=H.end(); ++nit){ |
544 | 544 | for( IncEdgeIt e( *G, *nit ); e!=INVALID; ++e ){ |
545 | 545 | if( (*c)[e] != PI[G->blueNode(e)] + PI[G->redNode(e)] ) continue; |
546 | | Node n = G->blueNode( e ); |
| 546 | BlueNode n = G->blueNode( e ); |
547 | 547 | if( !GammaH_map[n] ){ |
548 | 548 | GammaH.push_back(n); |
549 | 549 | GammaH_map[n] = true; |
… |
… |
|
552 | 552 | } |
553 | 553 | Value gamma = 0; |
554 | 554 | bool start = true; |
555 | | for (typename vector<Node>::iterator nit = H.begin(); |
| 555 | for (typename vector<RedNode>::iterator nit = H.begin(); |
556 | 556 | nit!=H.end(); ++nit){ |
557 | 557 | for( IncEdgeIt e( *G, *nit ); e!=INVALID; ++e ){ |
558 | | Node n = G->oppositeNode( *nit, e ); |
| 558 | BlueNode n = G->oppositeNode( *nit, e ); |
559 | 559 | if( !GammaH_map[ n ] ){ |
560 | 560 | Value dif = PI[ G->u(e) ] + PI[ G->v(e) ] - (*c)[e]; |
561 | 561 | if( start ){ gamma=dif; start=false; continue; } |
… |
… |
|
567 | 567 | |
568 | 568 | if(!gamma) return HUNGALG_ERROR; |
569 | 569 | |
570 | | for (typename vector<Node>::iterator nit = H.begin(); |
| 570 | for (typename vector<RedNode>::iterator nit = H.begin(); |
571 | 571 | nit!=H.end(); ++nit){ |
572 | 572 | PI[*nit] -= gamma; |
573 | 573 | } |
574 | | for (typename vector<Node>::iterator nit = GammaH.begin(); |
| 574 | for (typename vector<BlueNode>::iterator nit = GammaH.begin(); |
575 | 575 | nit!=GammaH.end(); ++nit){ |
576 | 576 | PI[*nit] += gamma; |
577 | 577 | } |
… |
… |
|
631 | 631 | { |
632 | 632 | Value retVal = 0; |
633 | 633 | Edge e; |
634 | | for( BlueIt n(*G); n != INVALID; ++n ) |
| 634 | for( BlueNodeIt n(*G); n != INVALID; ++n ) |
635 | 635 | if( ( e = (*BM)[n] ) != INVALID ) retVal += (*c)[e]; |
636 | 636 | return retVal; |
637 | 637 | } |
… |
… |
|
656 | 656 | /// \pre Either run() or start() must be called before using this function. |
657 | 657 | Edge matching(const Node& node) const |
658 | 658 | { |
659 | | return G->blue(node) ? (*BM)[node] : (*RM)[node]; |
| 659 | return G->blue(node) ? (*BM)[G->asBlueNodeUnsafe(node)] : (*RM)[G->asRedNodeUnsafe(node)]; |
660 | 660 | } |
661 | 661 | |
662 | 662 | /// \brief Return a const reference to the blue matching map. |
… |
… |
|
687 | 687 | { |
688 | 688 | Edge e; |
689 | 689 | if( G->blue(node) ){ |
690 | | if( ( e = (*BM)[node]) != INVALID ) return G->redNode(e); |
| 690 | if( ( e = (*BM)[G->asBlueNodeUnsafe(node)]) != INVALID ) return G->redNode(e); |
691 | 691 | else return INVALID; |
692 | 692 | } |
693 | 693 | else { |
694 | | if( ( e = (*RM)[node]) != INVALID ) return G->blueNode(e); |
| 694 | if( ( e = (*RM)[G->asRedNodeUnsafe(node)]) != INVALID ) return G->blueNode(e); |
695 | 695 | else return INVALID; |
696 | 696 | } |
697 | 697 | } |
… |
… |
|
738 | 738 | /// The value type of the edge weights |
739 | 739 | typedef typename WeightMap::Value Value; |
740 | 740 | /// The type of the red matching map |
741 | | typedef typename BpGraph::template RedMap<typename BpGraph::Edge> |
| 741 | typedef typename BpGraph::template RedNodeMap<typename BpGraph::Edge> |
742 | 742 | RedMatchingMap; |
743 | 743 | /// The type of the blue matching map |
744 | | typedef typename BpGraph::template BlueMap<typename BpGraph::Edge> |
| 744 | typedef typename BpGraph::template BlueNodeMap<typename BpGraph::Edge> |
745 | 745 | BlueMatchingMap; |
746 | 746 | |
747 | 747 | private: |
… |
… |
|
750 | 750 | |
751 | 751 | typedef typename BpGraph::template NodeMap<Value> NodeMap; |
752 | 752 | |
753 | | typedef typename BpGraph::template RedMap<BlueNode> BlueRedMap; |
| 753 | typedef typename BpGraph::template RedNodeMap<BlueNode> BlueRedMap; |
754 | 754 | |
755 | | typedef typename BpGraph::template BlueMap<RedNode> RedBlueMap; |
| 755 | typedef typename BpGraph::template BlueNodeMap<RedNode> RedBlueMap; |
756 | 756 | |
757 | 757 | typedef typename BpGraph::template NodeMap<Edge> EdgeNodeMap; |
758 | 758 | |
… |
… |
|
770 | 770 | RedBlueMap *RBM; |
771 | 771 | BlueRedMap *BRM; |
772 | 772 | |
773 | | void _processMins( bool &processedMins, queue<Node> &sources, NodeNodeMap &_pred, BoolNodeMap &_reached, BlueNode &first ) |
| 773 | void _processMins( bool &processedMins, queue<RedNode> &sources, NodeNodeMap &_pred, BoolNodeMap &_reached, BlueNode &first ) |
774 | 774 | { |
775 | 775 | if( processedMins ) return; |
776 | 776 | processedMins = true; |
777 | | for( BlueIt m(*G); m!=INVALID; ++m ) { |
| 777 | for( BlueNodeIt m(*G); m!=INVALID; ++m ) { |
778 | 778 | if( PI[m] == -MinPI ){ |
779 | 779 | _reached[m]=true; |
780 | 780 | if( (*RBM)[m] != INVALID ) { |
781 | | Node n; |
| 781 | RedNode n; |
782 | 782 | if (!_reached[n = (*RBM)[m]] ) { |
783 | 783 | sources.push( n ); |
784 | 784 | _pred[n] = m; |
… |
… |
|
788 | 788 | } |
789 | 789 | } |
790 | 790 | |
791 | | for( RedIt m(*G); m!=INVALID; ++m ) { |
| 791 | for( RedNodeIt m(*G); m!=INVALID; ++m ) { |
792 | 792 | if( PI[m] == MinPI && !_reached[ m ] && (*BRM)[m] == INVALID ) { |
793 | 793 | sources.push( m ); |
794 | 794 | _pred[m] = INVALID; |
… |
… |
|
798 | 798 | |
799 | 799 | } |
800 | 800 | |
801 | | void _setMatching( NodeNodeMap &pred, Node n, BlueNode &first ) { |
802 | | Node node = n; |
803 | | Node prevNode = pred[n]; |
| 801 | void _setMatching( NodeNodeMap &pred, BlueNode n, BlueNode &first ) { |
| 802 | BlueNode node = n; |
| 803 | RedNode prevNode = G->asRedNodeUnsafe(pred[n]); |
804 | 804 | while( 1 ) { |
805 | 805 | if( prevNode == INVALID ){ |
806 | 806 | if( PI[node] == -MinPI ){ |
… |
… |
|
811 | 811 | else if( (*RBM)[node] != prevNode ) { |
812 | 812 | (*BRM)[prevNode] = node; |
813 | 813 | (*RBM)[node] = prevNode; |
814 | | node = pred[prevNode]; |
| 814 | node = G->asBlueNodeUnsafe(pred[prevNode]); |
815 | 815 | } |
816 | 816 | if( node == INVALID ) { |
817 | 817 | if( ( PI[prevNode] == MinPI && (*BRM)[prevNode] == INVALID ) || first == INVALID ) return; |
818 | 818 | else node = first; |
819 | 819 | } |
820 | | prevNode = pred[node]; |
| 820 | prevNode = G->asRedNodeUnsafe(pred[node]); |
821 | 821 | } |
822 | 822 | } |
823 | 823 | |
… |
… |
|
858 | 858 | BRM = new BlueRedMap(*G, INVALID); |
859 | 859 | RBM = new RedBlueMap(*G, INVALID); |
860 | 860 | |
861 | | for( BlueIt n(*G); n != INVALID; ++n ) |
| 861 | for( BlueNodeIt n(*G); n != INVALID; ++n ) |
862 | 862 | { |
863 | 863 | Value max_C = 0; |
864 | | vector<Node> maxNodes; |
| 864 | vector<RedNode> maxNodes; |
865 | 865 | for( IncEdgeIt e( *G, n ); e!=INVALID; ++e ) { |
866 | 866 | if( (*c)[e] > max_C ) { |
867 | 867 | max_C = (*c)[e]; |
… |
… |
|
873 | 873 | } |
874 | 874 | } |
875 | 875 | PI[n] = max_C; |
876 | | for (typename vector<Node>::iterator eit = maxNodes.begin(); |
| 876 | for (typename vector<RedNode>::iterator eit = maxNodes.begin(); |
877 | 877 | eit!=maxNodes.end(); ++eit) |
878 | 878 | { |
879 | 879 | if( (*BRM)[*eit] == INVALID ) |
… |
… |
|
884 | 884 | } |
885 | 885 | } |
886 | 886 | } |
887 | | for( RedIt n(*G); n != INVALID; ++n ){ |
| 887 | for( RedNodeIt n(*G); n != INVALID; ++n ){ |
888 | 888 | PI[n] = 0; |
889 | 889 | } |
890 | 890 | } |
… |
… |
|
901 | 901 | for( NodeIt n(*G); n != INVALID; ++n ){ |
902 | 902 | |
903 | 903 | if( G->blue(n) ) { |
904 | | if( (*RBM)[n] == INVALID && PI[n] != -MinPI ){ |
| 904 | if( (*RBM)[G->asBlueNodeUnsafe(n)] == INVALID && PI[n] != -MinPI ){ |
905 | 905 | Continue = true; |
906 | 906 | } |
907 | 907 | } |
908 | 908 | else { |
909 | | if( (*BRM)[n] == INVALID && PI[n] != MinPI ){ |
| 909 | if( (*BRM)[G->asRedNodeUnsafe(n)] == INVALID && PI[n] != MinPI ){ |
910 | 910 | Continue = true; |
911 | 911 | } |
912 | 912 | } |
913 | 913 | } |
914 | 914 | if( !Continue ){ |
915 | | for( RedIt n(*G); n != INVALID; ++n ) { |
| 915 | for( RedNodeIt n(*G); n != INVALID; ++n ) { |
916 | 916 | PI[n] -= MinPI; |
917 | 917 | |
918 | 918 | for( IncEdgeIt e(*G,n); e != INVALID; ++e ) { |
919 | 919 | if( (*BRM)[n] == G->blueNode(e) ) (*RM)[n] = e; |
920 | 920 | } |
921 | 921 | } |
922 | | for( BlueIt n(*G); n != INVALID; ++n ) { |
| 922 | for( BlueNodeIt n(*G); n != INVALID; ++n ) { |
923 | 923 | PI[n] += MinPI; |
924 | 924 | |
925 | 925 | for( IncEdgeIt e(*G,n); e != INVALID; ++e ) { |
… |
… |
|
929 | 929 | |
930 | 930 | return true; |
931 | 931 | } |
932 | | queue<Node> sources; |
| 932 | queue<RedNode> sources; |
933 | 933 | BoolNodeMap _processed(*G, false); |
934 | 934 | NodeNodeMap _pred(*G, INVALID); |
935 | 935 | BoolNodeMap _reached(*G, false); |
936 | | vector<Node> H; |
| 936 | vector<RedNode> H; |
937 | 937 | bool isAlternatePath = false; |
938 | 938 | bool notMinUncovered = false; |
939 | 939 | BlueNode first = INVALID; |
940 | 940 | |
941 | | for( BlueIt n(*G); n != INVALID; ++n ){ |
| 941 | for( BlueNodeIt n(*G); n != INVALID; ++n ){ |
942 | 942 | if( (*RBM)[n] == INVALID && PI[n] != -MinPI ){ |
943 | 943 | notMinUncovered = true; |
944 | 944 | break; |
945 | 945 | } |
946 | 946 | } |
947 | 947 | |
948 | | for( RedIt n(*G); n != INVALID; ++n ){ |
| 948 | for( RedNodeIt n(*G); n != INVALID; ++n ){ |
949 | 949 | if( (*BRM)[n] == INVALID ){ |
950 | 950 | if( notMinUncovered || PI[n] != MinPI ) { |
951 | 951 | sources.push( n ); |
… |
… |
|
961 | 961 | } |
962 | 962 | |
963 | 963 | while ( !sources.empty() && !isAlternatePath ){ |
964 | | Node s = sources.front(); |
| 964 | RedNode s = sources.front(); |
965 | 965 | if(_processed[s]) { sources.pop(); continue; } |
966 | 966 | if(PI[s] == MinPI && (*BRM)[s] == INVALID ) _processMins( processedMins, sources, _pred, _reached, first ); |
967 | 967 | _processed[s] = true; |
968 | 968 | _reached[s] = true; |
969 | 969 | H.push_back( s ); |
970 | | Node m; |
| 970 | BlueNode m; |
971 | 971 | for( IncEdgeIt e(*G,s); e!=INVALID; ++e ) { |
972 | 972 | if( (*c)[e] != PI[G->blueNode(e)] + PI[G->redNode(e)] ) continue; |
973 | 973 | if( _reached[m=G->blueNode(e)] ) continue; |
974 | 974 | _reached[m]=true; |
975 | 975 | _pred[m]=s; |
976 | 976 | if( (*RBM)[m] != INVALID ) { |
977 | | Node n; |
| 977 | RedNode n; |
978 | 978 | if (!_reached[n = (*RBM)[m]] ) { |
979 | 979 | sources.push( n ); |
980 | 980 | _pred[n] = m; |
… |
… |
|
994 | 994 | } |
995 | 995 | |
996 | 996 | if( !isAlternatePath ) { |
997 | | vector<Node> GammaH; |
998 | | BoolBlueMap GammaH_map( *G, false ); |
999 | | for (typename vector<Node>::iterator nit = H.begin(); |
| 997 | vector<BlueNode> GammaH; |
| 998 | BoolBlueNodeMap GammaH_map( *G, false ); |
| 999 | for (typename vector<RedNode>::iterator nit = H.begin(); |
1000 | 1000 | nit!=H.end(); ++nit){ |
1001 | 1001 | for( IncEdgeIt e( *G, *nit ); e!=INVALID; ++e ){ |
1002 | 1002 | if( (*c)[e] != PI[G->blueNode(e)] + PI[G->redNode(e)] ) continue; |
1003 | | Node n = G->blueNode( e ); |
| 1003 | BlueNode n = G->blueNode( e ); |
1004 | 1004 | if( !GammaH_map[n] ){ |
1005 | 1005 | GammaH.push_back(n); |
1006 | 1006 | GammaH_map[n] = true; |
… |
… |
|
1008 | 1008 | } |
1009 | 1009 | } |
1010 | 1010 | if( processedMins ) { |
1011 | | for( BlueIt n(*G); n != INVALID; ++n ) { |
| 1011 | for( BlueNodeIt n(*G); n != INVALID; ++n ) { |
1012 | 1012 | if( PI[n] == -MinPI && !GammaH_map[n] ) { |
1013 | 1013 | GammaH.push_back(n); |
1014 | 1014 | GammaH_map[n] = true; |
… |
… |
|
1018 | 1018 | |
1019 | 1019 | Value gamma = 0; |
1020 | 1020 | bool start = true; |
1021 | | for (typename vector<Node>::iterator nit = H.begin(); |
| 1021 | for (typename vector<RedNode>::iterator nit = H.begin(); |
1022 | 1022 | nit!=H.end(); ++nit){ |
1023 | 1023 | for( IncEdgeIt e( *G, *nit ); e!=INVALID; ++e ){ |
1024 | 1024 | if((*c)[e]<0) continue; |
1025 | | Node n = G->oppositeNode( *nit, e ); |
| 1025 | BlueNode n = G->asBlueNodeUnsafe(G->oppositeNode( *nit, e )); |
1026 | 1026 | if( !GammaH_map[ n ] ){ |
1027 | 1027 | Value dif = PI[ G->u(e) ] + PI[ G->v(e) ] - (*c)[e]; |
1028 | 1028 | if( start ){ gamma=dif; start=false; continue; } |
… |
… |
|
1033 | 1033 | } |
1034 | 1034 | |
1035 | 1035 | if( processedMins ) { |
1036 | | for( BlueIt n(*G); n != INVALID; ++n ) { |
| 1036 | for( BlueNodeIt n(*G); n != INVALID; ++n ) { |
1037 | 1037 | if( !GammaH_map[n] && ( PI[n] + MinPI < gamma || !gamma ) ) gamma = PI[n] + MinPI; |
1038 | 1038 | } |
1039 | 1039 | } |
1040 | 1040 | |
1041 | | for (typename vector<Node>::iterator nit = H.begin(); |
| 1041 | for (typename vector<RedNode>::iterator nit = H.begin(); |
1042 | 1042 | nit!=H.end(); ++nit){ |
1043 | 1043 | PI[*nit] -= gamma; |
1044 | 1044 | } |
1045 | 1045 | if( processedMins ) MinPI -= gamma; |
1046 | | for (typename vector<Node>::iterator nit = GammaH.begin(); |
| 1046 | for (typename vector<BlueNode>::iterator nit = GammaH.begin(); |
1047 | 1047 | nit!=GammaH.end(); ++nit){ |
1048 | 1048 | PI[*nit] += gamma; |
1049 | 1049 | } |
… |
… |
|
1097 | 1097 | { |
1098 | 1098 | Value retVal = 0; |
1099 | 1099 | Edge e; |
1100 | | for( BlueIt n(*G); n != INVALID; ++n ) { |
| 1100 | for( BlueNodeIt n(*G); n != INVALID; ++n ) { |
1101 | 1101 | if( ( e = (*BM)[n] ) != INVALID ) retVal += (*c)[e]; |
1102 | 1102 | } |
1103 | 1103 | return retVal; |
… |
… |
|
1111 | 1111 | int matchingSize() const |
1112 | 1112 | { |
1113 | 1113 | int size = 0; |
1114 | | for ( BlueIt n(*G); n != INVALID; ++n) { |
| 1114 | for ( BlueNodeIt n(*G); n != INVALID; ++n) { |
1115 | 1115 | if ( (*BM)[n] != INVALID) { |
1116 | 1116 | ++size; |
1117 | 1117 | } |
… |
… |
|
1139 | 1139 | /// \pre Either run() or start() must be called before using this function. |
1140 | 1140 | Edge matching( const Node& node ) const |
1141 | 1141 | { |
1142 | | return G->blue(node) ? (*BM)[node] : (*RM)[node]; |
| 1142 | return G->blue(node) ? (*BM)[G->asBlueNodeUnsafe(node)] : (*RM)[G->asRedNodeUnsafe(node)]; |
1143 | 1143 | } |
1144 | 1144 | |
1145 | 1145 | /// \brief Return a const reference to the blue matching map. |
… |
… |
|
1170 | 1170 | { |
1171 | 1171 | Edge e; |
1172 | 1172 | if( G->blue(node) ){ |
1173 | | if( ( e = (*BM)[node]) != INVALID ) return G->redNode(e); |
| 1173 | if( ( e = (*BM)[G->asBlueNodeUnsafe(node)]) != INVALID ) return G->redNode(e); |
1174 | 1174 | else return INVALID; |
1175 | 1175 | } |
1176 | 1176 | else { |
1177 | | if( ( e = (*RM)[node]) != INVALID ) return G->blueNode(e); |
| 1177 | if( ( e = (*RM)[G->asRedNodeUnsafe(node)]) != INVALID ) return G->blueNode(e); |
1178 | 1178 | else return INVALID; |
1179 | 1179 | } |
1180 | 1180 | } |