MADNESS  0.10.1
cloud.h
Go to the documentation of this file.
1 
2 /**
3  \file cloud.h
4  \brief Declares the \c Cloud class for storing data and transfering them between worlds
5  \ingroup world
6 
7 */
8 
9 /**
10  * TODO: - delete container record upon caching if container is replicated
11  * - set read-only option upon replicating
12  */
13 
14 #ifndef SRC_MADNESS_WORLD_CLOUD_H_
15 #define SRC_MADNESS_WORLD_CLOUD_H_
16 
17 
19 #include<any>
20 #include<iomanip>
21 
22 
23 /*!
24  \file cloud.h
25  \brief Defines and implements most of madness cloud storage
26 
27  TODO: check use of preprocessor directives
28  TODO: clear cache in destructor won't work because no subworld is present -> must be explicitly called, error prone/
29 */
30 
31 namespace madness {
32 
33 template<typename keyT>
34 struct Recordlist {
35  std::list<keyT> list;
36 
37  Recordlist() : list() {};
38 
39  explicit Recordlist(const keyT &key) : list{key} {};
40 
41  Recordlist(const Recordlist &other) : list(other.list) {};
42 
43  Recordlist &operator+=(const Recordlist &list2) {
44  for (auto &l2 : list2.list) list.push_back(l2);
45  return *this;
46  }
47 
48  Recordlist &operator+=(const keyT &key) {
49  list.push_back(key);
50  return *this;
51  }
52 
54  keyT key = list.front();
55  list.pop_front();
56  return key;
57  }
58 
59  std::size_t size() const {
60  return list.size();
61  }
62 
63  // if type provides id() member function (i.e. WorldObject) use that for hashing, otherwise use hash_value() for
64  // fundamental types (see worldhash.h)
65  template <typename T>
66  using member_id_t = decltype(std::declval<T>().id());
67 
68  template <typename T>
70 
71  // if type provides a hashing function use that, intrusive hashing, see worldhash.h
72  template <typename T>
73  using member_hash_t = decltype(std::declval<T>().hash());
74 
75  template <typename T>
77 
78  template<typename T, std::size_t NDIM>
79  static keyT compute_record(const Function<T,NDIM>& arg) {return hash_value(arg.get_impl()->id());}
80 
81  template<typename T, std::size_t NDIM>
82  static keyT compute_record(const FunctionImpl<T,NDIM>* arg) {return hash_value(arg->id());}
83 
84  template<typename keyQ, typename valueT>
85  static keyT compute_record(const WorldContainer<keyQ,valueT>& arg) {return hash_value(arg.id());}
86 
87  template<typename keyQ, typename valueT>
88  static keyT compute_record(const std::shared_ptr<WorldContainer<keyQ,valueT>>& arg) {return hash_value(arg->id());}
89 
90  template<typename T, std::size_t NDIM>
91  static keyT compute_record(const std::shared_ptr<madness::FunctionImpl<T, NDIM>>& arg) {return hash_value(arg->id());}
92 
93  template<typename T>
94  static keyT compute_record(const std::vector<T>& arg) {return hash_range(arg.begin(), arg.end());}
95 
96  template<typename T>
97  static keyT compute_record(const Tensor<T>& arg) {return hash_value(arg.normf());}
98 
99  template<typename T>
100  static keyT compute_record(const std::shared_ptr<T>& arg) {return compute_record(*arg);}
101 
102  template<typename T>
103  static keyT compute_record(const T& arg) {
104  if constexpr (has_member_id<T>::value) {
105  return hash_value(arg.id());
106  } else if constexpr (std::is_pointer_v<T> && has_member_id<std::remove_pointer_t<T>>::value) {
107  return hash_value(arg->id());
108  } else {
109  // compute hash_code for fundamental types
110  std::size_t hashtype = typeid(T).hash_code();
111  hash_combine(hashtype,hash_value(arg));
112  return hashtype;
113  }
114  }
115 
116 
117  friend std::ostream &operator<<(std::ostream &os, const Recordlist &arg) {
118  using namespace madness::operators;
119  os << arg.list;
120  return os;
121  }
122 
123 };
124 
125 /// cloud class
126 
127 /// store and load data to/from the cloud into arbitrary worlds
128 ///
129 /// Distributed data is always bound to a certain world. If it needs to be
130 /// present in another world it can be serialized to the cloud and deserialized
131 /// from there again. For an example see test_cloud.cc
132 ///
133 /// Data is stored into a distributed container living in the universe.
134 /// During storing a (replicated) list of records is returned that can be used to find the data
135 /// in the container. If a combined object (a vector, tuple, etc) is stored a list of records
136 /// will be generated. When loading the data from the world the record list will be used to
137 /// deserialize all stored objects.
138 ///
139 /// Note that there must be a fence after the destruction of subworld containers, as in:
140 ///
141 /// create subworlds
142 /// {
143 /// dcT(subworld)
144 /// do work
145 /// }
146 /// subworld.gop.fence();
147 class Cloud {
148 
149  bool debug = false; ///< prints debug output
150  bool is_replicated=false; ///< if contents of the container are replicated
151  bool dofence = true; ///< fences after load/store
152  bool force_load_from_cache = false; ///< forces load from cache (mainly for debugging)
153 
154 public:
155 
156  typedef std::any cached_objT;
158  using valueT = std::vector<unsigned char>;
159  typedef std::map<keyT, cached_objT> cacheT;
161 
162 private:
165  recordlistT local_list_of_container_keys; // a world-local list of keys occupied in container
166 
167 public:
168  template <typename T>
169  using member_cloud_serialize_t = decltype(std::declval<T>().cloud_store(std::declval<World&>(), std::declval<Cloud&>()));
170 
171  template <typename T>
173 
174 public:
175 
176  /// @param[in] universe the universe world
177  Cloud(madness::World &universe) : container(universe), reading_time(0l), writing_time(0l),
178  cache_reads(0l), cache_stores(0l) {
179  }
180 
181  void set_debug(bool value) {
182  debug = value;
183  }
184 
185  void set_fence(bool value) {
186  dofence = value;
187  }
188 
189  void set_force_load_from_cache(bool value) {
190  force_load_from_cache = value;
191  }
192 
193  void print_size(World& universe) {
194 
195  std::size_t memsize=0;
196  std::size_t max_record_size=0;
197  for (auto& item : container) {
198  memsize+=item.second.size();
199  max_record_size=std::max(max_record_size,item.second.size());
200  }
201  std::size_t global_memsize=memsize;
202  std::size_t max_memsize=memsize;
203  std::size_t min_memsize=memsize;
204  universe.gop.sum(global_memsize);
205  universe.gop.max(max_memsize);
206  universe.gop.max(max_record_size);
207  universe.gop.min(min_memsize);
208 
209  auto local_size=container.size();
210  auto global_size=local_size;
211  universe.gop.sum(global_size);
212  double byte2gbyte=1.0/(1024*1024*1024);
213 
214  if (universe.rank()==0) {
215  print("Cloud memory:");
216  print(" replicated:",is_replicated);
217  print("size of cloud (total)");
218  print(" number of records: ",global_size);
219  print(" memory in GBytes: ",global_memsize*byte2gbyte);
220  print("size of cloud (average per node)");
221  print(" number of records: ",double(global_size)/universe.size());
222  print(" memory in GBytes: ",global_memsize*byte2gbyte/universe.size());
223  print("min/max of node");
224  print(" memory in GBytes: ",min_memsize*byte2gbyte,max_memsize*byte2gbyte);
225  print(" max record size in GBytes:",max_record_size*byte2gbyte);
226 
227  }
228  }
229 
230  void print_timings(World &universe) const {
231  double rtime = double(reading_time);
232  double wtime = double(writing_time);
233  double ptime = double(replication_time);
234  universe.gop.sum(rtime);
235  universe.gop.sum(wtime);
236  universe.gop.sum(ptime);
237  long creads = long(cache_reads);
238  long cstores = long(cache_stores);
239  universe.gop.sum(creads);
240  universe.gop.sum(cstores);
241  if (universe.rank() == 0) {
242  auto precision = std::cout.precision();
243  std::cout << std::fixed << std::setprecision(1);
244  print("cloud storing cpu time", wtime * 0.001);
245  print("cloud replication cpu time", ptime * 0.001);
246  print("cloud reading cpu time", rtime * 0.001, std::defaultfloat);
247  std::cout << std::setprecision(precision) << std::scientific;
248  print("cloud cache stores ", long(cstores));
249  print("cloud cache loads ", long(creads));
250  }
251  }
252  void clear_cache(World &subworld) {
253  cached_objects.clear();
254  local_list_of_container_keys.list.clear();
255  subworld.gop.fence();
256  }
257 
258  void clear() {
259  container.clear();
260  }
261 
262  void clear_timings() {
263  reading_time=0l;
264  writing_time=0l;
265  writing_time1=0l;
266  replication_time=0l;
267  cache_stores=0l;
268  cache_reads=0l;
269  }
270 
271  /// @param[in] world the subworld the objects are loaded to
272  /// @param[in] recordlist the list of records where the objects are stored
273  template<typename T>
274  T load(madness::World &world, const recordlistT recordlist) const {
275  recordlistT rlist = recordlist;
276  cloudtimer t(world, reading_time);
277 
278  // forward_load will consume the recordlist while loading elements
279  return forward_load<T>(world, rlist);
280  }
281 
282  /// load a single object from the cloud, recordlist is consumed while loading elements
283  template<typename T>
284  T forward_load(madness::World &world, recordlistT& recordlist) const {
285  // different objects are stored in different ways
286  // - tuples are split up into their components
287  // - classes with their own cloud serialization are stored using that
288  // - everything else is stored using their usual serialization
289  if constexpr (is_tuple<T>::value) {
290  return load_tuple<T>(world, recordlist);
291  } else if constexpr (has_cloud_serialize<T>::value) {
292  T target = allocator<T>(world);
293  target.cloud_load(world, *this, recordlist);
294  return target;
295  } else {
296  return do_load<T>(world, recordlist);
297  }
298  }
299 
300  /// @param[in] world presumably the universe
301  template<typename T>
303  if (is_replicated) {
304  print("Cloud contents are replicated and read-only!");
305  MADNESS_EXCEPTION("cloud error",1);
306  }
307  cloudtimer t(world,writing_time);
308 
309  // different objects are stored in different ways
310  // - tuples are split up into their components
311  // - classes with their own cloud serialization are stored using that
312  // - everything else is stored using their usual serialization
313  recordlistT recordlist;
314  if constexpr (is_tuple<T>::value) {
315  recordlist+=store_tuple(world,source);
316  } else if constexpr (has_cloud_serialize<T>::value) {
317  recordlist+=source.cloud_store(world,*this);
318  } else {
319  recordlist+=store_other(world,source);
320  }
321  if (dofence) world.gop.fence();
322  return recordlist;
323  }
324 
325  void replicate(const std::size_t chunk_size=INT_MAX) {
326 
327  World& world=container.get_world();
328  world.gop.fence();
329  cloudtimer t(world,replication_time);
330  container.reset_pmap_to_local();
331  is_replicated=true;
332 
333  std::list<keyT> keylist;
334  for (auto it=container.begin(); it!=container.end(); ++it) {
335  keylist.push_back(it->first);
336  }
337 
338  for (ProcessID rank=0; rank<world.size(); rank++) {
339  if (rank == world.rank()) {
340  std::size_t keylistsize = keylist.size();
341  world.mpi.Bcast(&keylistsize,sizeof(keylistsize),MPI_BYTE,rank);
342 
343  for (auto key : keylist) {
345  bool found=container.find(acc,key);
346  MADNESS_CHECK(found);
347  auto data = acc->second;
348  std::size_t sz=data.size();
349 
350  world.mpi.Bcast(&key,sizeof(key),MPI_BYTE,rank);
351  world.mpi.Bcast(&sz,sizeof(sz),MPI_BYTE,rank);
352 
353  // if data is too large for MPI_INT break it into pieces to avoid integer overflow
354  for (std::size_t start=0; start<sz; start+=chunk_size) {
355  std::size_t remainder = std::min(sz - start, chunk_size);
356  world.mpi.Bcast(&data[start], remainder, MPI_BYTE, rank);
357  }
358 
359  }
360  }
361  else {
362  std::size_t keylistsize;
363  world.mpi.Bcast(&keylistsize,sizeof(keylistsize),MPI_BYTE,rank);
364  for (size_t i=0; i<keylistsize; i++) {
365  keyT key;
366  world.mpi.Bcast(&key,sizeof(key),MPI_BYTE,rank);
367  std::size_t sz;
368  world.mpi.Bcast(&sz,sizeof(sz),MPI_BYTE,rank);
369  valueT data(sz);
370 // world.mpi.Bcast(&data[0],sz,MPI_BYTE,rank);
371  for (std::size_t start=0; start<sz; start+=chunk_size) {
372  std::size_t remainder=std::min(sz-start,chunk_size);
373  world.mpi.Bcast(&data[start],remainder,MPI_BYTE,rank);
374  }
375 
376  container.replace(key,data);
377  }
378  }
379  }
380  world.gop.fence();
381  }
382 
383 private:
384 
385  mutable std::atomic<long> reading_time=0l; // in ms
386  mutable std::atomic<long> writing_time=0l; // in ms
387  mutable std::atomic<long> writing_time1=0l; // in ms
388  mutable std::atomic<long> replication_time=0l; // in ms
389  mutable std::atomic<long> cache_reads=0l;
390  mutable std::atomic<long> cache_stores=0l;
391 
392  template<typename> struct is_tuple : std::false_type { };
393  template<typename ...T> struct is_tuple<std::tuple<T...>> : std::true_type { };
394 
395  template<typename Q> struct is_vector : std::false_type { };
396  template<typename Q> struct is_vector<std::vector<Q>> : std::true_type { };
397 
398  template<typename>
399  struct is_madness_function_vector : std::false_type {
400  };
401  template<typename T, std::size_t NDIM>
402  struct is_madness_function_vector<std::vector<Function<T, NDIM>>> : std::true_type {
403  };
404 
405  template<typename T> using is_parallel_serializable_object = std::is_base_of<archive::ParallelSerializableObject,T>;
406 
407  template<typename T> using is_world_constructible = std::is_constructible<T, World &>;
408 
409  struct cloudtimer {
411  double wall0;
412  std::atomic<long> &rtime;
413 
414  cloudtimer(World& world, std::atomic<long> &readtime) : world(world), wall0(wall_time()), rtime(readtime) {}
415 
417  long deltatime=long((wall_time() - wall0) * 1000l);
418  rtime += deltatime;
419  }
420  };
421 
422  template<typename T>
423  void cache(madness::World &world, const T &obj, const keyT &record) const {
424  const_cast<cacheT &>(cached_objects).insert({record,std::make_any<T>(obj)});
425  }
426 
427  /// load an object from the cache, record is unchanged
428  template<typename T>
429  T load_from_cache(madness::World &world, const keyT &record) const {
430  if (world.rank()==0) cache_reads++;
431  if (debug) print("loading", typeid(T).name(), "from cache record", record, "to world", world.id());
432  if (auto obj = std::any_cast<T>(&cached_objects.find(record)->second)) return *obj;
433  MADNESS_EXCEPTION("failed to load from cloud-cache", 1);
434  T target = allocator<T>(world);
435  return target;
436  }
437 
438  bool is_cached(const keyT &key) const {
439  return (cached_objects.count(key) == 1);
440  }
441 
442  /// checks if a (universe) container record is used
443 
444  /// currently implemented with a local copy of the recordlist, might be
445  /// reimplemented with container.find(), which would include blocking communication.
446  bool is_in_container(const keyT &key) const {
447  auto it = std::find(local_list_of_container_keys.list.begin(),
448  local_list_of_container_keys.list.end(), key);
449  return it!=local_list_of_container_keys.list.end();
450  }
451 
452  template<typename T>
453  T allocator(World &world) const {
454  if constexpr (is_world_constructible<T>::value) {
455  return T(world);
456  } else {
457  return T();
458  }
459  }
460 
461  template<typename T>
464  bool is_already_present= is_in_container(record);
465  if (debug) {
466  if (is_already_present) std::cout << "skipping ";
468  std::cout << "storing world object of " << typeid(T).name() << "id " << source.id() << " to record " << record << std::endl;
469  }
470  std::cout << "storing object of " << typeid(T).name() << " to record " << record << std::endl;
471  }
472 
473  // scope is important because of destruction ordering of world objects and fence
474  if (is_already_present) {
475  if (world.rank()==0) cache_stores++;
476  } else {
477  cloudtimer t(world,writing_time1);
478  madness::archive::ContainerRecordOutputArchive ar(world, container, record);
480  par & source;
481  local_list_of_container_keys+=record;
482  }
483  if (dofence) world.gop.fence();
484  return recordlistT{record};
485  }
486 
487 public:
488  /// load a vector from the cloud, pop records from recordlist
489  ///
490  /// @param[inout] world destination world
491  /// @param[inout] recordlist list of records to load from (reduced by the first few elements)
492  template<typename T>
493  typename std::enable_if<is_vector<T>::value, T>::type
494  do_load(World &world, recordlistT &recordlist) const {
495  std::size_t sz = do_load<std::size_t>(world, recordlist);
496  T target(sz);
497  for (std::size_t i = 0; i < sz; ++i) {
498  target[i] = do_load<typename T::value_type>(world, recordlist);
499  }
500  return target;
501  }
502 
503  /// load a single object from the cloud, pop record from recordlist
504  ///
505  /// @param[inout] world destination world
506  /// @param[inout] recordlist list of records to load from (reduced by the first element)
507  template<typename T>
508  typename std::enable_if<!is_vector<T>::value, T>::type
509  do_load(World &world, recordlistT &recordlist) const {
510  keyT record = recordlist.pop_front_and_return();
511  if (force_load_from_cache) MADNESS_CHECK(is_cached(record));
512 
513  if (is_cached(record)) return load_from_cache<T>(world, record);
514  if (debug) print("loading", typeid(T).name(), "from container record", record, "to world", world.id());
515  T target = allocator<T>(world);
516  madness::archive::ContainerRecordInputArchive ar(world, container, record);
518  par & target;
519  cache(world, target, record);
520  return target;
521  }
522 
523 public:
524 
525  // overloaded
526  template<typename T>
527  recordlistT store_other(madness::World& world, const std::vector<T>& source) {
528  if (debug)
529  std::cout << "storing " << typeid(source).name() << " of size " << source.size() << std::endl;
530  recordlistT l = store_other(world, source.size());
531  for (const auto& s : source) l += store_other(world, s);
532  if (dofence) world.gop.fence();
533  if (debug) std::cout << "done with vector storing; container size " << container.size() << std::endl;
534  return l;
535  }
536 
537  /// store a tuple in multiple records
538  template<typename... Ts>
539  recordlistT store_tuple(World &world, const std::tuple<Ts...> &input) {
540  recordlistT v;
541  auto storeaway = [&](const auto &arg) {
542  v += this->store(world, arg);
543  };
544  auto l = [&](Ts const &... arg) {
545  ((storeaway(arg)), ...);
546  };
547  std::apply(l, input);
548  return v;
549  }
550 
551  /// load a tuple from the cloud, pop records from recordlist
552  ///
553  /// @param[inout] world destination world
554  /// @param[inout] recordlist list of records to load from (reduced by the first few elements)
555  template<typename T>
556  T load_tuple(madness::World &world, recordlistT &recordlist) const {
557  if (debug) std::cout << "loading tuple of type " << typeid(T).name() << " to world " << world.id() << std::endl;
558  T target;
559  std::apply([&](auto &&... args) {
560  ((args = forward_load<typename std::remove_reference<decltype(args)>::type>(world, recordlist)), ...);
561  }, target);
562  return target;
563  }
564 };
565 
566 } /* namespace madness */
567 
568 #endif /* SRC_MADNESS_WORLD_CLOUD_H_ */
cloud class
Definition: cloud.h:147
bool is_cached(const keyT &key) const
Definition: cloud.h:438
void clear()
Definition: cloud.h:258
bool is_in_container(const keyT &key) const
checks if a (universe) container record is used
Definition: cloud.h:446
recordlistT store_other(madness::World &world, const std::vector< T > &source)
Definition: cloud.h:527
std::any cached_objT
Definition: cloud.h:156
recordlistT store(madness::World &world, const T &source)
Definition: cloud.h:302
T load_tuple(madness::World &world, recordlistT &recordlist) const
Definition: cloud.h:556
std::is_base_of< archive::ParallelSerializableObject, T > is_parallel_serializable_object
Definition: cloud.h:405
madness::archive::ContainerRecordOutputArchive::keyT keyT
Definition: cloud.h:157
Recordlist< keyT > recordlistT
Definition: cloud.h:160
std::is_constructible< T, World & > is_world_constructible
Definition: cloud.h:407
recordlistT store_other(madness::World &world, const T &source)
Definition: cloud.h:462
void set_force_load_from_cache(bool value)
Definition: cloud.h:189
decltype(std::declval< T >().cloud_store(std::declval< World & >(), std::declval< Cloud & >())) member_cloud_serialize_t
Definition: cloud.h:169
void replicate(const std::size_t chunk_size=INT_MAX)
Definition: cloud.h:325
recordlistT local_list_of_container_keys
Definition: cloud.h:165
void print_size(World &universe)
Definition: cloud.h:193
std::enable_if< is_vector< T >::value, T >::type do_load(World &world, recordlistT &recordlist) const
Definition: cloud.h:494
void clear_timings()
Definition: cloud.h:262
recordlistT store_tuple(World &world, const std::tuple< Ts... > &input)
store a tuple in multiple records
Definition: cloud.h:539
void set_debug(bool value)
Definition: cloud.h:181
T load(madness::World &world, const recordlistT recordlist) const
Definition: cloud.h:274
void cache(madness::World &world, const T &obj, const keyT &record) const
Definition: cloud.h:423
void set_fence(bool value)
Definition: cloud.h:185
Cloud(madness::World &universe)
Definition: cloud.h:177
cacheT cached_objects
Definition: cloud.h:164
void clear_cache(World &subworld)
Definition: cloud.h:252
T load_from_cache(madness::World &world, const keyT &record) const
load an object from the cache, record is unchanged
Definition: cloud.h:429
madness::meta::is_detected< member_cloud_serialize_t, T > has_cloud_serialize
Definition: cloud.h:172
std::vector< unsigned char > valueT
Definition: cloud.h:158
void print_timings(World &universe) const
Definition: cloud.h:230
T allocator(World &world) const
Definition: cloud.h:453
madness::WorldContainer< keyT, valueT > container
Definition: cloud.h:163
T forward_load(madness::World &world, recordlistT &recordlist) const
load a single object from the cloud, recordlist is consumed while loading elements
Definition: cloud.h:284
std::map< keyT, cached_objT > cacheT
Definition: cloud.h:159
std::enable_if<!is_vector< T >::value, T >::type do_load(World &world, recordlistT &recordlist) const
Definition: cloud.h:509
FunctionImpl holds all Function state to facilitate shallow copy semantics.
Definition: funcimpl.h:941
A multiresolution adaptive numerical function.
Definition: mra.h:122
A tensor is a multidimension array.
Definition: tensor.h:317
Makes a distributed container with specified attributes.
Definition: worlddc.h:866
bool find(accessor &acc, const keyT &key)
Write access to LOCAL value by key. Returns true if found, false otherwise (always false for remote).
Definition: worlddc.h:987
iterator begin()
Returns an iterator to the beginning of the local data (no communication)
Definition: worlddc.h:1070
void reset_pmap_to_local()
Returns shared pointer to the process mapping.
Definition: worlddc.h:1149
void replace(const pairT &datum)
Inserts/replaces key+value pair (non-blocking communication if key not local)
Definition: worlddc.h:974
iterator end()
Returns an iterator past the end of the local data (no communication)
Definition: worlddc.h:1084
World & get_world() const
Returns the world associated with this container.
Definition: worlddc.h:955
std::size_t size() const
Returns the number of local entries (no communication)
Definition: worlddc.h:1135
void clear()
Clears all local data (no communication)
Definition: worlddc.h:1128
void max(T *buf, size_t nelem)
Inplace global max while still processing AM & tasks.
Definition: worldgop.h:882
void fence(bool debug=false)
Synchronizes all processes in communicator AND globally ensures no pending AM or tasks.
Definition: worldgop.cc:161
void min(T *buf, size_t nelem)
Inplace global min while still processing AM & tasks.
Definition: worldgop.h:876
void sum(T *buf, size_t nelem)
Inplace global sum while still processing AM & tasks.
Definition: worldgop.h:870
void Bcast(T *buffer, int count, int root) const
MPI broadcast an array of count elements.
Definition: worldmpi.h:416
A parallel world class.
Definition: world.h:132
ProcessID rank() const
Returns the process rank in this World (same as MPI_Comm_rank()).
Definition: world.h:318
WorldMpiInterface & mpi
MPI interface.
Definition: world.h:202
ProcessID size() const
Returns the number of processes in this World (same as MPI_Comm_size()).
Definition: world.h:328
unsigned long id() const
Definition: world.h:313
WorldGopInterface & gop
Global operations.
Definition: world.h:205
Definition: parallel_dc_archive.h:60
Definition: parallel_dc_archive.h:14
long keyT
Definition: parallel_dc_archive.h:16
An archive for storing local or parallel data, wrapping a BinaryFstreamInputArchive.
Definition: parallel_archive.h:366
An archive for storing local or parallel data wrapping a BinaryFstreamOutputArchive.
Definition: parallel_archive.h:321
static bool debug
Definition: dirac-hatom.cc:16
Fcwf apply(World &world, real_convolution_3d &op, const Fcwf &psi)
Definition: fcwf.cc:281
auto T(World &world, response_space &f) -> response_space
Definition: global_functions.cc:34
Tensor< typename Tensor< T >::scalar_type > arg(const Tensor< T > &t)
Return a new tensor holding the argument of each element of t (complex types only)
Definition: tensor.h:2502
static const double v
Definition: hatom_sf_dirac.cc:20
#define max(a, b)
Definition: lda.h:51
#define MADNESS_CHECK(condition)
Check a condition — even in a release build the condition is always evaluated so it can have side eff...
Definition: madness_exception.h:190
#define MADNESS_EXCEPTION(msg, value)
Macro for throwing a MADNESS exception.
Definition: madness_exception.h:119
typename detail::detector< nonesuch, void, Op, Args... >::value_t is_detected
Definition: meta.h:169
Definition: array_addons.h:50
File holds all helper structures necessary for the CC_Operator and CC2 class.
Definition: DFParameters.h:10
void hash_range(hashT &seed, It first, It last)
Definition: worldhash.h:280
void hash_combine(hashT &seed, const T &v)
Combine hash values.
Definition: worldhash.h:260
static class madness::twoscale_cache_class cache[kmax+1]
void print(const T &t, const Ts &... ts)
Print items to std::cout (items separated by spaces) and terminate with a new line.
Definition: print.h:225
double wall_time()
Returns the wall time in seconds relative to an arbitrary origin.
Definition: timers.cc:48
std::string type(const PairType &n)
Definition: PNOParameters.h:18
std::string name(const FuncType &type, const int ex=-1)
Definition: ccpairfunction.h:28
madness::hashT hash_value(const std::array< T, N > &a)
Hash std::array with madness hash.
Definition: array_addons.h:78
Definition: mraimpl.h:50
Definition: hatom_sf_dirac.cc:91
Definition: test_ccpairfunction.cc:22
Definition: cloud.h:409
std::atomic< long > & rtime
Definition: cloud.h:412
World & world
Definition: cloud.h:410
double wall0
Definition: cloud.h:411
~cloudtimer()
Definition: cloud.h:416
cloudtimer(World &world, std::atomic< long > &readtime)
Definition: cloud.h:414
Definition: cloud.h:392
Definition: cloud.h:395
Definition: cloud.h:34
static keyT compute_record(const std::vector< T > &arg)
Definition: cloud.h:94
keyT pop_front_and_return()
Definition: cloud.h:53
static keyT compute_record(const Function< T, NDIM > &arg)
Definition: cloud.h:79
friend std::ostream & operator<<(std::ostream &os, const Recordlist &arg)
Definition: cloud.h:117
Recordlist(const Recordlist &other)
Definition: cloud.h:41
Recordlist(const keyT &key)
Definition: cloud.h:39
static keyT compute_record(const std::shared_ptr< T > &arg)
Definition: cloud.h:100
Recordlist & operator+=(const Recordlist &list2)
Definition: cloud.h:43
static keyT compute_record(const T &arg)
Definition: cloud.h:103
std::size_t size() const
Definition: cloud.h:59
madness::meta::is_detected< member_id_t, T > has_member_id
Definition: cloud.h:69
decltype(std::declval< T >().id()) member_id_t
Definition: cloud.h:66
static keyT compute_record(const WorldContainer< keyQ, valueT > &arg)
Definition: cloud.h:85
decltype(std::declval< T >().hash()) member_hash_t
Definition: cloud.h:73
std::list< keyT > list
Definition: cloud.h:35
static keyT compute_record(const FunctionImpl< T, NDIM > *arg)
Definition: cloud.h:82
static keyT compute_record(const std::shared_ptr< WorldContainer< keyQ, valueT >> &arg)
Definition: cloud.h:88
static keyT compute_record(const Tensor< T > &arg)
Definition: cloud.h:97
Recordlist & operator+=(const keyT &key)
Definition: cloud.h:48
madness::meta::is_detected< member_hash_t, T > has_member_hash
Definition: cloud.h:76
static keyT compute_record(const std::shared_ptr< madness::FunctionImpl< T, NDIM >> &arg)
Definition: cloud.h:91
Recordlist()
Definition: cloud.h:37
#define MPI_BYTE
Definition: stubmpi.h:74
double source(const coordT &r)
Definition: testperiodic.cc:48
int ProcessID
Used to clearly identify process number/rank.
Definition: worldtypes.h:43
FLOAT target(const FLOAT &x)
Definition: y.cc:295