3% imbalance should be specified as imbalance = 0.03
| 10 | |
| 11 | // 3% imbalance should be specified as imbalance = 0.03 |
| 12 | void ParHIPPartitionKWay(idxtype *vtxdist, idxtype *xadj, idxtype *adjncy, idxtype *vwgt, idxtype *adjwgt, |
| 13 | int *nparts, double* imbalance, bool suppress_output, int seed, int mode, int *edgecut, idxtype *part, |
| 14 | MPI_Comm *comm) { |
| 15 | |
| 16 | |
| 17 | |
| 18 | std::streambuf* backup = std::cout.rdbuf(); |
| 19 | std::ofstream ofs; |
| 20 | ofs.open("/dev/null"); |
| 21 | |
| 22 | if(suppress_output) { |
| 23 | std::cout.rdbuf(ofs.rdbuf()); |
| 24 | } |
| 25 | |
| 26 | PEID rank, size; |
| 27 | MPI_Comm_rank( *comm, &rank); |
| 28 | MPI_Comm_size( *comm, &size); |
| 29 | |
| 30 | //building internal graph data structure |
| 31 | idxtype local_number_of_nodes = vtxdist[rank+1] - vtxdist[rank]; |
| 32 | idxtype local_number_of_edges = xadj[local_number_of_nodes]; |
| 33 | idxtype number_of_nodes = vtxdist[size]; |
| 34 | |
| 35 | std::vector< NodeID > vertex_weights(local_number_of_nodes,1); |
| 36 | NodeWeight local_overall_node_weight = local_number_of_nodes; |
| 37 | NodeWeight global_node_weight = number_of_nodes; |
| 38 | if( vwgt != NULL ) { |
| 39 | local_overall_node_weight = 0; |
| 40 | global_node_weight = 0; |
| 41 | for( unsigned long long i = 0; i < local_number_of_nodes; i++) { |
| 42 | vertex_weights[i] = vwgt[i]; |
| 43 | local_overall_node_weight += vwgt[i]; |
| 44 | } |
| 45 | MPI_Allreduce(&local_overall_node_weight, &global_node_weight, 1, MPI_UNSIGNED_LONG_LONG, MPI_SUM, *comm); |
| 46 | } |
| 47 | |
| 48 | //// pe p obtains nodes p*ceil(n/size) to (p+1)floor(n/size) and the edges |
| 49 | idxtype from = vtxdist[rank]; |
| 50 | idxtype to = vtxdist[rank+1]-1; |
| 51 | |
| 52 | |
| 53 | unsigned long long global_number_of_edges = 0; |
| 54 | MPI_Allreduce(&local_number_of_edges, &global_number_of_edges, 1, MPI_UNSIGNED_LONG_LONG, MPI_SUM, *comm); |
| 55 | |
| 56 | parallel_graph_access G(*comm); |
| 57 | G.start_construction(local_number_of_nodes, local_number_of_edges, number_of_nodes, global_number_of_edges); |
| 58 | G.set_range(from, to); |
| 59 | std::vector< NodeID > vertex_dist( size+1, 0 ); |
| 60 | for( PEID peID = 0; peID <= size; peID++) { |
| 61 | vertex_dist[peID] = vtxdist[peID]; |
| 62 | } |
| 63 | G.set_range_array(vertex_dist); |
| 64 | |
| 65 | if( adjwgt != NULL ) { |
| 66 | for (NodeID i = 0; i < local_number_of_nodes; ++i) { |
| 67 | NodeID node = G.new_node(); |
| 68 | G.setNodeWeight(node, vertex_weights[i]); |
| 69 | G.setNodeLabel(node, from+node); |