Boost logo

Boost-Commit :

Subject: [Boost-commit] svn:boost r54064 - in branches/release: boost/graph boost/graph/distributed libs/graph/doc libs/graph/test libs/graph_parallel/example libs/graph_parallel/test status
From: jewillco_at_[hidden]
Date: 2009-06-18 15:34:29


Author: jewillco
Date: 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
New Revision: 54064
URL: http://svn.boost.org/trac/boost/changeset/54064

Log:
Merged in commits on trunk mentioned in comments 1-32 of #3134, plus r54059 not listed there; refs #3134
Added:
   branches/release/libs/graph_parallel/example/Jamfile.v2
      - copied, changed from r53934, /trunk/libs/graph_parallel/example/Jamfile.v2
   branches/release/libs/graph_parallel/test/Jamfile.v2
      - copied, changed from r53934, /trunk/libs/graph_parallel/test/Jamfile.v2
Text files modified:
   branches/release/boost/graph/adj_list_serialize.hpp | 17
   branches/release/boost/graph/adjacency_list_io.hpp | 44 ++--
   branches/release/boost/graph/astar_search.hpp | 17 -
   branches/release/boost/graph/bc_clustering.hpp | 8
   branches/release/boost/graph/compressed_sparse_row_graph.hpp | 369 ++++++++++++++++++++++++++++++++++-----
   branches/release/boost/graph/cuthill_mckee_ordering.hpp | 5
   branches/release/boost/graph/depth_first_search.hpp | 10
   branches/release/boost/graph/distributed/adjacency_list.hpp | 2
   branches/release/boost/graph/distributed/betweenness_centrality.hpp | 8
   branches/release/boost/graph/distributed/connected_components.hpp | 1
   branches/release/boost/graph/distributed/eager_dijkstra_shortest_paths.hpp | 12 -
   branches/release/boost/graph/edge_connectivity.hpp | 6
   branches/release/boost/graph/graph_utility.hpp | 21 ++
   branches/release/boost/graph/howard_cycle_ratio.hpp | 3
   branches/release/boost/graph/isomorphism.hpp | 10
   branches/release/boost/graph/iteration_macros.hpp | 69 ++++---
   branches/release/boost/graph/king_ordering.hpp | 5
   branches/release/boost/graph/metric_tsp_approx.hpp | 2
   branches/release/boost/graph/named_function_params.hpp | 6
   branches/release/boost/graph/properties.hpp | 8
   branches/release/boost/graph/push_relabel_max_flow.hpp | 43 ++--
   branches/release/boost/graph/relax.hpp | 7
   branches/release/boost/graph/rmat_graph_generator.hpp | 21 +
   branches/release/libs/graph/doc/compressed_sparse_row.html | 112 +++++++++++
   branches/release/libs/graph/test/Jamfile.v2 | 2
   branches/release/libs/graph/test/betweenness_centrality_test.cpp | 7
   branches/release/libs/graph/test/csr_graph_test.cpp | 15 +
   branches/release/libs/graph/test/gursoy_atun_layout_test.cpp | 8
   branches/release/libs/graph_parallel/example/Jamfile.v2 | 6
   branches/release/libs/graph_parallel/example/breadth_first_search.cpp | 2
   branches/release/libs/graph_parallel/example/dijkstra_shortest_paths.cpp | 2
   branches/release/libs/graph_parallel/test/Jamfile.v2 | 40 ++--
   branches/release/libs/graph_parallel/test/distributed_adjacency_list_test.cpp | 6
   branches/release/libs/graph_parallel/test/distributed_dfs_test.cpp | 2
   branches/release/libs/graph_parallel/test/distributed_property_map_test.cpp | 4
   branches/release/status/explicit-failures-markup.xml | 12 +
   36 files changed, 671 insertions(+), 241 deletions(-)

Modified: branches/release/boost/graph/adj_list_serialize.hpp
==============================================================================
--- branches/release/boost/graph/adj_list_serialize.hpp (original)
+++ branches/release/boost/graph/adj_list_serialize.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -10,6 +10,7 @@
 #define ADJ_LIST_SERIALIZE_HPP
 
 #include <boost/graph/adjacency_list.hpp>
+#include <boost/graph/iteration_macros.hpp>
 #include <boost/pending/property_serialize.hpp>
 #include <boost/config.hpp>
 #include <boost/detail/workaround.hpp>
@@ -49,18 +50,16 @@
   // assign indices to vertices
   std::map<Vertex,int> indices;
   int num = 0;
- typename graph_traits<Graph>::vertex_iterator vi;
- for (vi = vertices(graph).first; vi != vertices(graph).second; ++vi) {
- indices[*vi] = num++;
- ar << serialization::make_nvp("vertex_property", get(vertex_all_t(), graph, *vi) );
+ BGL_FORALL_VERTICES_T(v, graph, Graph) {
+ indices[v] = num++;
+ ar << serialization::make_nvp("vertex_property", get(vertex_all_t(), graph, v) );
   }
   
   // write edges
- typename graph_traits<Graph>::edge_iterator ei;
- for (ei = edges(graph).first; ei != edges(graph).second; ++ei){
- ar << serialization::make_nvp("u" , indices[source(*ei,graph)]);
- ar << serialization::make_nvp("v" , indices[target(*ei,graph)]);
- ar << serialization::make_nvp("edge_property", get(edge_all_t(), graph, *ei) );
+ BGL_FORALL_EDGES_T(e, graph, Graph) {
+ ar << serialization::make_nvp("u" , indices[source(e,graph)]);
+ ar << serialization::make_nvp("v" , indices[target(e,graph)]);
+ ar << serialization::make_nvp("edge_property", get(edge_all_t(), graph, e) );
   }
 }
 

Modified: branches/release/boost/graph/adjacency_list_io.hpp
==============================================================================
--- branches/release/boost/graph/adjacency_list_io.hpp (original)
+++ branches/release/boost/graph/adjacency_list_io.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -12,6 +12,7 @@
 #include <iostream>
 #include <vector>
 #include <boost/graph/adjacency_list.hpp>
+#include <boost/graph/iteration_macros.hpp>
 #include <cctype>
 
 // Method read to parse an adjacency list from an input stream. Examples:
@@ -211,13 +212,13 @@
         
         PropertyPrinter( const Graph& g ):graph(&g){}
         
- template<class Iterator>
- PropertyPrinter& operator () ( std::ostream& out, Iterator it )
+ template<class Val>
+ PropertyPrinter& operator () ( std::ostream& out, const Val& v )
         {
                 typename property_map<Graph,Tag>::type ps = get(Tag(), *graph);
- out << ps[ *it ] <<" ";
+ out << ps[ v ] <<" ";
                 PropertyPrinter<Graph,Next> print(*graph);
- print(out, it);
+ print(out, v);
                 return (*this);
         }
 private:
@@ -229,10 +230,10 @@
 {
         PropertyPrinter( const Graph& g ):graph(&g){}
         
- template<class Iterator>
- PropertyPrinter& operator () ( std::ostream& out, Iterator it )
+ template<class Val>
+ PropertyPrinter& operator () ( std::ostream& out, const Val& v )
         {
- out << (*graph)[ *it ] <<" ";
+ out << (*graph)[ v ] <<" ";
                 return (*this);
         }
 private:
@@ -244,13 +245,13 @@
 {
         PropertyPrinter( const Graph& g ):graph(&g){}
         
- template<class Iterator>
- PropertyPrinter& operator () ( std::ostream& out, Iterator it )
+ template<class Val>
+ PropertyPrinter& operator () ( std::ostream& out, const Val& v )
         {
                 typename property_map<Graph,Tag>::type ps = get(Tag(), *graph);
- out << ps[ *it ] <<" ";
+ out << ps[ v ] <<" ";
                 PropertyPrinter<Graph,Next> print(*graph);
- print(out, it);
+ print(out, v);
                 return (*this);
         }
 private:
@@ -263,8 +264,8 @@
 {
         PropertyPrinter( const Graph& ){}
 
- template<class Iterator>
- PropertyPrinter& operator () ( std::ostream&, Iterator it ){ return *this; }
+ template<class Val>
+ PropertyPrinter& operator () ( std::ostream&, const Val& ){ return *this; }
 };
 
 // property printer
@@ -287,18 +288,16 @@
                 // assign indices to vertices
                 std::map<Vertex,int> indices;
                 int num = 0;
- typename graph_traits<Graph>::vertex_iterator vi;
- for (vi = vertices(graph).first; vi != vertices(graph).second; ++vi){
- indices[*vi] = num++;
+ BGL_FORALL_VERTICES_T(v, graph, Graph) {
+ indices[v] = num++;
                 }
 
                 // write edges
                 PropertyPrinter<Graph, EdgeProperty> print_Edge(graph);
                 out << "e" << std::endl;
- typename graph_traits<Graph>::edge_iterator ei;
- for (ei = edges(graph).first; ei != edges(graph).second; ++ei){
- out << indices[source(*ei,graph)] << " " << indices[target(*ei,graph)] << " ";
- print_Edge(out,ei);
+ BGL_FORALL_EDGES_T(e, graph, Graph) {
+ out << indices[source(e,graph)] << " " << indices[target(e,graph)] << " ";
+ print_Edge(out,e);
                         out << std::endl;
                 }
                 out << std::endl;
@@ -322,9 +321,8 @@
         {
                 PropertyPrinter<Graph, V> printNode(this->graph);
                 out << "v"<<std::endl;
- typename graph_traits<Graph>::vertex_iterator vi;
- for (vi = vertices(this->graph).first; vi != vertices(this->graph).second; ++vi){
- printNode(out,vi);
+ BGL_FORALL_VERTICES_T(v, this->graph, Graph) {
+ printNode(out,v);
                         out << std::endl;
                 }
                 

Modified: branches/release/boost/graph/astar_search.hpp
==============================================================================
--- branches/release/boost/graph/astar_search.hpp (original)
+++ branches/release/boost/graph/astar_search.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -172,20 +172,10 @@
 
       template <class Edge, class Graph>
       void gray_target(Edge e, Graph& g) {
- distance_type old_distance = get(m_distance, target(e, g));
-
         m_decreased = relax(e, g, m_weight, m_predecessor, m_distance,
                             m_combine, m_compare);
 
- /* On x86 Linux with optimization, we sometimes get into a
- horrible case where m_decreased is true but the distance hasn't
- actually changed. This occurs when the comparison inside
- relax() occurs with the 80-bit precision of the x87 floating
- point unit, but the difference is lost when the resulting
- values are written back to lower-precision memory (e.g., a
- double). With the eager Dijkstra's implementation, this results
- in looping. */
- if(m_decreased && old_distance != get(m_distance, target(e, g))) {
+ if(m_decreased) {
           put(m_cost, target(e, g),
               m_combine(get(m_distance, target(e, g)),
                         m_h(target(e, g))));
@@ -198,13 +188,10 @@
 
       template <class Edge, class Graph>
       void black_target(Edge e, Graph& g) {
- distance_type old_distance = get(m_distance, target(e, g));
-
         m_decreased = relax(e, g, m_weight, m_predecessor, m_distance,
                             m_combine, m_compare);
 
- /* See comment in gray_target */
- if(m_decreased && old_distance != get(m_distance, target(e, g))) {
+ if(m_decreased) {
           m_vis.edge_relaxed(e, g);
           put(m_cost, target(e, g),
               m_combine(get(m_distance, target(e, g)),

Modified: branches/release/boost/graph/bc_clustering.hpp
==============================================================================
--- branches/release/boost/graph/bc_clustering.hpp (original)
+++ branches/release/boost/graph/bc_clustering.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -11,6 +11,7 @@
 
 #include <boost/graph/betweenness_centrality.hpp>
 #include <boost/graph/graph_traits.hpp>
+#include <boost/graph/graph_utility.hpp>
 #include <boost/pending/indirect_cmp.hpp>
 #include <algorithm>
 #include <vector>
@@ -116,7 +117,7 @@
   typedef typename graph_traits<MutableGraph>::vertices_size_type
     vertices_size_type;
 
- if (edges(g).first == edges(g).second) return;
+ if (has_no_edges(g)) return;
 
   // Function object that compares the centrality of edges
   indirect_cmp<EdgeCentralityMap, std::less<centrality_type> >
@@ -127,10 +128,11 @@
     brandes_betweenness_centrality(g,
                                    edge_centrality_map(edge_centrality)
                                    .vertex_index_map(vertex_index));
- edge_descriptor e = *max_element(edges(g).first, edges(g).second, cmp);
+ std::pair<edge_iterator, edge_iterator> edges_iters = edges(g);
+ edge_descriptor e = *max_element(edges_iters.first, edges_iters.second, cmp);
     is_done = done(get(edge_centrality, e), e, g);
     if (!is_done) remove_edge(e, g);
- } while (!is_done && edges(g).first != edges(g).second);
+ } while (!is_done && !has_no_edges(g));
 }
 
 /**

Modified: branches/release/boost/graph/compressed_sparse_row_graph.hpp
==============================================================================
--- branches/release/boost/graph/compressed_sparse_row_graph.hpp (original)
+++ branches/release/boost/graph/compressed_sparse_row_graph.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -19,9 +19,12 @@
 #include <climits>
 #include <cassert>
 #include <iterator>
-#include <iostream> // FIXME
+#if 0
+#include <iostream> // For some debugging code below
+#endif
 #include <boost/graph/graph_traits.hpp>
 #include <boost/graph/properties.hpp>
+#include <boost/graph/filtered_graph.hpp> // For keep_all
 #include <boost/graph/detail/indexed_properties.hpp>
 #include <boost/iterator/counting_iterator.hpp>
 #include <boost/property_map/property_map.hpp>
@@ -58,26 +61,35 @@
 // A type (edges_are_sorted_t) and a value (edges_are_sorted) used to indicate
 // that the edge list passed into the CSR graph is already sorted by source
 // vertex.
-struct edges_are_sorted_internal {};
-inline void edges_are_sorted(edges_are_sorted_internal) {}
-typedef void (*edges_are_sorted_t)(edges_are_sorted_internal);
+enum edges_are_sorted_t {edges_are_sorted};
 
 #ifdef BOOST_GRAPH_USE_NEW_CSR_INTERFACE
 // A type (edges_are_unsorted_t) and a value (edges_are_unsorted) used to
 // indicate that the edge list passed into the CSR graph is not sorted by
-// source vertex.
-struct edges_are_unsorted_internal {};
-inline void edges_are_unsorted(edges_are_unsorted_internal) {}
-typedef void (*edges_are_unsorted_t)(edges_are_unsorted_internal);
+// source vertex. This version caches the edge information in memory, and thus
+// requires only a single pass over the input data.
+enum edges_are_unsorted_t {edges_are_unsorted};
+
+// A type (edges_are_unsorted_multi_pass_t) and a value
+// (edges_are_unsorted_multi_pass) used to indicate that the edge list passed
+// into the CSR graph is not sorted by source vertex. This version uses less
+// memory but requires multi-pass capability on the iterators.
+enum edges_are_unsorted_multi_pass_t {edges_are_unsorted_multi_pass};
+
+// A type (edges_are_unsorted_multi_pass_filtered_t) and a value
+// (edges_are_unsorted_multi_pass_filtered) used to indicate that the edge list
+// passed into the CSR graph is not sorted by source vertex. This version uses
+// less memory but requires multi-pass capability on the iterators. The
+// filtering is done here because it is often faster and it greatly simplifies
+// handling of edge properties.
+enum edges_are_unsorted_multi_pass_filtered_t {edges_are_unsorted_multi_pass_filtered};
 
 // A type (construct_inplace_from_sources_and_targets_t) and a value
 // (construct_inplace_from_sources_and_targets) used to indicate that mutable
 // vectors of sources and targets (and possibly edge properties) are being used
 // to construct the CSR graph. These vectors are sorted in-place and then the
 // targets and properties are swapped into the graph data structure.
-struct construct_inplace_from_sources_and_targets_internal {};
-inline void construct_inplace_from_sources_and_targets(construct_inplace_from_sources_and_targets_internal) {}
-typedef void (*construct_inplace_from_sources_and_targets_t)(construct_inplace_from_sources_and_targets_internal);
+enum construct_inplace_from_sources_and_targets_t {construct_inplace_from_sources_and_targets};
 
 // A type (construct_inplace_from_sources_and_targets_global_t) and a value
 // (construct_inplace_from_sources_and_targets_global) used to indicate that
@@ -88,9 +100,16 @@
 // used, and a map is required to convert those to local indices. This
 // constructor is intended for internal use by the various CSR graphs
 // (sequential and distributed).
-struct construct_inplace_from_sources_and_targets_global_internal {};
-inline void construct_inplace_from_sources_and_targets_global(construct_inplace_from_sources_and_targets_global_internal) {}
-typedef void (*construct_inplace_from_sources_and_targets_global_t)(construct_inplace_from_sources_and_targets_global_internal);
+enum construct_inplace_from_sources_and_targets_global_t {construct_inplace_from_sources_and_targets_global};
+
+// A type (edges_are_unsorted_for_distributed_graph_t) and a value
+// (edges_are_unsorted_for_distributed_graph) used to indicate that the edge
+// list passed into the CSR graph is not sorted by source vertex. The data is
+// also stored using global vertex indices, and must be filtered to choose only
+// local vertices. This constructor caches the edge information in memory, and
+// thus requires only a single pass over the input data. This constructor is
+// intended for internal use by the distributed CSR constructors.
+enum edges_are_unsorted_for_distributed_graph_t {edges_are_unsorted_for_distributed_graph};
 
 #endif // BOOST_GRAPH_USE_NEW_CSR_INTERFACE
 
@@ -111,14 +130,33 @@
 
 #ifdef BOOST_GRAPH_USE_NEW_CSR_INTERFACE
 namespace detail {
- // Less-than operator for comparing only the first elements of two arbitrary
- // Boost tuples
- struct compare_first_elements_in_tuples {
- template <typename Tuple>
- bool operator()(const Tuple& a, const Tuple& b) const {
- return (a.template get<0>()) < (b.template get<0>());
- }
- };
+ template<typename InputIterator>
+ size_t
+ reserve_count_for_single_pass_helper(InputIterator, InputIterator,
+ std::input_iterator_tag)
+ {
+ // Do nothing: we have no idea how much storage to reserve.
+ return 0;
+ }
+
+ template<typename InputIterator>
+ size_t
+ reserve_count_for_single_pass_helper(InputIterator first, InputIterator last,
+ std::random_access_iterator_tag)
+ {
+ using std::distance;
+ typename std::iterator_traits<InputIterator>::difference_type n =
+ distance(first, last);
+ return (size_t)n;
+ }
+
+ template<typename InputIterator>
+ size_t
+ reserve_count_for_single_pass(InputIterator first, InputIterator last) {
+ typedef typename std::iterator_traits<InputIterator>::iterator_category
+ category;
+ return reserve_count_for_single_pass_helper(first, last, category());
+ }
 }
 #endif // BOOST_GRAPH_USE_NEW_CSR_INTERFACE
 
@@ -241,19 +279,20 @@
   }
 
 #ifdef BOOST_GRAPH_USE_NEW_CSR_INTERFACE
- // From number of vertices and unsorted list of edges
- template <typename MultiPassInputIterator>
- compressed_sparse_row_graph(edges_are_unsorted_t,
- MultiPassInputIterator edge_begin,
- MultiPassInputIterator edge_end,
- vertices_size_type numverts,
- const GraphProperty& prop = GraphProperty())
- : inherited_vertex_properties(numverts), m_rowstart(numverts + 1),
- m_column(0), m_property(prop)
- {
+ // Rebuild graph from number of vertices and multi-pass unsorted list of
+ // edges (filtered using edge_pred)
+ template <typename MultiPassInputIterator, typename EdgePred>
+ void
+ assign_unsorted_multi_pass_edges(MultiPassInputIterator edge_begin,
+ MultiPassInputIterator edge_end,
+ vertices_size_type numverts,
+ const EdgePred& edge_pred) {
+ m_rowstart.clear();
+ m_rowstart.resize(numverts + 1, 0);
     // Put the degree of each vertex v into m_rowstart[v + 1]
     for (MultiPassInputIterator i = edge_begin; i != edge_end; ++i)
- ++m_rowstart[i->first + 1];
+ if (edge_pred(*i))
+ ++m_rowstart[i->first + 1];
 
     // Compute the partial sum of the degrees to get the actual values of
     // m_rowstart
@@ -271,26 +310,25 @@
     std::vector<EdgeIndex>
       current_insert_positions(m_rowstart.begin(), m_rowstart.begin() + numverts);
     for (; edge_begin != edge_end; ++edge_begin)
- m_column[current_insert_positions[edge_begin->first]++] = edge_begin->second;
-
- // Default-construct properties for edges
- inherited_edge_properties::resize(m_column.size());
+ if (edge_pred(*edge_begin))
+ m_column[current_insert_positions[edge_begin->first]++] = edge_begin->second;
   }
 
- // From number of vertices and unsorted list of edges, plus edge properties
- template <typename MultiPassInputIterator, typename EdgePropertyIterator>
- compressed_sparse_row_graph(edges_are_unsorted_t,
- MultiPassInputIterator edge_begin,
- MultiPassInputIterator edge_end,
- EdgePropertyIterator ep_iter,
- vertices_size_type numverts,
- const GraphProperty& prop = GraphProperty())
- : inherited_vertex_properties(numverts), m_rowstart(numverts + 1),
- m_column(0), m_property(prop)
- {
+ // Rebuild graph from number of vertices and multi-pass unsorted list of
+ // edges and their properties (filtered using edge_pred)
+ template <typename MultiPassInputIterator, typename EdgePropertyIterator, typename EdgePred>
+ void
+ assign_unsorted_multi_pass_edges(MultiPassInputIterator edge_begin,
+ MultiPassInputIterator edge_end,
+ EdgePropertyIterator ep_iter,
+ vertices_size_type numverts,
+ const EdgePred& edge_pred) {
+ m_rowstart.clear();
+ m_rowstart.resize(numverts + 1, 0);
     // Put the degree of each vertex v into m_rowstart[v + 1]
     for (MultiPassInputIterator i = edge_begin; i != edge_end; ++i)
- ++m_rowstart[i->first + 1];
+ if (edge_pred(*i))
+ ++m_rowstart[i->first + 1];
 
     // Compute the partial sum of the degrees to get the actual values of
     // m_rowstart
@@ -309,13 +347,77 @@
     std::vector<EdgeIndex>
       current_insert_positions(m_rowstart.begin(), m_rowstart.begin() + numverts);
     for (; edge_begin != edge_end; ++edge_begin, ++ep_iter) {
- vertices_size_type source = edge_begin->first;
- EdgeIndex insert_pos = current_insert_positions[source];
- ++current_insert_positions[source];
- m_column[insert_pos] = edge_begin->second;
- inherited_edge_properties::write_by_index(insert_pos, *ep_iter);
+ if (edge_pred(*edge_begin)) {
+ vertices_size_type source = edge_begin->first;
+ EdgeIndex insert_pos = current_insert_positions[source];
+ ++current_insert_positions[source];
+ m_column[insert_pos] = edge_begin->second;
+ inherited_edge_properties::write_by_index(insert_pos, *ep_iter);
+ }
     }
   }
+
+ // From number of vertices and unsorted list of edges
+ template <typename MultiPassInputIterator>
+ compressed_sparse_row_graph(edges_are_unsorted_multi_pass_t,
+ MultiPassInputIterator edge_begin,
+ MultiPassInputIterator edge_end,
+ vertices_size_type numverts,
+ const GraphProperty& prop = GraphProperty())
+ : inherited_vertex_properties(numverts), m_rowstart(),
+ m_column(0), m_property(prop)
+ {
+ assign_unsorted_multi_pass_edges(edge_begin, edge_end, numverts, keep_all());
+
+ // Default-construct properties for edges
+ inherited_edge_properties::resize(m_column.size());
+ }
+
+ // From number of vertices and unsorted list of edges, plus edge properties
+ template <typename MultiPassInputIterator, typename EdgePropertyIterator>
+ compressed_sparse_row_graph(edges_are_unsorted_multi_pass_t,
+ MultiPassInputIterator edge_begin,
+ MultiPassInputIterator edge_end,
+ EdgePropertyIterator ep_iter,
+ vertices_size_type numverts,
+ const GraphProperty& prop = GraphProperty())
+ : inherited_vertex_properties(numverts), m_rowstart(),
+ m_column(0), m_property(prop)
+ {
+ assign_unsorted_multi_pass_edges(edge_begin, edge_end, ep_iter, numverts, keep_all());
+ }
+
+ // From number of vertices and unsorted list of edges, with filter
+ template <typename MultiPassInputIterator, typename EdgePred>
+ compressed_sparse_row_graph(edges_are_unsorted_multi_pass_filtered_t,
+ MultiPassInputIterator edge_begin,
+ MultiPassInputIterator edge_end,
+ vertices_size_type numverts,
+ const EdgePred& edge_pred,
+ const GraphProperty& prop = GraphProperty())
+ : inherited_vertex_properties(numverts), m_rowstart(),
+ m_column(0), m_property(prop)
+ {
+ assign_unsorted_multi_pass_edges(edge_begin, edge_end, numverts, edge_pred);
+
+ // Default-construct properties for edges
+ inherited_edge_properties::resize(m_column.size());
+ }
+
+ // From number of vertices and unsorted list of edges, plus edge properties, with filter
+ template <typename MultiPassInputIterator, typename EdgePropertyIterator, typename EdgePred>
+ compressed_sparse_row_graph(edges_are_unsorted_multi_pass_filtered_t,
+ MultiPassInputIterator edge_begin,
+ MultiPassInputIterator edge_end,
+ EdgePropertyIterator ep_iter,
+ vertices_size_type numverts,
+ const EdgePred& edge_pred,
+ const GraphProperty& prop = GraphProperty())
+ : inherited_vertex_properties(numverts), m_rowstart(),
+ m_column(0), m_property(prop)
+ {
+ assign_unsorted_multi_pass_edges(edge_begin, edge_end, ep_iter, numverts, edge_pred);
+ }
 #endif // BOOST_GRAPH_USE_NEW_CSR_INTERFACE
 
 #ifdef BOOST_GRAPH_USE_OLD_CSR_INTERFACE
@@ -557,6 +659,106 @@
     assign_sources_and_targets_global(sources, targets, edge_props, numlocalverts, global_to_local);
   }
 
+ // From number of vertices and single-pass range of unsorted edges. Data is
+ // cached in coordinate form before creating the actual graph.
+ template<typename InputIterator>
+ compressed_sparse_row_graph(edges_are_unsorted_t,
+ InputIterator edge_begin, InputIterator edge_end,
+ vertices_size_type numverts,
+ const GraphProperty& prop = GraphProperty())
+ : inherited_vertex_properties(numverts), m_rowstart(),
+ m_column(), m_property(prop)
+ {
+ std::vector<vertex_descriptor> sources, targets;
+ size_t reserve_size
+ = detail::reserve_count_for_single_pass(edge_begin, edge_end);
+ sources.reserve(reserve_size);
+ targets.reserve(reserve_size);
+ for (; edge_begin != edge_end; ++edge_begin) {
+ sources.push_back(edge_begin->first);
+ targets.push_back(edge_begin->second);
+ }
+ assign_sources_and_targets_global(sources, targets, numverts, boost::identity_property_map());
+ }
+
+ // From number of vertices and single-pass range of unsorted edges and
+ // single-pass range of edge properties. Data is cached in coordinate form
+ // before creating the actual graph.
+ template<typename InputIterator, typename EdgePropertyIterator>
+ compressed_sparse_row_graph(edges_are_unsorted_t,
+ InputIterator edge_begin, InputIterator edge_end,
+ EdgePropertyIterator ep_iter,
+ vertices_size_type numverts,
+ const GraphProperty& prop = GraphProperty())
+ : inherited_vertex_properties(numverts), m_rowstart(),
+ m_column(), m_property(prop)
+ {
+ std::vector<vertex_descriptor> sources, targets;
+ std::vector<typename inherited_edge_properties::edge_property_type> edge_props;
+ size_t reserve_size
+ = detail::reserve_count_for_single_pass(edge_begin, edge_end);
+ sources.reserve(reserve_size);
+ targets.reserve(reserve_size);
+ edge_props.reserve(reserve_size);
+ for (; edge_begin != edge_end; ++edge_begin, ++ep_iter) {
+ sources.push_back(edge_begin->first);
+ targets.push_back(edge_begin->second);
+ edge_props.push_back(*ep_iter);
+ }
+ assign_sources_and_targets_global(sources, targets, edge_props, numverts, boost::identity_property_map());
+ }
+
+ // From number of vertices and single-pass range of unsorted edges. Data is
+ // cached in coordinate form before creating the actual graph. Edges are
+ // filtered and transformed for use in a distributed graph.
+ template<typename InputIterator, typename GlobalToLocal, typename EdgePred>
+ compressed_sparse_row_graph(edges_are_unsorted_for_distributed_graph_t,
+ InputIterator edge_begin, InputIterator edge_end,
+ vertices_size_type numlocalverts,
+ GlobalToLocal global_to_local,
+ const EdgePred& edge_pred,
+ const GraphProperty& prop = GraphProperty())
+ : inherited_vertex_properties(numlocalverts), m_rowstart(),
+ m_column(), m_property(prop)
+ {
+ std::vector<vertex_descriptor> sources, targets;
+ for (; edge_begin != edge_end; ++edge_begin) {
+ if (edge_pred(*edge_begin)) {
+ sources.push_back(edge_begin->first);
+ targets.push_back(edge_begin->second);
+ }
+ }
+ assign_sources_and_targets_global(sources, targets, numlocalverts, global_to_local);
+ }
+
+ // From number of vertices and single-pass range of unsorted edges and
+ // single-pass range of edge properties. Data is cached in coordinate form
+ // before creating the actual graph. Edges are filtered and transformed for
+ // use in a distributed graph.
+ template<typename InputIterator, typename EdgePropertyIterator,
+ typename GlobalToLocal, typename EdgePred>
+ compressed_sparse_row_graph(edges_are_unsorted_for_distributed_graph_t,
+ InputIterator edge_begin, InputIterator edge_end,
+ EdgePropertyIterator ep_iter,
+ vertices_size_type numlocalverts,
+ GlobalToLocal global_to_local,
+ const EdgePred& edge_pred,
+ const GraphProperty& prop = GraphProperty())
+ : inherited_vertex_properties(numlocalverts), m_rowstart(),
+ m_column(), m_property(prop)
+ {
+ std::vector<vertex_descriptor> sources, targets;
+ std::vector<typename inherited_edge_properties::edge_property_type> edge_props;
+ for (; edge_begin != edge_end; ++edge_begin, ++ep_iter) {
+ if (edge_pred(*edge_begin)) {
+ sources.push_back(edge_begin->first);
+ targets.push_back(edge_begin->second);
+ edge_props.push_back(*ep_iter);
+ }
+ }
+ assign_sources_and_targets_global(sources, targets, edge_props, numlocalverts, global_to_local);
+ }
+
   // Replace graph with sources and targets given, sorting them in-place, and
   // using the given global-to-local property map to get local indices from
   // global ones in the two arrays.
@@ -841,6 +1043,65 @@
 }
 #endif // BOOST_GRAPH_USE_OLD_CSR_INTERFACE
 
+#ifdef BOOST_GRAPH_USE_NEW_CSR_INTERFACE
+// Add edges from a range of (source, target) pairs that are unsorted
+template <BOOST_CSR_GRAPH_TEMPLATE_PARMS, typename InputIterator>
+inline void
+add_edges(InputIterator first, InputIterator last, BOOST_CSR_GRAPH_TYPE& g) {
+ typedef BOOST_CSR_GRAPH_TYPE Graph;
+ typedef typename boost::graph_traits<Graph>::vertex_descriptor vertex_t;
+ typedef typename boost::graph_traits<Graph>::vertices_size_type vertex_num;
+ typedef typename boost::graph_traits<Graph>::edges_size_type edge_num;
+ typedef std::vector<std::pair<vertex_t, vertex_t> > edge_vector_t;
+ edge_vector_t new_edges(first, last);
+ if (new_edges.empty()) return;
+ std::sort(new_edges.begin(), new_edges.end());
+ edge_num edges_added_before_i = new_edges.size(); // Count increment to add to rowstarts
+ g.m_column.resize(g.m_column.size() + new_edges.size());
+ typename edge_vector_t::const_reverse_iterator
+ current_new_edge = new_edges.rbegin(),
+ prev_new_edge = new_edges.rbegin();
+ for (vertex_num i_plus_1 = num_vertices(g); i_plus_1 > 0; --i_plus_1) {
+ vertex_num i = i_plus_1 - 1;
+ prev_new_edge = current_new_edge;
+ // edges_added_to_this_vertex = #mbrs of new_edges with first == i
+ edge_num edges_added_to_this_vertex = 0;
+ while (current_new_edge !=
+ (typename edge_vector_t::const_reverse_iterator)new_edges.rend()) {
+ if (current_new_edge->first != i) break;
+ ++current_new_edge;
+ ++edges_added_to_this_vertex;
+ }
+ edges_added_before_i -= edges_added_to_this_vertex;
+ // Invariant: edges_added_before_i = #mbrs of new_edges with first < i
+ edge_num old_rowstart = g.m_rowstart[i];
+ edge_num new_rowstart = g.m_rowstart[i] + edges_added_before_i;
+ edge_num old_degree = g.m_rowstart[i + 1] - g.m_rowstart[i];
+ edge_num new_degree = old_degree + edges_added_to_this_vertex;
+ // Move old edges forward (by #new_edges before this i) to make room
+ // new_rowstart > old_rowstart, so use copy_backwards
+ if (old_rowstart != new_rowstart) {
+ std::copy_backward(g.m_column.begin() + old_rowstart,
+ g.m_column.begin() + old_rowstart + old_degree,
+ g.m_column.begin() + new_rowstart + old_degree);
+ }
+ // Add new edges (reversed because current_new_edge is a
+ // const_reverse_iterator)
+ typename edge_vector_t::const_reverse_iterator temp = current_new_edge;
+ for (; temp != prev_new_edge; ++old_degree) {
+ --temp;
+ g.m_column[new_rowstart + old_degree] = temp->second;
+ }
+ g.m_rowstart[i + 1] = new_rowstart + new_degree;
+ if (edges_added_before_i == 0) break; // No more edges inserted before this point
+ // g.m_rowstart[i] will be fixed up on the next iteration (to avoid
+ // changing the degree of vertex i - 1); the last iteration never changes
+ // it (either because of the condition of the break or because
+ // g.m_rowstart[0] is always 0)
+ }
+}
+#endif // BOOST_GRAPH_USE_NEW_CSR_INTERFACE
+
 // From VertexListGraph
 template<BOOST_CSR_GRAPH_TEMPLATE_PARMS>
 inline Vertex

Modified: branches/release/boost/graph/cuthill_mckee_ordering.hpp
==============================================================================
--- branches/release/boost/graph/cuthill_mckee_ordering.hpp (original)
+++ branches/release/boost/graph/cuthill_mckee_ordering.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -13,6 +13,7 @@
 
 #include <boost/config.hpp>
 #include <boost/graph/detail/sparse_ordering.hpp>
+#include <boost/graph/graph_utility.hpp>
 #include <algorithm>
 
 
@@ -132,7 +133,7 @@
   cuthill_mckee_ordering(const Graph& G, OutputIterator permutation,
                          ColorMap color, DegreeMap degree)
   {
- if (vertices(G).first == vertices(G).second)
+ if (has_no_vertices(G))
       return permutation;
 
     typedef typename boost::graph_traits<Graph>::vertex_descriptor Vertex;
@@ -168,7 +169,7 @@
   cuthill_mckee_ordering(const Graph& G, OutputIterator permutation,
                          VertexIndexMap index_map)
   {
- if (vertices(G).first == vertices(G).second)
+ if (has_no_vertices(G))
       return permutation;
     
     typedef out_degree_property_map<Graph> DegreeMap;

Modified: branches/release/boost/graph/depth_first_search.hpp
==============================================================================
--- branches/release/boost/graph/depth_first_search.hpp (original)
+++ branches/release/boost/graph/depth_first_search.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -214,10 +214,12 @@
   void
   depth_first_search(const VertexListGraph& g, DFSVisitor vis, ColorMap color)
   {
- if (vertices(g).first == vertices(g).second)
+ typedef typename boost::graph_traits<VertexListGraph>::vertex_iterator vi;
+ std::pair<vi, vi> verts = vertices(g);
+ if (verts.first == verts.second)
       return;
 
- depth_first_search(g, vis, color, *vertices(g).first);
+ depth_first_search(g, vis, color, *verts.first);
   }
 
   template <class Visitors = null_visitor>
@@ -284,7 +286,9 @@
   depth_first_search(const VertexListGraph& g,
                      const bgl_named_params<P, T, R>& params)
   {
- if (vertices(g).first == vertices(g).second)
+ typedef typename boost::graph_traits<VertexListGraph>::vertex_iterator vi;
+ std::pair<vi, vi> verts = vertices(g);
+ if (verts.first == verts.second)
       return;
     using namespace boost::graph::keywords;
     typedef bgl_named_params<P, T, R> params_type;

Modified: branches/release/boost/graph/distributed/adjacency_list.hpp
==============================================================================
--- branches/release/boost/graph/distributed/adjacency_list.hpp (original)
+++ branches/release/boost/graph/distributed/adjacency_list.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -1417,7 +1417,7 @@
       in_edge_iterator;
 
     /// Iterator over the neighbors of a vertex
- typedef adjacency_iterator<
+ typedef boost::adjacency_iterator<
               adjacency_list, vertex_descriptor, out_edge_iterator,
               typename detail::iterator_traits<base_out_edge_iterator>
                          ::difference_type>

Modified: branches/release/boost/graph/distributed/betweenness_centrality.hpp
==============================================================================
--- branches/release/boost/graph/distributed/betweenness_centrality.hpp (original)
+++ branches/release/boost/graph/distributed/betweenness_centrality.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -295,8 +295,8 @@
 #endif
                                              Dist delta)
     : g(g),
- distance(distance),
       incoming(incoming),
+ distance(distance),
       weight(weight),
       path_count(path_count),
 #ifdef COMPUTE_PATH_COUNTS_INLINE
@@ -1047,7 +1047,7 @@
       vertices_size_type n = num_vertices(g);
       n = boost::parallel::all_reduce(pg, n, std::plus<vertices_size_type>());
       
- for (int i = 0; i < n; ++i) {
+ for (vertices_size_type i = 0; i < n; ++i) {
         vertex_descriptor v = vertex(i, g);
 
         do_brandes_sssp(g, centrality, edge_centrality_map, incoming, distance,
@@ -1189,7 +1189,7 @@
       }
 
       // DO SSSPs
- for(int i = 0; i < local_sources.size(); ++i)
+ for(size_t i = 0; i < local_sources.size(); ++i)
         do_sequential_brandes_sssp(g, centrality, edge_centrality_map, incoming,
                                    distance, dependency, path_count, vertex_index,
                                    shortest_paths, ordered_vertices, local_sources[i]);
@@ -1198,7 +1198,7 @@
       typedef typename graph_traits<Graph>::vertices_size_type vertices_size_type;
       vertices_size_type n = num_vertices(g);
       
- for (int i = id; i < n; i += p) {
+ for (vertices_size_type i = id; i < n; i += p) {
         vertex_descriptor v = vertex(i, g);
 
         do_sequential_brandes_sssp(g, centrality, edge_centrality_map, incoming,

Modified: branches/release/boost/graph/distributed/connected_components.hpp
==============================================================================
--- branches/release/boost/graph/distributed/connected_components.hpp (original)
+++ branches/release/boost/graph/distributed/connected_components.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -409,7 +409,6 @@
 #ifdef PBGL_EXPLICIT_SYNCH
       synchronize(p);
 #endif
- size_t lone_vertex_count = roots.size();
 
       // Lastly, remove roots with no adjacent vertices, this is
       // unnecessary but will speed up sparse graphs

Modified: branches/release/boost/graph/distributed/eager_dijkstra_shortest_paths.hpp
==============================================================================
--- branches/release/boost/graph/distributed/eager_dijkstra_shortest_paths.hpp (original)
+++ branches/release/boost/graph/distributed/eager_dijkstra_shortest_paths.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -113,20 +113,10 @@
     boost::parallel::caching_property_map<PredecessorMap> c_pred(m_predecessor);
     boost::parallel::caching_property_map<DistanceMap> c_dist(m_distance);
 
- distance_type old_distance = get(c_dist, target(e, g));
-
     bool m_decreased = relax(e, g, m_weight, c_pred, c_dist,
                              m_combine, m_compare);
 
- /* On x86 Linux with optimization, we sometimes get into a
- horrible case where m_decreased is true but the distance hasn't
- actually changed. This occurs when the comparison inside
- relax() occurs with the 80-bit precision of the x87 floating
- point unit, but the difference is lost when the resulting
- values are written back to lower-precision memory (e.g., a
- double). With the eager Dijkstra's implementation, this results
- in looping. */
- if (m_decreased && old_distance != get(c_dist, target(e, g))) {
+ if (m_decreased) {
       m_Q.update(target(e, g));
       m_vis.edge_relaxed(e, g);
     } else

Modified: branches/release/boost/graph/edge_connectivity.hpp
==============================================================================
--- branches/release/boost/graph/edge_connectivity.hpp (original)
+++ branches/release/boost/graph/edge_connectivity.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -132,7 +132,8 @@
     detail::neighbors(g, S.begin(), S.end(),
                       std::inserter(neighbor_S, neighbor_S.begin()));
 
- std::set_difference(vertices(g).first, vertices(g).second,
+ tie(vi, vi_end) = vertices(g);
+ std::set_difference(vi, vi_end,
                         neighbor_S.begin(), neighbor_S.end(),
                         std::back_inserter(non_neighbor_S));
 
@@ -153,7 +154,8 @@
       neighbor_S.insert(k);
       detail::neighbors(g, k, std::inserter(neighbor_S, neighbor_S.begin()));
       non_neighbor_S.clear();
- std::set_difference(vertices(g).first, vertices(g).second,
+ tie(vi, vi_end) = vertices(g);
+ std::set_difference(vi, vi_end,
                           neighbor_S.begin(), neighbor_S.end(),
                           std::back_inserter(non_neighbor_S));
     }

Modified: branches/release/boost/graph/graph_utility.hpp
==============================================================================
--- branches/release/boost/graph/graph_utility.hpp (original)
+++ branches/release/boost/graph/graph_utility.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -445,6 +445,27 @@
       add_removed_edge_capacity(Graph& g) : base(get(edge_capacity, g)) {}
     };
 
+ template <typename Graph>
+ bool has_no_vertices(const Graph& g) {
+ typedef typename boost::graph_traits<Graph>::vertex_iterator vi;
+ std::pair<vi, vi> p = vertices(g);
+ return (p.first == p.second);
+ }
+
+ template <typename Graph>
+ bool has_no_edges(const Graph& g) {
+ typedef typename boost::graph_traits<Graph>::edge_iterator ei;
+ std::pair<ei, ei> p = edges(g);
+ return (p.first == p.second);
+ }
+
+ template <typename Graph>
+ bool has_no_out_edges(const typename boost::graph_traits<Graph>::vertex_descriptor& v, const Graph& g) {
+ typedef typename boost::graph_traits<Graph>::out_edge_iterator ei;
+ std::pair<ei, ei> p = out_edges(v, g);
+ return (p.first == p.second);
+ }
+
   } // namespace graph
 
 } /* namespace boost */

Modified: branches/release/boost/graph/howard_cycle_ratio.hpp
==============================================================================
--- branches/release/boost/graph/howard_cycle_ratio.hpp (original)
+++ branches/release/boost/graph/howard_cycle_ratio.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -29,6 +29,7 @@
 #include <boost/graph/reverse_graph.hpp>
 #include <boost/graph/breadth_first_search.hpp>
 #include <boost/graph/iteration_macros.hpp>
+#include <boost/graph/graph_utility.hpp>
 
 namespace boost {
   namespace detail {
@@ -172,7 +173,7 @@
           }
         BGL_FORALL_VERTICES_T(vd1, m_g, TGraph)
           {
- if (boost::out_edges(vd1, m_g).first == boost::out_edges(vd1, m_g).second) throw bad_graph(m_vim[vd1]);
+ if (boost::graph::has_no_out_edges(vd1, m_g)) throw bad_graph(m_vim[vd1]);
             mcr_edge_t ed = *boost::out_edges(vd1, m_g).first;
             pi_edge_t pied = boost::add_edge(m_g2pi_g_vm[source(ed, m_g)], m_g2pi_g_vm[target(ed, m_g)], m_pi_g).first;
             boost::put(boost::edge_weight, m_pi_g, pied, m_ew1m[ed]);

Modified: branches/release/boost/graph/isomorphism.hpp
==============================================================================
--- branches/release/boost/graph/isomorphism.hpp (original)
+++ branches/release/boost/graph/isomorphism.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -439,13 +439,11 @@
       return false;
 #endif
   
- for (typename graph_traits<Graph1>::edge_iterator e1 = edges(g1).first;
- e1 != edges(g1).second; ++e1) {
+ BGL_FORALL_EDGES_T(e1, g1, Graph1) {
       bool found_edge = false;
- for (typename graph_traits<Graph2>::edge_iterator e2 = edges(g2).first;
- e2 != edges(g2).second && !found_edge; ++e2) {
- if (source(*e2, g2) == get(iso_map, source(*e1, g1)) &&
- target(*e2, g2) == get(iso_map, target(*e1, g1))) {
+ BGL_FORALL_EDGES_T(e2, g2, Graph2) {
+ if (source(e2, g2) == get(iso_map, source(e1, g1)) &&
+ target(e2, g2) == get(iso_map, target(e1, g1))) {
           found_edge = true;
         }
       }

Modified: branches/release/boost/graph/iteration_macros.hpp
==============================================================================
--- branches/release/boost/graph/iteration_macros.hpp (original)
+++ branches/release/boost/graph/iteration_macros.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -10,9 +10,12 @@
 #ifndef BOOST_GRAPH_ITERATION_MACROS_HPP
 #define BOOST_GRAPH_ITERATION_MACROS_HPP
 
+#include <utility>
+
 #define BGL_CAT(x,y) x ## y
-#define BGL_FIRST(linenum) BGL_CAT(bgl_first_,linenum)
-#define BGL_LAST(linenum) BGL_CAT(bgl_last_,linenum)
+#define BGL_RANGE(linenum) BGL_CAT(bgl_range_,linenum)
+#define BGL_FIRST(linenum) (BGL_RANGE(linenum).first)
+#define BGL_LAST(linenum) (BGL_RANGE(linenum).second)
 
 /*
   BGL_FORALL_VERTICES_T(v, g, graph_t) // This is on line 9
@@ -22,7 +25,7 @@
            bgl_first_9 = vertices(g).first, bgl_last_9 = vertices(g).second;
        bgl_first_9 != bgl_last_9; bgl_first_9 = bgl_last_9)
     for (typename boost::graph_traits<graph_t>::vertex_descriptor v;
- bgl_first_9 != bgl_last ? (v = *bgl_first_9, true) : false;
+ bgl_first_9 != bgl_last_9 ? (v = *bgl_first_9, true) : false;
          ++bgl_first_9)
 
   The purpose of having two for-loops is just to provide a place to
@@ -37,90 +40,98 @@
   Use the _T versions when the graph type is a template parameter or
   dependent on a template parameter. Otherwise use the non _T versions.
   
+ -----------------------
+ 6/9/09 THK
+
+ The above contains two calls to the vertices function. I modified these
+ macros to expand to
+
+ for (std::pair<typename boost::graph_traits<graph_t>::vertex_iterator,
+ typename boost::graph_traits<graph_t>::vertex_iterator> bgl_range_9 = vertices(g);
+ bgl_range_9.first != bgl_range_9.second;
+ bgl_range_9.first = bgl_range_9.second)
+ for (typename boost::graph_traits<graph_t>::vertex_descriptor v;
+ bgl_range_9.first != bgl_range_9.second ? (v = *bgl_range_9.first, true) : false;
+ ++bgl_range_9.first)
+
  */
 
 
 #define BGL_FORALL_VERTICES_T(VNAME, GNAME, GraphType) \
-for (typename boost::graph_traits<GraphType>::vertex_iterator \
- BGL_FIRST(__LINE__) = vertices(GNAME).first, BGL_LAST(__LINE__) = vertices(GNAME).second; \
+for (std::pair<typename boost::graph_traits<GraphType>::vertex_iterator, \
+ typename boost::graph_traits<GraphType>::vertex_iterator> BGL_RANGE(__LINE__) = vertices(GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
   for (typename boost::graph_traits<GraphType>::vertex_descriptor VNAME; \
     BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (VNAME = *BGL_FIRST(__LINE__), true):false; \
      ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_VERTICES(VNAME, GNAME, GraphType) \
-for (boost::graph_traits<GraphType>::vertex_iterator \
- BGL_FIRST(__LINE__) = vertices(GNAME).first, BGL_LAST(__LINE__) = vertices(GNAME).second; \
+for (std::pair<boost::graph_traits<GraphType>::vertex_iterator, \
+ boost::graph_traits<GraphType>::vertex_iterator> BGL_RANGE(__LINE__) = vertices(GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
   for (boost::graph_traits<GraphType>::vertex_descriptor VNAME; \
     BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (VNAME = *BGL_FIRST(__LINE__), true):false; \
      ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_EDGES_T(ENAME, GNAME, GraphType) \
-for (typename boost::graph_traits<GraphType>::edge_iterator \
- BGL_FIRST(__LINE__) = edges(GNAME).first, BGL_LAST(__LINE__) = edges(GNAME).second; \
+for (std::pair<typename boost::graph_traits<GraphType>::edge_iterator, \
+ typename boost::graph_traits<GraphType>::edge_iterator> BGL_RANGE(__LINE__) = edges(GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
   for (typename boost::graph_traits<GraphType>::edge_descriptor ENAME; \
     BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (ENAME = *BGL_FIRST(__LINE__), true):false; \
      ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_EDGES(ENAME, GNAME, GraphType) \
-for (boost::graph_traits<GraphType>::edge_iterator \
- BGL_FIRST(__LINE__) = edges(GNAME).first, BGL_LAST(__LINE__) = edges(GNAME).second; \
+for (std::pair<boost::graph_traits<GraphType>::edge_iterator, \
+ boost::graph_traits<GraphType>::edge_iterator> BGL_RANGE(__LINE__) = edges(GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
   for (boost::graph_traits<GraphType>::edge_descriptor ENAME; \
      BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (ENAME = *BGL_FIRST(__LINE__), true):false; \
      ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_ADJ_T(UNAME, VNAME, GNAME, GraphType) \
-for (typename boost::graph_traits<GraphType>::adjacency_iterator \
- BGL_FIRST(__LINE__) = adjacent_vertices(UNAME, GNAME).first,\
- BGL_LAST(__LINE__) = adjacent_vertices(UNAME, GNAME).second; \
+for (std::pair<typename boost::graph_traits<GraphType>::adjacency_iterator, \
+ typename boost::graph_traits<GraphType>::adjacency_iterator> BGL_RANGE(__LINE__) = adjacent_vertices(UNAME, GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
 for (typename boost::graph_traits<GraphType>::vertex_descriptor VNAME; \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (VNAME = *BGL_FIRST(__LINE__), true) : false; \
    ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_ADJ(UNAME, VNAME, GNAME, GraphType) \
-for (boost::graph_traits<GraphType>::adjacency_iterator \
- BGL_FIRST(__LINE__) = adjacent_vertices(UNAME, GNAME).first,\
- BGL_LAST(__LINE__) = adjacent_vertices(UNAME, GNAME).second; \
+for (std::pair<boost::graph_traits<GraphType>::adjacency_iterator, \
+ boost::graph_traits<GraphType>::adjacency_iterator> BGL_RANGE(__LINE__) = adjacent_vertices(UNAME, GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
 for (boost::graph_traits<GraphType>::vertex_descriptor VNAME; \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (VNAME = *BGL_FIRST(__LINE__), true) : false; \
    ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_OUTEDGES_T(UNAME, ENAME, GNAME, GraphType) \
-for (typename boost::graph_traits<GraphType>::out_edge_iterator \
- BGL_FIRST(__LINE__) = out_edges(UNAME, GNAME).first,\
- BGL_LAST(__LINE__) = out_edges(UNAME, GNAME).second; \
+for (std::pair<typename boost::graph_traits<GraphType>::out_edge_iterator, \
+ typename boost::graph_traits<GraphType>::out_edge_iterator> BGL_RANGE(__LINE__) = out_edges(UNAME, GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
 for (typename boost::graph_traits<GraphType>::edge_descriptor ENAME; \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (ENAME = *BGL_FIRST(__LINE__), true) : false; \
    ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_OUTEDGES(UNAME, ENAME, GNAME, GraphType) \
-for (boost::graph_traits<GraphType>::out_edge_iterator \
- BGL_FIRST(__LINE__) = out_edges(UNAME, GNAME).first,\
- BGL_LAST(__LINE__) = out_edges(UNAME, GNAME).second; \
+for (std::pair<boost::graph_traits<GraphType>::out_edge_iterator, \
+ boost::graph_traits<GraphType>::out_edge_iterator> BGL_RANGE(__LINE__) = out_edges(UNAME, GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
 for (boost::graph_traits<GraphType>::edge_descriptor ENAME; \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (ENAME = *BGL_FIRST(__LINE__), true) : false; \
    ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_INEDGES_T(UNAME, ENAME, GNAME, GraphType) \
-for (typename boost::graph_traits<GraphType>::in_edge_iterator \
- BGL_FIRST(__LINE__) = in_edges(UNAME, GNAME).first,\
- BGL_LAST(__LINE__) = in_edges(UNAME, GNAME).second; \
+for (std::pair<typename boost::graph_traits<GraphType>::in_edge_iterator, \
+ typename boost::graph_traits<GraphType>::in_edge_iterator> BGL_RANGE(__LINE__) = in_edges(UNAME, GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
 for (typename boost::graph_traits<GraphType>::edge_descriptor ENAME; \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (ENAME = *BGL_FIRST(__LINE__), true) : false; \
    ++BGL_FIRST(__LINE__))
 
 #define BGL_FORALL_INEDGES(UNAME, ENAME, GNAME, GraphType) \
-for (boost::graph_traits<GraphType>::in_edge_iterator \
- BGL_FIRST(__LINE__) = in_edges(UNAME, GNAME).first,\
- BGL_LAST(__LINE__) = in_edges(UNAME, GNAME).second; \
+for (std::pair<boost::graph_traits<GraphType>::in_edge_iterator, \
+ boost::graph_traits<GraphType>::in_edge_iterator> BGL_RANGE(__LINE__) = in_edges(UNAME, GNAME); \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__); BGL_FIRST(__LINE__) = BGL_LAST(__LINE__)) \
 for (boost::graph_traits<GraphType>::edge_descriptor ENAME; \
   BGL_FIRST(__LINE__) != BGL_LAST(__LINE__) ? (ENAME = *BGL_FIRST(__LINE__), true) : false; \

Modified: branches/release/boost/graph/king_ordering.hpp
==============================================================================
--- branches/release/boost/graph/king_ordering.hpp (original)
+++ branches/release/boost/graph/king_ordering.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -13,6 +13,7 @@
 
 #include <boost/config.hpp>
 #include <boost/graph/detail/sparse_ordering.hpp>
+#include <boost/graph/graph_utility.hpp>
 
 /*
   King Algorithm for matrix reordering
@@ -262,7 +263,7 @@
   king_ordering(const Graph& G, OutputIterator permutation,
                 ColorMap color, DegreeMap degree, VertexIndexMap index_map)
   {
- if (vertices(G).first == vertices(G).second)
+ if (has_no_vertices(G))
       return permutation;
 
     typedef typename boost::graph_traits<Graph>::vertex_descriptor Vertex;
@@ -298,7 +299,7 @@
   king_ordering(const Graph& G, OutputIterator permutation,
                 VertexIndexMap index_map)
   {
- if (vertices(G).first == vertices(G).second)
+ if (has_no_vertices(G))
       return permutation;
 
     typedef out_degree_property_map<Graph> DegreeMap;

Modified: branches/release/boost/graph/metric_tsp_approx.hpp
==============================================================================
--- branches/release/boost/graph/metric_tsp_approx.hpp (original)
+++ branches/release/boost/graph/metric_tsp_approx.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -310,4 +310,4 @@
 
 } //boost
 
-#endif // BOOST_GRAPH_METRIC_TSP_APPROX_HPP
\ No newline at end of file
+#endif // BOOST_GRAPH_METRIC_TSP_APPROX_HPP

Modified: branches/release/boost/graph/named_function_params.hpp
==============================================================================
--- branches/release/boost/graph/named_function_params.hpp (original)
+++ branches/release/boost/graph/named_function_params.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -49,6 +49,8 @@
   struct iterations_t { };
   struct diameter_range_t { };
   struct learning_constant_range_t { };
+ struct vertices_equivalent_t { };
+ struct edges_equivalent_t { };
 
 #define BOOST_BGL_DECLARE_NAMED_PARAMS \
     BOOST_BGL_ONE_PARAM_CREF(weight_map, edge_weight) \
@@ -94,7 +96,9 @@
     BOOST_BGL_ONE_PARAM_CREF(cooling, cooling) \
     BOOST_BGL_ONE_PARAM_CREF(iterations, iterations) \
     BOOST_BGL_ONE_PARAM_CREF(diameter_range, diameter_range) \
- BOOST_BGL_ONE_PARAM_CREF(learning_constant_range, learning_constant_range)
+ BOOST_BGL_ONE_PARAM_CREF(learning_constant_range, learning_constant_range) \
+ BOOST_BGL_ONE_PARAM_CREF(vertices_equivalent, vertices_equivalent) \
+ BOOST_BGL_ONE_PARAM_CREF(edges_equivalent, edges_equivalent)
 
   template <typename T, typename Tag, typename Base = no_property>
   struct bgl_named_params : public Base

Modified: branches/release/boost/graph/properties.hpp
==============================================================================
--- branches/release/boost/graph/properties.hpp (original)
+++ branches/release/boost/graph/properties.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -13,6 +13,7 @@
 #include <boost/config.hpp>
 #include <cassert>
 #include <boost/pending/property.hpp>
+#include <boost/detail/workaround.hpp>
 
 // Include the property map library and extensions in the BGL.
 #include <boost/property_map/property_map.hpp>
@@ -357,6 +358,13 @@
 # define BOOST_GRAPH_NO_BUNDLED_PROPERTIES
 #endif
 
+#if BOOST_WORKAROUND(__SUNPRO_CC, BOOST_TESTED_AT(0x590)) && !defined (BOOST_GRAPH_NO_BUNDLED_PROPERTIES)
+// This compiler cannot define a partial specialization based on a
+// pointer-to-member type, as seen in boost/graph/subgraph.hpp line 985 (as of
+// trunk r53912)
+# define BOOST_GRAPH_NO_BUNDLED_PROPERTIES
+#endif
+
 #ifndef BOOST_GRAPH_NO_BUNDLED_PROPERTIES
   template<typename Graph, typename Descriptor, typename Bundle, typename T>
   struct bundle_property_map

Modified: branches/release/boost/graph/push_relabel_max_flow.hpp
==============================================================================
--- branches/release/boost/graph/push_relabel_max_flow.hpp (original)
+++ branches/release/boost/graph/push_relabel_max_flow.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -121,7 +121,7 @@
         : g(g_), n(num_vertices(g_)), capacity(cap), src(src_), sink(sink_),
           index(idx),
           excess_flow(num_vertices(g_)),
- current(num_vertices(g_), out_edges(*vertices(g_).first, g_).second),
+ current(num_vertices(g_), out_edges(*vertices(g_).first, g_)),
           distance(num_vertices(g_)),
           color(num_vertices(g_)),
           reverse_edge(rev),
@@ -149,7 +149,7 @@
         for (tie(u_iter, u_end) = vertices(g); u_iter != u_end; ++u_iter) {
           vertex_descriptor u = *u_iter;
           excess_flow[u] = 0;
- current[u] = out_edges(u, g).first;
+ current[u] = out_edges(u, g);
         }
 
         bool overflow_detected = false;
@@ -240,7 +240,7 @@
                 && is_residual_edge(reverse_edge[a])) {
               distance[v] = d_v;
               color[v] = ColorTraits::gray();
- current[v] = out_edges(v, g).first;
+ current[v] = out_edges(v, g);
               max_distance = max BOOST_PREVENT_MACRO_SUBSTITUTION(d_v, max_distance);
 
               if (excess_flow[v] > 0)
@@ -262,8 +262,7 @@
         assert(excess_flow[u] > 0);
         while (1) {
           out_edge_iterator ai, ai_end;
- for (ai = current[u], ai_end = out_edges(u, g).second;
- ai != ai_end; ++ai) {
+ for (tie(ai, ai_end) = current[u]; ai != ai_end; ++ai) {
             edge_descriptor a = *ai;
             if (is_residual_edge(a)) {
               vertex_descriptor v = target(a, g);
@@ -291,7 +290,7 @@
             if (distance[u] == n)
               break;
           } else { // i is no longer active
- current[u] = ai;
+ current[u].first = ai;
             add_to_inactive_list(u, layer);
             break;
           }
@@ -350,7 +349,7 @@
         ++min_distance;
         if (min_distance < n) {
           distance[u] = min_distance; // this is the main action
- current[u] = min_edge_iter;
+ current[u].first = min_edge_iter;
           max_distance = max BOOST_PREVENT_MACRO_SUBSTITUTION(min_distance, max_distance);
         }
         return min_distance;
@@ -444,7 +443,7 @@
           u = *u_iter;
           color[u] = ColorTraits::white();
           parent[u] = u;
- current[u] = out_edges(u, g).first;
+ current[u] = out_edges(u, g);
         }
         // eliminate flow cycles and topologically order the vertices
         for (tie(u_iter, u_end) = vertices(g); u_iter != u_end; ++u_iter) {
@@ -455,8 +454,8 @@
             r = u;
             color[r] = ColorTraits::gray();
             while (1) {
- for (; current[u] != out_edges(u, g).second; ++current[u]) {
- edge_descriptor a = *current[u];
+ for (; current[u].first != current[u].second; ++current[u].first) {
+ edge_descriptor a = *current[u].first;
                 if (capacity[a] == 0 && is_residual_edge(a)) {
                   vertex_descriptor v = target(a, g);
                   if (color[v] == ColorTraits::white()) {
@@ -469,16 +468,16 @@
                     FlowValue delta = residual_capacity[a];
                     while (1) {
                       BOOST_USING_STD_MIN();
- delta = min BOOST_PREVENT_MACRO_SUBSTITUTION(delta, residual_capacity[*current[v]]);
+ delta = min BOOST_PREVENT_MACRO_SUBSTITUTION(delta, residual_capacity[*current[v].first]);
                       if (v == u)
                         break;
                       else
- v = target(*current[v], g);
+ v = target(*current[v].first, g);
                     }
                     // remove delta flow units
                     v = u;
                     while (1) {
- a = *current[v];
+ a = *current[v].first;
                       residual_capacity[a] -= delta;
                       residual_capacity[reverse_edge[a]] += delta;
                       v = target(a, g);
@@ -488,25 +487,25 @@
 
                     // back-out of DFS to the first saturated edge
                     restart = u;
- for (v = target(*current[u], g); v != u; v = target(a, g)){
- a = *current[v];
+ for (v = target(*current[u].first, g); v != u; v = target(a, g)){
+ a = *current[v].first;
                       if (color[v] == ColorTraits::white()
                           || is_saturated(a)) {
- color[target(*current[v], g)] = ColorTraits::white();
+ color[target(*current[v].first, g)] = ColorTraits::white();
                         if (color[v] != ColorTraits::white())
                           restart = v;
                       }
                     }
                     if (restart != u) {
                       u = restart;
- ++current[u];
+ ++current[u].first;
                       break;
                     }
                   } // else if (color[v] == ColorTraits::gray())
                 } // if (capacity[a] == 0 ...
               } // for out_edges(u, g) (though "u" changes during loop)
               
- if (current[u] == out_edges(u, g).second) {
+ if ( current[u].first == current[u].second ) {
                 // scan of i is complete
                 color[u] = ColorTraits::black();
                 if (u != src) {
@@ -521,7 +520,7 @@
                 }
                 if (u != r) {
                   u = parent[u];
- ++current[u];
+ ++current[u].first;
                 } else
                   break;
               }
@@ -533,8 +532,8 @@
         // note that the sink is not on the stack
         if (! bos_null) {
           for (u = tos; u != bos; u = topo_next[u]) {
- ai = out_edges(u, g).first;
- while (excess_flow[u] > 0 && ai != out_edges(u, g).second) {
+ tie(ai, a_end) = out_edges(u, g);
+ while (excess_flow[u] > 0 && ai != a_end) {
               if (capacity[*ai] == 0 && is_residual_edge(*ai))
                 push_flow(*ai);
               ++ai;
@@ -632,7 +631,7 @@
 
       // will need to use random_access_property_map with these
       std::vector< FlowValue > excess_flow;
- std::vector< out_edge_iterator > current;
+ std::vector< std::pair<out_edge_iterator, out_edge_iterator> > current;
       std::vector< distance_size_type > distance;
       std::vector< default_color_type > color;
 

Modified: branches/release/boost/graph/relax.hpp
==============================================================================
--- branches/release/boost/graph/relax.hpp (original)
+++ branches/release/boost/graph/relax.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -48,14 +48,17 @@
       D d_u = get(d, u), d_v = get(d, v);
       W w_e = get(w, e);
       
+ // The redundant gets in the return statements are to ensure that extra
+ // floating-point precision in x87 registers does not lead to relax()
+ // returning true when the distance did not actually change.
       if ( compare(combine(d_u, w_e), d_v) ) {
         put(d, v, combine(d_u, w_e));
         put(p, v, u);
- return true;
+ return compare(get(d, v), d_v);
       } else if (is_undirected && compare(combine(d_v, w_e), d_u)) {
         put(d, u, combine(d_v, w_e));
         put(p, u, v);
- return true;
+ return compare(get(d, u), d_u);
       } else
         return false;
     }

Modified: branches/release/boost/graph/rmat_graph_generator.hpp
==============================================================================
--- branches/release/boost/graph/rmat_graph_generator.hpp (original)
+++ branches/release/boost/graph/rmat_graph_generator.hpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -17,9 +17,11 @@
 #include <map>
 #include <boost/shared_ptr.hpp>
 #include <boost/random/uniform_int.hpp>
+#include <boost/random/uniform_01.hpp>
 #include <boost/graph/graph_traits.hpp>
 #include <boost/type_traits/is_base_and_derived.hpp>
 #include <boost/type_traits/is_same.hpp>
+#include <boost/test/floating_point_comparison.hpp>
 
 using boost::shared_ptr;
 using boost::uniform_01;
@@ -103,7 +105,10 @@
     
     double S = a + b + c + d;
     
- a /= S; b /= S; c /= S; d /= S;
+ a /= S; b /= S; c /= S;
+ // d /= S;
+ // Ensure all values add up to 1, regardless of floating point errors
+ d = 1. - a - b - c;
   }
 
   return std::make_pair(u, v);
@@ -150,7 +155,7 @@
     {
       this->gen.reset(new uniform_01<RandomGenerator>(gen));
 
- assert(a + b + c + d == 1);
+ assert(boost::test_tools::check_is_close(a + b + c + d, 1., boost::test_tools::fraction_tolerance(1.e-5)));
 
       if (permute_vertices)
         generate_permutation_vector(gen, vertexPermutation, n);
@@ -225,9 +230,9 @@
     bool operator() (const std::pair<T,T>& x, const std::pair<T,T>& y)
     {
       if (x.first == y.first)
- return x.second >= y.second;
+ return x.second > y.second;
       else
- return x.first >= y.first;
+ return x.first > y.first;
     }
   };
 
@@ -260,7 +265,7 @@
         values(sort_pair<vertices_size_type>()), done(false)
               
     {
- assert(a + b + c + d == 1);
+ assert(boost::test_tools::check_is_close(a + b + c + d, 1., boost::test_tools::fraction_tolerance(1.e-5)));
 
       this->gen.reset(new uniform_01<RandomGenerator>(gen));
 
@@ -271,7 +276,7 @@
       // TODO: "Clip and flip" if undirected graph
       int SCALE = int_log2(n);
       
- for (int i = 0; i < m; ++i) {
+ for (edges_size_type i = 0; i < m; ++i) {
 
         vertices_size_type u, v;
         tie(u, v) = generate_edge(this->gen, n, SCALE, a, b, c, d);
@@ -361,7 +366,7 @@
       : gen(), done(false)
               
     {
- assert(a + b + c + d == 1);
+ assert(boost::test_tools::check_is_close(a + b + c + d, 1., boost::test_tools::fraction_tolerance(1.e-5)));
 
       this->gen.reset(new uniform_01<RandomGenerator>(gen));
 
@@ -474,7 +479,7 @@
         values(sort_pair<vertices_size_type>()), done(false)
               
     {
- assert(a + b + c + d == 1);
+ assert(boost::test_tools::check_is_close(a + b + c + d, 1., boost::test_tools::fraction_tolerance(1.e-5)));
 
       this->gen.reset(new uniform_01<RandomGenerator>(gen));
       

Modified: branches/release/libs/graph/doc/compressed_sparse_row.html
==============================================================================
--- branches/release/libs/graph/doc/compressed_sparse_row.html (original)
+++ branches/release/libs/graph/doc/compressed_sparse_row.html 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -115,14 +115,27 @@
   <a href="#default-const">compressed_sparse_row_graph</a>();
 
   <i>// Unsorted edge list constructors <b>(new interface only)</b></i>
- template&lt;typename MultiPassInputIterator&gt;
+ template&lt;typename InputIterator&gt;
   <a href="#edge-const">compressed_sparse_row_graph</a>(edges_are_unsorted_t,
+ InputIterator edge_begin, InputIterator edge_end,
+ vertices_size_type numverts,
+ const GraphProperty&amp; prop = GraphProperty());
+
+ template&lt;typename InputIterator, typename EdgePropertyIterator&gt;
+ compressed_sparse_row_graph(edges_are_unsorted_t,
+ InputIterator edge_begin, InputIterator edge_end,
+ EdgePropertyIterator ep_iter,
+ vertices_size_type numverts,
+ const GraphProperty&amp; prop = GraphProperty());
+
+ template&lt;typename MultiPassInputIterator&gt;
+ compressed_sparse_row_graph(edges_are_unsorted_multi_pass_t,
                               MultiPassInputIterator edge_begin, MultiPassInputIterator edge_end,
                               vertices_size_type numverts,
                               const GraphProperty&amp; prop = GraphProperty());
 
   template&lt;typename MultiPassInputIterator, typename EdgePropertyIterator&gt;
- compressed_sparse_row_graph(edges_are_unsorted_t,
+ compressed_sparse_row_graph(edges_are_unsorted_multi_pass_t,
                               MultiPassInputIterator edge_begin, MultiPassInputIterator edge_end,
                               EdgePropertyIterator ep_iter,
                               vertices_size_type numverts,
@@ -264,16 +277,23 @@
 void set_property(const compressed_sparse_row_graph&amp; g, GraphPropertyTag,
                   const typename graph_property&lt;compressed_sparse_row_graph, GraphPropertyTag&gt;::type&amp; value);
 
-<i>// Incremental construction functions (old interface only)</i>
+<i>// Incremental construction functions</i>
+<b>(old interface only)</b>
 template&lt;typename Graph&gt;
 vertex_descriptor add_vertex(compressed_sparse_row_graph&amp; g);
 
+<b>(old interface only)</b>
 template&lt;typename Graph&gt;
 vertex_descriptor add_vertices(vertices_size_type count, compressed_sparse_row_graph&amp; g);
 
+<b>(old interface only)</b>
 template&lt;typename Graph&gt;
 edge_descriptor add_edge(vertex_descriptor src, vertex_descriptor tgt, compressed_sparse_row_graph&amp; g);
 
+<b>(new interface only)</b>
+template&lt;typename InputIterator, typename Graph&gt;
+void add_edges(InputIterator first, InputIterator last, compressed_sparse_row_graph&amp; g);
+
 } <i>// end namespace boost</i>
    </pre>
 
@@ -401,8 +421,67 @@
     <hr></hr>
 
     <pre><a name="edge-const"></a>
- template&lt;typename MultiPassInputIterator&gt;
+ template&lt;typename InputIterator&gt;
+ compressed_sparse_row_graph(edges_are_unsorted_t,
+ InputIterator edge_begin, InputIterator edge_end,
+ vertices_size_type numverts,
+ const GraphProperty&amp; prop = GraphProperty());
+ </pre>
+
+ <p class="indent">
+ Constructs a graph with <code>numverts</code> vertices whose
+ edges are specified by the iterator range <code>[edge_begin,
+ edge_end)</code>. The <tt>InputIterator</tt> must be a model of
+ <a
+ href="http://www.sgi.com/tech/stl/InputIterator.html">InputIterator</a>
+ whose <code>value_type</code> is an <code>std::pair</code> of
+ integer values. These integer values are the source and target
+ vertices for the edges, and must fall within the range <code>[0,
+ numverts)</code>. The edges in <code>[edge_begin,
+ edge_end)</code> do not need to be sorted. This constructor uses extra
+ memory to save the edge information before adding it to the graph,
+ avoiding the requirement for the iterator to have multi-pass capability.
+ <b>(This function is only provided by the new interface.)</b>
+ </p>
+
+ <p class="indent">
+ The value <code>prop</code> will be used to initialize the graph
+ property.
+ </p>
+
+ <hr></hr>
+
+ <pre><a name="edge-prop-const"></a>
+ template&lt;typename InputIterator, typename EdgePropertyIterator&gt;
   compressed_sparse_row_graph(edges_are_unsorted_t,
+ InputIterator edge_begin, InputIterator edge_end,
+ EdgePropertyIterator ep_iter,
+ vertices_size_type numverts,
+ const GraphProperty&amp; prop = GraphProperty());
+ </pre>
+ <p class="indent">
+ This constructor constructs a graph with <code>numverts</code>
+ vertices and the edges provided in the iterator range
+ <code>[edge_begin, edge_end)</code>. Its semantics are identical
+ to the edge range constructor, except
+ that edge properties are also initialized. The type
+ <tt>EdgePropertyIterator</tt> must be a model of the <a
+ href="http://www.sgi.com/tech/stl/InputIterator.html">InputIterator</a>
+ concept whose <tt>value_type</tt> is convertible to
+ <tt>EdgeProperty</tt>. The iterator range <tt>[ep_iter, ep_ter +
+ m)</tt> will be used to initialize the properties on the edges
+ of the graph, where <tt>m</tt> is distance from
+ <tt>edge_begin</tt> to <tt>edge_end</tt>. This constructor uses extra
+ memory to save the edge information before adding it to the graph,
+ avoiding the requirement for the iterator to have multi-pass capability.
+ <b>(This function is only provided by the new interface.)</b>
+ </p>
+
+ <hr></hr>
+
+ <pre><a name="edge-const"></a>
+ template&lt;typename MultiPassInputIterator&gt;
+ compressed_sparse_row_graph(edges_are_unsorted_multi_pass_t,
                               MultiPassInputIterator edge_begin, MultiPassInputIterator edge_end,
                               vertices_size_type numverts,
                               const GraphProperty&amp; prop = GraphProperty());
@@ -418,7 +497,8 @@
       integer values. These integer values are the source and target
       vertices for the edges, and must fall within the range <code>[0,
       numverts)</code>. The edges in <code>[edge_begin,
- edge_end)</code> do not need to be sorted.
+ edge_end)</code> do not need to be sorted. Multiple passes will be made
+ over the edge range.
       <b>(This function is only provided by the new interface.)</b>
     </p>
 
@@ -431,7 +511,7 @@
 
     <pre><a name="edge-prop-const"></a>
   template&lt;typename MultiPassInputIterator, typename EdgePropertyIterator&gt;
- compressed_sparse_row_graph(edges_are_unsorted_t,
+ compressed_sparse_row_graph(edges_are_unsorted_multi_pass_t,
                               MultiPassInputIterator edge_begin, MultiPassInputIterator edge_end,
                               EdgePropertyIterator ep_iter,
                               vertices_size_type numverts,
@@ -449,7 +529,8 @@
       <tt>EdgeProperty</tt>. The iterator range <tt>[ep_iter, ep_ter +
         m)</tt> will be used to initialize the properties on the edges
       of the graph, where <tt>m</tt> is distance from
- <tt>edge_begin</tt> to <tt>edge_end</tt>.
+ <tt>edge_begin</tt> to <tt>edge_end</tt>. Multiple passes will be made
+ over the edge and property ranges.
       <b>(This function is only provided by the new interface.)</b>
     </p>
 
@@ -834,6 +915,23 @@
     </p>
 
     <hr></hr>
+
+ <pre><a name="add_edges"></a>
+template&lt;typename InputIterator&gt;
+edge_descriptor add_edges(InputIterator first, InputIterator last, compressed_sparse_row_graph&amp; g)
+ </pre>
+
+ <p class="indent">
+ Add a range of edges (from <tt>first</tt> to <tt>last</tt>) to the graph.
+ The <tt>InputIterator</tt> must be a model of <a
+ href="http://www.sgi.com/tech/stl/InputIterator.html">InputIterator</a>
+ whose <code>value_type</code> is an <code>std::pair</code> of integer
+ values. These integer values are the source and target vertices of the
+ new edges. The edges do not need to be sorted.
+ <b>(This function is only provided by the new interface.)</b>
+ </p>
+
+ <hr></hr>
     <a name="example"></a><h2>Example</h2>
 
     <br>[<a

Modified: branches/release/libs/graph/test/Jamfile.v2
==============================================================================
--- branches/release/libs/graph/test/Jamfile.v2 (original)
+++ branches/release/libs/graph/test/Jamfile.v2 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -41,7 +41,7 @@
     [ run bfs.cpp ../../test/build//boost_test_exec_monitor ]
     [ compile bfs_cc.cpp ]
     [ run bellman-test.cpp ]
- [ run betweenness_centrality_test.cpp ]
+ [ run betweenness_centrality_test.cpp : 100 ]
     [ run bidir_remove_edge.cpp ]
     [ run csr_graph_test.cpp : : : : : <variant>release ]
     [ run dag_longest_paths.cpp ]

Modified: branches/release/libs/graph/test/betweenness_centrality_test.cpp
==============================================================================
--- branches/release/libs/graph/test/betweenness_centrality_test.cpp (original)
+++ branches/release/libs/graph/test/betweenness_centrality_test.cpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -16,6 +16,7 @@
 #include <boost/test/minimal.hpp>
 #include <boost/random/uniform_01.hpp>
 #include <boost/random/linear_congruential.hpp>
+#include <boost/lexical_cast.hpp>
 
 using namespace boost;
 
@@ -440,8 +441,10 @@
   }
 }
 
-int test_main(int, char*[])
+int test_main(int argc, char* argv[])
 {
+ int random_test_num_vertices = 300;
+ if (argc >= 2) random_test_num_vertices = boost::lexical_cast<int>(argv[1]);
   typedef adjacency_list<listS, listS, undirectedS,
                          property<vertex_index_t, int>, EdgeProperties>
     Graph;
@@ -512,7 +515,7 @@
 
   run_wheel_test((Graph*)0, 15);
 
- random_unweighted_test((Graph*)0, 300);
+ random_unweighted_test((Graph*)0, random_test_num_vertices);
 
   return 0;
 }

Modified: branches/release/libs/graph/test/csr_graph_test.cpp
==============================================================================
--- branches/release/libs/graph/test/csr_graph_test.cpp (original)
+++ branches/release/libs/graph/test/csr_graph_test.cpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -84,6 +84,7 @@
       std::sort(edges1.begin(), edges1.end());
       std::sort(edges2.begin(), edges2.end());
       if (edges1 != edges2) {
+ std::cerr << "For vertex " << v1 << std::endl;
         std::cerr << "edges1:";
         for (size_t i = 0; i < edges1.size(); ++i) std::cerr << " " << edges1[i];
         std::cerr << std::endl;
@@ -481,7 +482,21 @@
     std::cout << "Testing CSR graph built from unsorted edges" << std::endl;
     std::pair<int, int> unsorted_edges[] = {std::make_pair(5, 0), std::make_pair(3, 2), std::make_pair(4, 1), std::make_pair(4, 0), std::make_pair(0, 2), std::make_pair(5, 2)};
     CSRGraphT g(boost::edges_are_unsorted, unsorted_edges, unsorted_edges + sizeof(unsorted_edges) / sizeof(*unsorted_edges), 6);
+ CSRGraphT g2(boost::edges_are_unsorted_multi_pass, unsorted_edges, unsorted_edges + sizeof(unsorted_edges) / sizeof(*unsorted_edges), 6);
     graph_test(g);
+ graph_test(g2);
+ assert_graphs_equal(g, boost::identity_property_map(),
+ g2, boost::identity_property_map(),
+ boost::identity_property_map());
+ std::cout << "Testing CSR graph built using add_edges" << std::endl;
+ // Test building a graph using add_edges on unsorted lists
+ CSRGraphT g3(boost::edges_are_unsorted, unsorted_edges, unsorted_edges, 6); // Empty range
+ add_edges(unsorted_edges, unsorted_edges + 3, g3);
+ add_edges(unsorted_edges + 3, unsorted_edges + 6, g3);
+ graph_test(g3);
+ assert_graphs_equal(g, boost::identity_property_map(),
+ g3, boost::identity_property_map(),
+ boost::identity_property_map());
   }
 #endif // BOOST_GRAPH_USE_NEW_CSR_INTERFACE
 

Modified: branches/release/libs/graph/test/gursoy_atun_layout_test.cpp
==============================================================================
--- branches/release/libs/graph/test/gursoy_atun_layout_test.cpp (original)
+++ branches/release/libs/graph/test/gursoy_atun_layout_test.cpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -59,7 +59,7 @@
 
   // Make grid, like Gursoy and Atun used
   std::map<int, std::map<int, vertex_descriptor> > verts;
- const int grid_size = 30;
+ const int grid_size = 20;
   boost::minstd_rand edge_weight_gen;
   boost::uniform_01<boost::minstd_rand> random_edge_weight(edge_weight_gen);
   for (int i = 0; i < grid_size; ++i)
@@ -94,7 +94,7 @@
                    plod_iterator<minstd_rand, graph_type>(),
                    n);
 #else
- int n = 100000;
+ int n = 1000;
   int k = 6;
   double p = 0.001;
   minstd_rand gen;
@@ -120,19 +120,23 @@
 
   boost::gursoy_atun_layout(graph, space, position);
 
+#if 0
   std::cerr << "--------Unweighted layout--------\n";
   boost::write_graphviz(std::cout, graph,
                         position_writer<Position, vertex_descriptor>(position),
                         boost::default_writer(),
                         graph_writer());
+#endif
 
   boost::gursoy_atun_layout(graph, space, position,
                             weight_map(get(boost::edge_weight, graph)));
 
+#if 0
   std::cerr << "--------Weighted layout--------\n";
   boost::write_graphviz(std::cout, graph,
                         position_writer<Position, vertex_descriptor>(position),
                         boost::default_writer(),
                         graph_writer());
+#endif
   return 0;
 }

Copied: branches/release/libs/graph_parallel/example/Jamfile.v2 (from r53934, /trunk/libs/graph_parallel/example/Jamfile.v2)
==============================================================================
--- /trunk/libs/graph_parallel/example/Jamfile.v2 (original)
+++ branches/release/libs/graph_parallel/example/Jamfile.v2 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -1,3 +1,9 @@
+# Copyright 2009 Vladimir Prus.
+#
+# Distributed under the Boost Software License, Version 1.0.
+# (See accompanying file LICENSE_1_0.txt or copy at
+# http://www.boost.org/LICENSE_1_0.txt)
+
 
 project : requirements <library>../build//boost_graph_parallel
     <library>../../system/build//boost_system

Modified: branches/release/libs/graph_parallel/example/breadth_first_search.cpp
==============================================================================
--- branches/release/libs/graph_parallel/example/breadth_first_search.cpp (original)
+++ branches/release/libs/graph_parallel/example/breadth_first_search.cpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -83,7 +83,7 @@
     outfile = argv[2];
   else {
     outfile = filename;
- int i = outfile.rfind('.');
+ size_t i = outfile.rfind('.');
     if (i != std::string::npos)
       outfile.erase(outfile.begin() + i, outfile.end());
     outfile += "-bfs.dot";

Modified: branches/release/libs/graph_parallel/example/dijkstra_shortest_paths.cpp
==============================================================================
--- branches/release/libs/graph_parallel/example/dijkstra_shortest_paths.cpp (original)
+++ branches/release/libs/graph_parallel/example/dijkstra_shortest_paths.cpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -78,7 +78,7 @@
   if (argc > 2)
     outfile = argv[2];
   else {
- int i = outfile.rfind('.');
+ size_t i = outfile.rfind('.');
     if (i != std::string::npos)
       outfile.erase(outfile.begin() + i, outfile.end());
     outfile += "-dijkstra.dot";

Copied: branches/release/libs/graph_parallel/test/Jamfile.v2 (from r53934, /trunk/libs/graph_parallel/test/Jamfile.v2)
==============================================================================
--- /trunk/libs/graph_parallel/test/Jamfile.v2 (original)
+++ branches/release/libs/graph_parallel/test/Jamfile.v2 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -17,30 +17,30 @@
 {
 test-suite graph_parallel
   :
- [ mpi-test distributed_property_map_test ]
- [ mpi-test distributed_queue_test ]
+ [ mpi-test distributed_property_map_test : : : 2 ]
+ [ mpi-test distributed_queue_test : : : 2 ]
   [ mpi-test process_group_serialization : : : 2 ]
- [ mpi-test adjlist_build_test ]
- [ mpi-test adjlist_redist_test ]
+ [ mpi-test adjlist_build_test : : : 2 ]
+ [ mpi-test adjlist_redist_test : : : 2 ]
   [ mpi-test adjlist_remove_test : : : 2 ]
- [ mpi-test distributed_adjacency_list_test ]
- [ mpi-test distributed_connected_components_test ]
- [ mpi-test distributed_page_rank_test ]
- [ mpi-test distributed_csr_test ]
- [ mpi-test distributed_dfs_test ]
- [ mpi-test distributed_graph_coloring_test ]
- [ mpi-test distributed_mst_test ]
- [ mpi-test distributed_strong_components_test ]
- [ mpi-test hohberg_biconnected_components_test ]
- [ mpi-test mesh_generator_test : : <testing.arg>"1000 1000 1 0" ]
+ [ mpi-test distributed_adjacency_list_test : : : 2 ]
+ [ mpi-test distributed_connected_components_test : : : 2 ]
+ [ mpi-test distributed_page_rank_test : : : 2 ]
+ [ mpi-test distributed_csr_test : : : 2 ]
+ [ mpi-test distributed_dfs_test : : : 2 ]
+ [ mpi-test distributed_graph_coloring_test : : : 2 ]
+ [ mpi-test distributed_mst_test : : : 2 ]
+ [ mpi-test distributed_strong_components_test : : : 2 ]
+ [ mpi-test hohberg_biconnected_components_test : : : 2 ]
+ [ mpi-test mesh_generator_test : : <testing.arg>"1000 1000 1 0" : 2 ]
   [ mpi-test named_vertices_seq : : : 1 ]
- [ mpi-test distributed_shortest_paths_test ]
+ [ mpi-test distributed_shortest_paths_test : : : 2 ]
   [ mpi-test distributed_csr_algorithm_test : : : 1 ]
- [ mpi-test distributed_betweenness_centrality_test ]
- [ mpi-test distributed_dimacs_reader ]
- [ mpi-test distributed_rmat_cc_ps ]
- [ mpi-test distributed_rmat_cc ]
- [ mpi-test distributed_rmat_pagerank ]
+ [ mpi-test distributed_betweenness_centrality_test : : : 2 ]
+ [ mpi-test distributed_dimacs_reader : : : 2 ]
+ [ mpi-test distributed_rmat_cc_ps : : : 2 ]
+ [ mpi-test distributed_rmat_cc : : : 2 ]
+ [ mpi-test distributed_rmat_pagerank : : : 2 ]
   ;
 }
 

Modified: branches/release/libs/graph_parallel/test/distributed_adjacency_list_test.cpp
==============================================================================
--- branches/release/libs/graph_parallel/test/distributed_adjacency_list_test.cpp (original)
+++ branches/release/libs/graph_parallel/test/distributed_adjacency_list_test.cpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -198,7 +198,7 @@
       in_degree(*v, g3);
     }
 
- int added_edges = 0;
+ graph_traits<Graph3>::vertices_size_type added_edges = 0;
     if (num_vertices(g3) >= 2) {
       graph_traits<Graph3>::vertex_iterator vi = vertices(g3).first;
       graph_traits<Graph3>::vertex_descriptor u = *vi++;
@@ -239,7 +239,7 @@
     }
 
     synchronize(g3);
- assert(std::distance(edges(g3).first, edges(g3).second) == added_edges);
+ assert(std::distance(edges(g3).first, edges(g3).second) == (ptrdiff_t)added_edges);
     assert(num_edges(g3) == added_edges);
 
     // Verify the remote edges
@@ -250,7 +250,7 @@
       int prior_processor = (process_id(pg) + num_processes(pg) - 1)
         % num_processes(pg);
       const int n = 20;
- int vertices_in_prior = (n / num_processes(pg))
+ graph_traits<Graph3>::vertices_size_type vertices_in_prior = (n / num_processes(pg))
         + (n % num_processes(pg) > prior_processor? 1 : 0);
       if (in_degree(u, g3) != vertices_in_prior + 2) {
         std::cerr << "#" << process_id(pg) << ": " << in_degree(u, g3)

Modified: branches/release/libs/graph_parallel/test/distributed_dfs_test.cpp
==============================================================================
--- branches/release/libs/graph_parallel/test/distributed_dfs_test.cpp (original)
+++ branches/release/libs/graph_parallel/test/distributed_dfs_test.cpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -139,8 +139,10 @@
      make_iterator_property_map(explore.begin(), get(vertex_index, g)),
      get(vertex_index, g));
 
+#if 0
   std::size_t correct_parents1[N] = {u, u, y, y, v, w};
   std::size_t correct_parents2[N] = {u, u, y, v, x, w};
+#endif
 
   for (std::size_t i = 0; i < N; ++i) {
     vertex_descriptor v = vertex(i, g);

Modified: branches/release/libs/graph_parallel/test/distributed_property_map_test.cpp
==============================================================================
--- branches/release/libs/graph_parallel/test/distributed_property_map_test.cpp (original)
+++ branches/release/libs/graph_parallel/test/distributed_property_map_test.cpp 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -182,7 +182,7 @@
   
   bool my_start_value = process_id(pg) % 2;
   int next_processor = (process_id(pg) + 1) % num_processes(pg);
- bool next_start_value = !my_start_value;
+ bool next_start_value = ((process_id(pg) + 1) % num_processes(pg)) % 2;
 
   // Initial color map: even-numbered processes are false,
   // odd-numbered processes are true
@@ -298,7 +298,7 @@
   // check next processor's strings
   for (int i = 0; i < n; ++i) {
     remote_key k(next_processor, i);
- BOOST_CHECK(get(strings, k) == std::string());
+ BOOST_CHECK(get(strings, k) == (num_processes(pg) == 1 ? my_start_string : std::string()));
   }
 
   if (process_id(pg) == 0) std::cerr << "OK.\nSynchronizing...";

Modified: branches/release/status/explicit-failures-markup.xml
==============================================================================
--- branches/release/status/explicit-failures-markup.xml (original)
+++ branches/release/status/explicit-failures-markup.xml 2009-06-18 15:34:25 EDT (Thu, 18 Jun 2009)
@@ -1790,10 +1790,18 @@
     <!-- graph -->
     <library name="graph">
         <mark-unusable>
- <toolset name="borland-5.6*"/>
- <toolset name="borland-5.8*"/>
+ <toolset name="borland-5.*"/>
+ <toolset name="borland-6.*"/>
             <toolset name="msvc-6.5*"/>
             <toolset name="sunpro-5_3-sunos"/>
+ <!-- Open64 and Pathscale ICE on almost all test cases, often
+ because of http://gcc.gnu.org/bugzilla/show_bug.cgi?id=17327;
+ property type detection fails because it uses enum types as tags.
+ -->
+ <toolset name="gcc-open64"/>
+ <toolset name="pathscale-3.1"/>
+ <!-- vacpp ICEs on many of the tests -->
+ <toolset name="vacpp"/>
         </mark-unusable>
         <mark-expected-failures>
             <test name="adj_matrix_cc"/>


Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk