Zoltan2
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Pages
Zoltan2_TpetraCrsColorerUtils.hpp
Go to the documentation of this file.
1 #pragma once
2 
3 #include "Teuchos_RCP.hpp"
4 #include "Teuchos_Comm.hpp"
5 
6 #include "Tpetra_CrsGraph.hpp"
7 #include "Tpetra_CrsMatrix.hpp"
8 
9 //#include "Tpetra_RowMatrixTransposer.hpp"
10 
11 #include "KokkosKernels_Utils.hpp"
12 #include "KokkosSparse_Utils.hpp"
13 
14 namespace Zoltan2
15 {
16 
17 // Some utility functions to help with coloring
18 namespace Impl
19 {
20 
21 // Check coloring is valid for a given graph
22 template <typename LO, typename GO, typename NO, typename list_of_colors_t>
23 bool
25  const Tpetra::CrsGraph<LO, GO, NO> &graph,
26  const list_of_colors_t &list_of_colors)
27 {
28  typedef typename list_of_colors_t::execution_space execution_space;
29 
30  Teuchos::RCP<const Teuchos::Comm<int>> comm = graph.getRowMap()->getComm();
31  const int rank = comm->getRank();
32  auto local_graph = graph.getLocalGraphDevice();
33  const size_t num_rows = graph.getLocalNumRows();
34  size_t num_conflict = 0;
35 
36  Kokkos::parallel_reduce(
37  "check_coloring()", Kokkos::RangePolicy<execution_space>(0, num_rows),
38  KOKKOS_LAMBDA(const size_t row, size_t &lcl_conflict) {
39  const size_t entry_begin = local_graph.row_map(row);
40  const size_t entry_end = local_graph.row_map(row + 1);
41  for (size_t entry = entry_begin; entry < entry_end; entry++)
42  {
43  const size_t col = local_graph.entries(entry);
44  for (size_t entry2 = entry_begin; entry2 < entry_end; ++entry2)
45  {
46  const size_t col2 = local_graph.entries(entry2);
47  if (col != col2 && list_of_colors[col] == list_of_colors[col2])
48  {
49  ++lcl_conflict;
50  Kokkos::printf(
51  "proc = %i : Invalid coloring! Local row %zu"
52  " and columns %zu, %zu have the same color %i\n",
53  rank, row, col, col2, list_of_colors[col]);
54  }
55  }
56  }
57  },
58  num_conflict);
59 
60  size_t global_num_conflict = 0;
61  Teuchos::reduceAll(*comm, Teuchos::REDUCE_SUM, 1, &num_conflict,
62  &global_num_conflict);
63 
64  return global_num_conflict == 0;
65 }
66 
68 template <typename LocalCrsGraphType>
69 LocalCrsGraphType
71  const LocalCrsGraphType &local_graph,
72  const size_t num_cols)
73 {
74  using KokkosSparse::Impl::transpose_graph;
75 
76  typedef LocalCrsGraphType graph_t;
77  typedef typename graph_t::row_map_type lno_view_t;
78  typedef typename graph_t::entries_type lno_nnz_view_t;
79  typedef typename lno_view_t::non_const_type trans_row_view_t;
80  typedef typename lno_nnz_view_t::non_const_type trans_nnz_view_t;
81  typedef typename lno_view_t::execution_space exec_t;
82 
83  // Build tranpose graph
84  const size_t num_rows = local_graph.row_map.extent(0) - 1;
85  const size_t num_nnz = local_graph.entries.extent(0);
86 
87  trans_row_view_t trans_row_map("trans_row_map", num_cols + 1);
88  trans_nnz_view_t trans_entries("trans_entries", num_nnz);
89 
90  transpose_graph<lno_view_t, lno_nnz_view_t, trans_row_view_t,
91  trans_nnz_view_t, trans_row_view_t, exec_t>(
92  num_rows, num_cols, local_graph.row_map, local_graph.entries,
93  trans_row_map, trans_entries);
94 
95  graph_t local_trans_graph(trans_entries, trans_row_map);
96 
97  return local_trans_graph;
98 }
99 
101 // template <typename LO, typename GO, typename NO>
102 // Teuchos::RCP<const Tpetra::CrsGraph<LO,GO,NO> >
103 // compute_transpose_graph(const Tpetra::CrsGraph<LO,GO,NO>& graph)
104 // {
105 // typedef double SC;
106 // Teuchos::RCP< Tpetra::CrsMatrix<SC,LO,GO,NO> > matrix =
107 // Teuchos::rcp(new Tpetra::CrsMatrix<double,LO,GO,NO>(Teuchos::rcp(&graph,false)));
108 // Tpetra::RowMatrixTransposer<SC,LO,GO,NO> transposer(matrix);
109 // Teuchos::RCP<Tpetra::CrsMatrix<SC,LO,GO,NO> > trans_matrix =
110 // transposer.createTranspose();
111 // return trans_matrix->getCrsGraph();
112 // }
113 
115 template <typename LO, typename GO, typename NO>
116 Teuchos::RCP<Tpetra::CrsGraph<LO, GO, NO>>
117 compute_transpose_graph(const Tpetra::CrsGraph<LO, GO, NO> &graph)
118 {
119  using Teuchos::RCP;
120  using Teuchos::rcp;
121 
122  typedef Tpetra::CrsGraph<LO, GO, NO> graph_t;
123  typedef typename graph_t::local_graph_device_type local_graph_t;
124 
125  // Transpose local graph
126  local_graph_t local_graph = graph.getLocalGraphDevice();
127  local_graph_t local_trans_graph =
128  compute_local_transpose_graph(local_graph,
129  graph.getLocalNumCols());
130 
131  // Build (possibly overlapped) transpose graph using original graph's
132  // column map as the new row map, and vice versa
133  //
134  // Normally, for a transpose graph, we'd use
135  // original matrix's RangeMap as the DomainMap, and
136  // original matrix's DomainMap as the RangeMap.
137  // Moreover, we're not doing SpMV with the transpose graph, so
138  // you might think we wouldn't care about RangeMap and DomainMap.
139  // But we DO care, because exportAndFillCompleteCrsGraph uses the
140  // shared (overlapped) transpose matrix's RangeMap as the RowMap of the
141  // transpose matrix, while the Zoltan callbacks are assuming the
142  // transpose matrix's RowMap is the same as the original matrix's.
143  // So we'll use the original matrix's RowMap as the RangeMap.
144  RCP<graph_t> trans_graph_shared = rcp(new graph_t(
145  local_trans_graph, graph.getColMap(), graph.getRowMap(),
146  graph.getRangeMap(), graph.getRowMap()));
147 
148  RCP<graph_t> trans_graph;
149 
150  // Export graph to non-overlapped distribution if necessary.
151  // If the exporter is null, we don't need to export
152  RCP<const Tpetra::Export<LO, GO, NO>> exporter =
153  trans_graph_shared->getExporter();
154  if (exporter == Teuchos::null)
155  trans_graph = trans_graph_shared;
156  else
157  {
158  RCP<const graph_t> trans_graph_shared_const = trans_graph_shared;
159  trans_graph = Tpetra::exportAndFillCompleteCrsGraph(
160  trans_graph_shared_const, *exporter,
161  Teuchos::null, Teuchos::null, Teuchos::null);
162  }
163 
164  return trans_graph;
165 }
166 
168 template <typename SC, typename LO, typename GO, typename NO>
169 Teuchos::RCP<Tpetra::CrsGraph<LO, GO, NO>>
170 compute_transpose_graph(const Tpetra::CrsMatrix<SC, LO, GO, NO> &matrix)
171 {
172  return compute_transpose_graph(*(matrix.getCrsGraph()));
173 }
174 
176 template <typename SC, typename LO, typename GO, typename NO>
177 Teuchos::RCP<Tpetra::CrsGraph<LO, GO, NO>>
178 compute_transpose_graph(const Tpetra::BlockCrsMatrix<SC, LO, GO, NO> &matrix)
179 {
180  return compute_transpose_graph(matrix.getCrsGraph());
181 }
182 } // namespace Impl
183 } // namespace Zoltan2
LocalCrsGraphType compute_local_transpose_graph(const LocalCrsGraphType &local_graph, const size_t num_cols)
Teuchos::RCP< Tpetra::CrsGraph< LO, GO, NO > > compute_transpose_graph(const Tpetra::CrsGraph< LO, GO, NO > &graph)
bool check_coloring(const Tpetra::CrsGraph< LO, GO, NO > &graph, const list_of_colors_t &list_of_colors)