Zoltan2
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Pages
Zoltan2_CoordinateModel.hpp
Go to the documentation of this file.
1 // @HEADER
2 //
3 // ***********************************************************************
4 //
5 // Zoltan2: A package of combinatorial algorithms for scientific computing
6 // Copyright 2012 Sandia Corporation
7 //
8 // Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
9 // the U.S. Government retains certain rights in this software.
10 //
11 // Redistribution and use in source and binary forms, with or without
12 // modification, are permitted provided that the following conditions are
13 // met:
14 //
15 // 1. Redistributions of source code must retain the above copyright
16 // notice, this list of conditions and the following disclaimer.
17 //
18 // 2. Redistributions in binary form must reproduce the above copyright
19 // notice, this list of conditions and the following disclaimer in the
20 // documentation and/or other materials provided with the distribution.
21 //
22 // 3. Neither the name of the Corporation nor the names of the
23 // contributors may be used to endorse or promote products derived from
24 // this software without specific prior written permission.
25 //
26 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
27 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
29 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
30 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
31 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
32 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
33 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
34 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
35 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
36 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
37 //
38 // Questions? Contact Karen Devine (kddevin@sandia.gov)
39 // Erik Boman (egboman@sandia.gov)
40 // Siva Rajamanickam (srajama@sandia.gov)
41 //
42 // ***********************************************************************
43 //
44 // @HEADER
45 
51 #ifndef _ZOLTAN2_COORDINATEMODEL_HPP_
52 #define _ZOLTAN2_COORDINATEMODEL_HPP_
53 
54 #include <Zoltan2_Model.hpp>
55 #include <Zoltan2_MeshAdapter.hpp>
57 #include <Zoltan2_GraphAdapter.hpp>
60 #include <Zoltan2_StridedData.hpp>
61 
62 namespace Zoltan2 {
63 
70 template <typename Adapter>
71 class CoordinateModel : public Model<Adapter>
72 {
73 public:
74 
75 #ifndef DOXYGEN_SHOULD_SKIP_THIS
76  typedef typename Adapter::scalar_t scalar_t;
77  typedef typename Adapter::gno_t gno_t;
78  typedef typename Adapter::lno_t lno_t;
79  typedef typename Adapter::node_t node_t;
80  typedef typename Adapter::user_t user_t;
81  typedef typename Adapter::userCoord_t userCoord_t;
82  typedef StridedData<lno_t, scalar_t> input_t;
83 #endif
84 
86  // Constructors for each Adapter type
88 
89  // VectorAdapter
90  CoordinateModel(const RCP<const VectorAdapter<user_t> > &ia,
91  const RCP<const Environment> &env,
92  const RCP<const Comm<int> > &comm,
93  modelFlag_t &flags):
94  numGlobalCoordinates_(), env_(env), comm_(comm),
95  coordinateDim_(), gids_(),
96  xyz_(), userNumWeights_(0), weights_()
97  {
98  this->ia_ = ia;
99  typedef VectorAdapter<user_t> adapterWithCoords_t;
100  sharedConstructor<adapterWithCoords_t>(&(*ia), env, comm, flags);
101  }
102 
103  // MatrixAdapter
105  const RCP<const Environment> &env,
106  const RCP<const Comm<int> > &comm,
107  modelFlag_t &flags) :
108  numGlobalCoordinates_(), env_(env), comm_(comm),
109  coordinateDim_(), gids_(),
110  xyz_(), userNumWeights_(0), weights_()
111  {
112  if (!(ia->coordinatesAvailable()))
113  throw std::logic_error("No coordinate info provided to MatrixAdapter.");
114  else {
115  this->ia_ = ia;
116  typedef VectorAdapter<userCoord_t> adapterWithCoords_t;
117  adapterWithCoords_t *va = ia->getCoordinateInput();
118  // this->ia = va;
119  sharedConstructor<adapterWithCoords_t>(va, env, comm, flags);
120  }
121  }
122 
123  // GraphAdapter
125  const RCP<const Environment> &env,
126  const RCP<const Comm<int> > &comm,
127  modelFlag_t &flags) :
128  numGlobalCoordinates_(), env_(env), comm_(comm),
129  coordinateDim_(), gids_(),
130  xyz_(), userNumWeights_(0), weights_()
131  {
132  if (!(ia->coordinatesAvailable()))
133  throw std::logic_error("No coordinate info provided to GraphAdapter.");
134  else {
135  this->ia_ = ia;
136  typedef VectorAdapter<userCoord_t> adapterWithCoords_t;
137  adapterWithCoords_t *va = ia->getCoordinateInput();
138 
139  sharedConstructor<adapterWithCoords_t>(va, env, comm, flags);
140  }
141  }
142 
143  // MeshAdapter
144  CoordinateModel(const RCP<const MeshAdapter<user_t> > &ia,
145  const RCP<const Environment> &env,
146  const RCP<const Comm<int> > &comm,
147  modelFlag_t &flags) :
148  numGlobalCoordinates_(), env_(env), comm_(comm),
149  coordinateDim_(), gids_(),
150  xyz_(), userNumWeights_(0), weights_()
151  {
152  this->ia_ = ia;
153  typedef MeshAdapter<user_t> adapterWithCoords_t;
154  sharedConstructor<adapterWithCoords_t>(&(*ia), env, comm, flags);
155  }
156 
157  // IdentifierAdapter
159  const RCP<const Environment> &env,
160  const RCP<const Comm<int> > &comm,
161  modelFlag_t &flags)
162  {
163  throw std::logic_error(
164  "A coordinate model can not be build from an IdentifierAdapter");
165  }
166 
168  // CoordinateModel interface.
170 
173  int getCoordinateDim() const { return coordinateDim_;}
174 
177  size_t getLocalNumCoordinates() const { return gids_.size();}
178 
181  global_size_t getGlobalNumCoordinates() const {return numGlobalCoordinates_;}
182 
185  int getNumWeightsPerCoordinate() const { return userNumWeights_;}
186 
209  size_t getCoordinates(ArrayView<const gno_t> &Ids,
210  ArrayView<input_t> &xyz,
211  ArrayView<input_t> &wgts) const
212  {
213  xyz = xyz_.view(0, coordinateDim_);
214  wgts = weights_.view(0, userNumWeights_);
215 
216  size_t nCoord = getLocalNumCoordinates();
217  Ids = ArrayView<const gno_t>();
218 
219  if (nCoord){
220  Ids = Teuchos::arrayView<const gno_t>(
221  reinterpret_cast<const gno_t *>(gids_.getRawPtr()), nCoord);
222  }
223 
224  return nCoord;
225  }
226 
235  Kokkos::View<const gno_t *, typename node_t::device_type> &Ids,
236  // coordinates in MJ are LayoutLeft since Tpetra Multivector gives LayoutLeft
237  Kokkos::View<scalar_t **,
238  Kokkos::LayoutLeft, typename node_t::device_type> &xyz,
239  Kokkos::View<scalar_t **, typename node_t::device_type> &wgts) const
240  {
241  const auto type = ia_->adapterType();
242 
243  if (type == VectorAdapterType or type == MeshAdapterType)
244  {
245  auto adapterWithCoords = dynamic_cast<const AdapterWithCoords<user_t>*>(&(*ia_));
246  adapterWithCoords->getCoordinatesKokkosView(xyz);
247  }
248  else if (type == MatrixAdapterType or type == GraphAdapterType)
249  {
250  auto wrapper = dynamic_cast<const AdapterWithCoordsWrapper<user_t, userCoord_t>*>(&(*ia_));
252  }
253 
254  ia_->getIDsKokkosView(Ids);
255 
256  if(userNumWeights_ > 0) {
257  ia_->getWeightsKokkosView(wgts);
258  }
259 
260  return getLocalNumCoordinates();
261  }
262 
264  // The Model interface.
266 
267  size_t getLocalNumObjects() const
268  {
269  return getLocalNumCoordinates();
270  }
271 
272  size_t getGlobalNumObjects() const
273  {
274  return getGlobalNumCoordinates();
275  }
276 
277 private:
278  RCP<const BaseAdapter<user_t>> ia_;
279 
280  size_t numGlobalCoordinates_;
281  const RCP<const Environment> env_;
282  const RCP<const Comm<int> > comm_;
283  int coordinateDim_;
284 
285  ArrayRCP<const gno_t> gids_;
286  ArrayRCP<input_t> xyz_;
287  int userNumWeights_;
288  ArrayRCP<input_t> weights_;
289 
290  template <typename AdapterWithCoords_>
291  void sharedConstructor(const AdapterWithCoords_ *ia,
292  const RCP<const Environment> &env,
293  const RCP<const Comm<int> > &comm,
294  modelFlag_t &flags);
295 
296 };
297 
298 
300 
301 // sharedConstructor
302 template <typename Adapter>
303 template <typename AdapterWithCoords_>
304 void CoordinateModel<Adapter>::sharedConstructor(
305  const AdapterWithCoords_ *ia,
306  const RCP<const Environment> &/* env */,
307  const RCP<const Comm<int> > &comm,
308  modelFlag_t &/* flags */)
309 {
310  size_t nLocalIds = ia_->getLocalNumIDs();
311 
312  // Get coordinates and weights (if any)
313 
314  int tmp[2], gtmp[2];
315  tmp[0] = ia->getDimension();
316  tmp[1] = ia->getNumWeightsPerID();
317  Teuchos::reduceAll<int, int>(*comm, Teuchos::REDUCE_MAX, 2, tmp, gtmp);
318  coordinateDim_ = gtmp[0];
319  userNumWeights_ = gtmp[1];
320 
321  env_->localBugAssertion(__FILE__, __LINE__, "coordinate dimension",
322  coordinateDim_ > 0, COMPLEX_ASSERTION);
323 
324  input_t *coordArray = new input_t [coordinateDim_];
325  input_t *weightArray = NULL;
326  if (userNumWeights_)
327  weightArray = new input_t [userNumWeights_];
328 
329  env_->localMemoryAssertion(__FILE__, __LINE__, userNumWeights_+coordinateDim_,
330  coordArray && (!userNumWeights_|| weightArray));
331 
332 
333  if (nLocalIds){
334  const gno_t *gids=NULL;
335 
336  ia->getIDsView(gids);
337  gids_ = arcp(gids, 0, nLocalIds, false);
338 
339  for (int dim=0; dim < coordinateDim_; dim++){
340  int stride;
341  const scalar_t *coords=NULL;
342  try{
343  ia->getCoordinatesView(coords, stride, dim);
344  }
346 
347  ArrayRCP<const scalar_t> cArray(coords, 0, nLocalIds*stride, false);
348  coordArray[dim] = input_t(cArray, stride);
349  }
350 
351  for (int idx=0; idx < userNumWeights_; idx++){
352  int stride;
353  const scalar_t *weights;
354  try{
355  ia->getWeightsView(weights, stride, idx);
356  }
358 
359  ArrayRCP<const scalar_t> wArray(weights, 0, nLocalIds*stride, false);
360  weightArray[idx] = input_t(wArray, stride);
361  }
362  }
363 
364  xyz_ = arcp(coordArray, 0, coordinateDim_);
365 
366  if (userNumWeights_)
367  weights_ = arcp(weightArray, 0, userNumWeights_);
368 
369  Teuchos::reduceAll<int, size_t>(*comm, Teuchos::REDUCE_SUM, 1,
370  &nLocalIds, &numGlobalCoordinates_);
371 
372  env_->memory("After construction of coordinate model");
373 }
374 
375 } // namespace Zoltan2
376 
377 #endif
virtual VectorAdapter< UserCoord > * getCoordinateInput() const =0
global_size_t getGlobalNumCoordinates() const
Returns the global number coordinates.
IdentifierAdapter defines the interface for identifiers.
CoordinateModel(const RCP< const MatrixAdapter< user_t, userCoord_t > > &ia, const RCP< const Environment > &env, const RCP< const Comm< int > > &comm, modelFlag_t &flags)
#define Z2_FORWARD_EXCEPTIONS
Forward an exception back through call stack.
CoordinateModel(const RCP< const MeshAdapter< user_t > > &ia, const RCP< const Environment > &env, const RCP< const Comm< int > > &comm, modelFlag_t &flags)
MatrixAdapter defines the adapter interface for matrices.
Defines the Model interface.
static ArrayRCP< ArrayRCP< zscalar_t > > weights
void getCoordinatesKokkosView(typename AdapterWithCoords< User >::CoordsDeviceView &elements) const override
GraphAdapter defines the interface for graph-based user data.
Defines the MeshAdapter interface.
MeshAdapter defines the interface for mesh input.
more involved, like validate a graph
std::bitset< NUM_MODEL_FLAGS > modelFlag_t
map_t::global_ordinal_type gno_t
Definition: mapRemotes.cpp:18
Defines the IdentifierAdapter interface.
Defines the VectorAdapter interface.
typename Zoltan2::InputTraits< ztcrsmatrix_t >::node_t node_t
This class provides geometric coordinates with optional weights to the Zoltan2 algorithm.
size_t getCoordinates(ArrayView< const gno_t > &Ids, ArrayView< input_t > &xyz, ArrayView< input_t > &wgts) const
Returns the coordinate ids, values and optional weights.
CoordinateModel(const RCP< const GraphAdapter< user_t, userCoord_t > > &ia, const RCP< const Environment > &env, const RCP< const Comm< int > > &comm, modelFlag_t &flags)
size_t getCoordinatesKokkos(Kokkos::View< const gno_t *, typename node_t::device_type > &Ids, Kokkos::View< scalar_t **, Kokkos::LayoutLeft, typename node_t::device_type > &xyz, Kokkos::View< scalar_t **, typename node_t::device_type > &wgts) const
Returns the coordinate ids, values and optional weights.
VectorAdapter defines the interface for vector input.
size_t getLocalNumObjects() const
Return the local number of objects.
The StridedData class manages lists of weights or coordinates.
size_t getGlobalNumObjects() const
Return the global number of objects.
map_t::local_ordinal_type lno_t
Definition: mapRemotes.cpp:17
size_t getLocalNumCoordinates() const
Returns the number of coordinates on this process.
int getNumWeightsPerCoordinate() const
Returns the number (0 or greater) of weights per coordinate.
Defines the MatrixAdapter interface.
The base class for all model classes.
Tpetra::global_size_t global_size_t
CoordinateModel(const RCP< const VectorAdapter< user_t > > &ia, const RCP< const Environment > &env, const RCP< const Comm< int > > &comm, modelFlag_t &flags)
Defines the GraphAdapter interface.
int getCoordinateDim() const
Returns the dimension of the coordinates.
virtual void getCoordinatesKokkosView(CoordsDeviceView &elements) const =0
CoordinateModel(const RCP< const IdentifierAdapter< user_t > > &ia, const RCP< const Environment > &env, const RCP< const Comm< int > > &comm, modelFlag_t &flags)
This file defines the StridedData class.
Zoltan2::BasicUserTypes< zscalar_t, zlno_t, zgno_t > user_t
Definition: Metric.cpp:74