/Src/Dependencies/Boost/boost/mpi/collectives.hpp

http://hadesmem.googlecode.com/ · C++ Header · 545 lines · 122 code · 42 blank · 381 comment · 0 complexity · dfb75e994077f14546e04bac39a91815 MD5 · raw file

  1. // Copyright (C) 2005-2006 Douglas Gregor <doug.gregor -at- gmail.com>.
  2. // Use, modification and distribution is subject to the Boost Software
  3. // License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
  4. // http://www.boost.org/LICENSE_1_0.txt)
  5. // Message Passing Interface 1.1 -- Section 4. MPI Collectives
  6. /** @file collectives.hpp
  7. *
  8. * This header contains MPI collective operations, which implement
  9. * various parallel algorithms that require the coordination of all
  10. * processes within a communicator. The header @c collectives_fwd.hpp
  11. * provides forward declarations for each of these operations. To
  12. * include only specific collective algorithms, use the headers @c
  13. * boost/mpi/collectives/algorithm_name.hpp.
  14. */
  15. #ifndef BOOST_MPI_COLLECTIVES_HPP
  16. #define BOOST_MPI_COLLECTIVES_HPP
  17. #include <boost/mpi/communicator.hpp>
  18. #include <vector>
  19. namespace boost { namespace mpi {
  20. /**
  21. * @brief Gather the values stored at every process into vectors of
  22. * values from each process.
  23. *
  24. * @c all_gather is a collective algorithm that collects the values
  25. * stored at each process into a vector of values indexed by the
  26. * process number they came from. The type @c T of the values may be
  27. * any type that is serializable or has an associated MPI data type.
  28. *
  29. * When the type @c T has an associated MPI data type, this routine
  30. * invokes @c MPI_Allgather to gather the values.
  31. *
  32. * @param comm The communicator over which the all-gather will
  33. * occur.
  34. *
  35. * @param in_value The value to be transmitted by each process. To
  36. * gather an array of values, @c in_values points to the @c n local
  37. * values to be transmitted.
  38. *
  39. * @param out_values A vector or pointer to storage that will be
  40. * populated with the values from each process, indexed by the
  41. * process ID number. If it is a vector, the vector will be resized
  42. * accordingly.
  43. */
  44. template<typename T>
  45. void
  46. all_gather(const communicator& comm, const T& in_value,
  47. std::vector<T>& out_values);
  48. /**
  49. * \overload
  50. */
  51. template<typename T>
  52. void
  53. all_gather(const communicator& comm, const T& in_value, T* out_values);
  54. /**
  55. * \overload
  56. */
  57. template<typename T>
  58. void
  59. all_gather(const communicator& comm, const T* in_values, int n,
  60. std::vector<T>& out_values);
  61. /**
  62. * \overload
  63. */
  64. template<typename T>
  65. void
  66. all_gather(const communicator& comm, const T* in_values, int n, T* out_values);
  67. /**
  68. * @brief Combine the values stored by each process into a single
  69. * value available to all processes.
  70. *
  71. * @c all_reduce is a collective algorithm that combines the values
  72. * stored by each process into a single value available to all
  73. * processes. The values are combined in a user-defined way,
  74. * specified via a function object. The type @c T of the values may
  75. * be any type that is serializable or has an associated MPI data
  76. * type. One can think of this operation as a @c all_gather, followed
  77. * by an @c std::accumulate() over the gather values and using the
  78. * operation @c op.
  79. *
  80. * When the type @c T has an associated MPI data type, this routine
  81. * invokes @c MPI_Allreduce to perform the reduction. If possible,
  82. * built-in MPI operations will be used; otherwise, @c all_reduce()
  83. * will create a custom MPI_Op for the call to MPI_Allreduce.
  84. *
  85. * @param comm The communicator over which the reduction will
  86. * occur.
  87. *
  88. * @param in_value The local value to be combined with the local
  89. * values of every other process. For reducing arrays, @c in_values
  90. * is a pointer to the local values to be reduced and @c n is the
  91. * number of values to reduce. See @c reduce for more information.
  92. *
  93. * @param out_value Will receive the result of the reduction
  94. * operation. If this parameter is omitted, the outgoing value will
  95. * instead be returned.
  96. *
  97. * @param op The binary operation that combines two values of type
  98. * @c T and returns a third value of type @c T. For types @c T that has
  99. * ssociated MPI data types, @c op will either be translated into
  100. * an @c MPI_Op (via @c MPI_Op_create) or, if possible, mapped
  101. * directly to a built-in MPI operation. See @c is_mpi_op in the @c
  102. * operations.hpp header for more details on this mapping. For any
  103. * non-built-in operation, commutativity will be determined by the
  104. * @c is_commmutative trait (also in @c operations.hpp): users are
  105. * encouraged to mark commutative operations as such, because it
  106. * gives the implementation additional lattitude to optimize the
  107. * reduction operation.
  108. *
  109. * @returns If no @p out_value parameter is supplied, returns the
  110. * result of the reduction operation.
  111. */
  112. template<typename T, typename Op>
  113. void
  114. all_reduce(const communicator& comm, const T& in_value, T& out_value, Op op);
  115. /**
  116. * \overload
  117. */
  118. template<typename T, typename Op>
  119. T all_reduce(const communicator& comm, const T& in_value, Op op);
  120. /**
  121. * \overload
  122. */
  123. template<typename T, typename Op>
  124. void
  125. all_reduce(const communicator& comm, const T* in_values, int n, T* out_values,
  126. Op op);
  127. /**
  128. * @brief Send data from every process to every other process.
  129. *
  130. * @c all_to_all is a collective algorithm that transmits @c p values
  131. * from every process to every other process. On process i, jth value
  132. * of the @p in_values vector is sent to process j and placed in the
  133. * ith position of the @p out_values vector in process @p j. The type
  134. * @c T of the values may be any type that is serializable or has an
  135. * associated MPI data type. If @c n is provided, then arrays of @p n
  136. * values will be transferred from one process to another.
  137. *
  138. * When the type @c T has an associated MPI data type, this routine
  139. * invokes @c MPI_Alltoall to scatter the values.
  140. *
  141. * @param comm The communicator over which the all-to-all
  142. * communication will occur.
  143. *
  144. * @param in_values A vector or pointer to storage that contains
  145. * the values to send to each process, indexed by the process ID
  146. * number.
  147. *
  148. * @param out_values A vector or pointer to storage that will be
  149. * updated to contain the values received from other processes. The
  150. * jth value in @p out_values will come from the procss with rank j.
  151. */
  152. template<typename T>
  153. void
  154. all_to_all(const communicator& comm, const std::vector<T>& in_values,
  155. std::vector<T>& out_values);
  156. /**
  157. * \overload
  158. */
  159. template<typename T>
  160. void all_to_all(const communicator& comm, const T* in_values, T* out_values);
  161. /**
  162. * \overload
  163. */
  164. template<typename T>
  165. void
  166. all_to_all(const communicator& comm, const std::vector<T>& in_values, int n,
  167. std::vector<T>& out_values);
  168. /**
  169. * \overload
  170. */
  171. template<typename T>
  172. void
  173. all_to_all(const communicator& comm, const T* in_values, int n, T* out_values);
  174. /**
  175. * @brief Broadcast a value from a root process to all other
  176. * processes.
  177. *
  178. * @c broadcast is a collective algorithm that transfers a value from
  179. * an arbitrary @p root process to every other process that is part of
  180. * the given communicator. The @c broadcast algorithm can transmit any
  181. * Serializable value, values that have associated MPI data types,
  182. * packed archives, skeletons, and the content of skeletons; see the
  183. * @c send primitive for communicators for a complete list. The type
  184. * @c T shall be the same for all processes that are a part of the
  185. * communicator @p comm, unless packed archives are being transferred:
  186. * with packed archives, the root sends a @c packed_oarchive or @c
  187. * packed_skeleton_oarchive whereas the other processes receive a
  188. * @c packed_iarchive or @c packed_skeleton_iarchve, respectively.
  189. *
  190. * When the type @c T has an associated MPI data type, this routine
  191. * invokes @c MPI_Bcast to perform the broadcast.
  192. *
  193. * @param comm The communicator over which the broadcast will
  194. * occur.
  195. *
  196. * @param value The value (or values, if @p n is provided) to be
  197. * transmitted (if the rank of @p comm is equal to @p root) or
  198. * received (if the rank of @p comm is not equal to @p root). When
  199. * the @p value is a @c skeleton_proxy, only the skeleton of the
  200. * object will be broadcast. In this case, the @p root will build a
  201. * skeleton from the object help in the proxy and all of the
  202. * non-roots will reshape the objects held in their proxies based on
  203. * the skeleton sent from the root.
  204. *
  205. * @param n When supplied, the number of values that the pointer @p
  206. * values points to, for broadcasting an array of values. The value
  207. * of @p n must be the same for all processes in @p comm.
  208. *
  209. * @param root The rank/process ID of the process that will be
  210. * transmitting the value.
  211. */
  212. template<typename T>
  213. void broadcast(const communicator& comm, T& value, int root);
  214. /**
  215. * \overload
  216. */
  217. template<typename T>
  218. void broadcast(const communicator& comm, T* values, int n, int root);
  219. /**
  220. * \overload
  221. */
  222. template<typename T>
  223. void broadcast(const communicator& comm, skeleton_proxy<T>& value, int root);
  224. /**
  225. * \overload
  226. */
  227. template<typename T>
  228. void
  229. broadcast(const communicator& comm, const skeleton_proxy<T>& value, int root);
  230. /**
  231. * @brief Gather the values stored at every process into a vector at
  232. * the root process.
  233. *
  234. * @c gather is a collective algorithm that collects the values
  235. * stored at each process into a vector of values at the @p root
  236. * process. This vector is indexed by the process number that the
  237. * value came from. The type @c T of the values may be any type that
  238. * is serializable or has an associated MPI data type.
  239. *
  240. * When the type @c T has an associated MPI data type, this routine
  241. * invokes @c MPI_Gather to gather the values.
  242. *
  243. * @param comm The communicator over which the gather will occur.
  244. *
  245. * @param in_value The value to be transmitted by each process. For
  246. * gathering arrays of values, @c in_values points to storage for
  247. * @c n*comm.size() values.
  248. *
  249. * @param out_values A vector or pointer to storage that will be
  250. * populated with the values from each process, indexed by the
  251. * process ID number. If it is a vector, it will be resized
  252. * accordingly. For non-root processes, this parameter may be
  253. * omitted. If it is still provided, however, it will be unchanged.
  254. *
  255. * @param root The process ID number that will collect the
  256. * values. This value must be the same on all processes.
  257. */
  258. template<typename T>
  259. void
  260. gather(const communicator& comm, const T& in_value, std::vector<T>& out_values,
  261. int root);
  262. /**
  263. * \overload
  264. */
  265. template<typename T>
  266. void
  267. gather(const communicator& comm, const T& in_value, T* out_values, int root);
  268. /**
  269. * \overload
  270. */
  271. template<typename T>
  272. void gather(const communicator& comm, const T& in_value, int root);
  273. /**
  274. * \overload
  275. */
  276. template<typename T>
  277. void
  278. gather(const communicator& comm, const T* in_values, int n,
  279. std::vector<T>& out_values, int root);
  280. /**
  281. * \overload
  282. */
  283. template<typename T>
  284. void
  285. gather(const communicator& comm, const T* in_values, int n, T* out_values,
  286. int root);
  287. /**
  288. * \overload
  289. */
  290. template<typename T>
  291. void gather(const communicator& comm, const T* in_values, int n, int root);
  292. /**
  293. * @brief Scatter the values stored at the root to all processes
  294. * within the communicator.
  295. *
  296. * @c scatter is a collective algorithm that scatters the values
  297. * stored in the @p root process (inside a vector) to all of the
  298. * processes in the communicator. The vector @p out_values (only
  299. * significant at the @p root) is indexed by the process number to
  300. * which the corresponding value will be sent. The type @c T of the
  301. * values may be any type that is serializable or has an associated
  302. * MPI data type.
  303. *
  304. * When the type @c T has an associated MPI data type, this routine
  305. * invokes @c MPI_Scatter to scatter the values.
  306. *
  307. * @param comm The communicator over which the gather will occur.
  308. *
  309. * @param in_values A vector or pointer to storage that will contain
  310. * the values to send to each process, indexed by the process rank.
  311. * For non-root processes, this parameter may be omitted. If it is
  312. * still provided, however, it will be unchanged.
  313. *
  314. * @param out_value The value received by each process. When
  315. * scattering an array of values, @p out_values points to the @p n
  316. * values that will be received by each process.
  317. *
  318. * @param root The process ID number that will scatter the
  319. * values. This value must be the same on all processes.
  320. */
  321. template<typename T>
  322. void
  323. scatter(const communicator& comm, const std::vector<T>& in_values, T& out_value,
  324. int root);
  325. /**
  326. * \overload
  327. */
  328. template<typename T>
  329. void
  330. scatter(const communicator& comm, const T* in_values, T& out_value, int root);
  331. /**
  332. * \overload
  333. */
  334. template<typename T>
  335. void scatter(const communicator& comm, T& out_value, int root);
  336. /**
  337. * \overload
  338. */
  339. template<typename T>
  340. void
  341. scatter(const communicator& comm, const std::vector<T>& in_values,
  342. T* out_values, int n, int root);
  343. /**
  344. * \overload
  345. */
  346. template<typename T>
  347. void
  348. scatter(const communicator& comm, const T* in_values, T* out_values, int n,
  349. int root);
  350. /**
  351. * \overload
  352. */
  353. template<typename T>
  354. void scatter(const communicator& comm, T* out_values, int n, int root);
  355. /**
  356. * @brief Combine the values stored by each process into a single
  357. * value at the root.
  358. *
  359. * @c reduce is a collective algorithm that combines the values
  360. * stored by each process into a single value at the @c root. The
  361. * values can be combined arbitrarily, specified via a function
  362. * object. The type @c T of the values may be any type that is
  363. * serializable or has an associated MPI data type. One can think of
  364. * this operation as a @c gather to the @p root, followed by an @c
  365. * std::accumulate() over the gathered values and using the operation
  366. * @c op.
  367. *
  368. * When the type @c T has an associated MPI data type, this routine
  369. * invokes @c MPI_Reduce to perform the reduction. If possible,
  370. * built-in MPI operations will be used; otherwise, @c reduce() will
  371. * create a custom MPI_Op for the call to MPI_Reduce.
  372. *
  373. * @param comm The communicator over which the reduction will
  374. * occur.
  375. *
  376. * @param in_value The local value to be combined with the local
  377. * values of every other process. For reducing arrays, @c in_values
  378. * contains a pointer to the local values. In this case, @c n is
  379. * the number of values that will be reduced. Reduction occurs
  380. * independently for each of the @p n values referenced by @p
  381. * in_values, e.g., calling reduce on an array of @p n values is
  382. * like calling @c reduce @p n separate times, one for each
  383. * location in @p in_values and @p out_values.
  384. *
  385. * @param out_value Will receive the result of the reduction
  386. * operation, but only for the @p root process. Non-root processes
  387. * may omit if parameter; if they choose to supply the parameter,
  388. * it will be unchanged. For reducing arrays, @c out_values
  389. * contains a pointer to the storage for the output values.
  390. *
  391. * @param op The binary operation that combines two values of type
  392. * @c T into a third value of type @c T. For types @c T that has
  393. * ssociated MPI data types, @c op will either be translated into
  394. * an @c MPI_Op (via @c MPI_Op_create) or, if possible, mapped
  395. * directly to a built-in MPI operation. See @c is_mpi_op in the @c
  396. * operations.hpp header for more details on this mapping. For any
  397. * non-built-in operation, commutativity will be determined by the
  398. * @c is_commmutative trait (also in @c operations.hpp): users are
  399. * encouraged to mark commutative operations as such, because it
  400. * gives the implementation additional lattitude to optimize the
  401. * reduction operation.
  402. *
  403. * @param root The process ID number that will receive the final,
  404. * combined value. This value must be the same on all processes.
  405. */
  406. template<typename T, typename Op>
  407. void
  408. reduce(const communicator& comm, const T& in_value, T& out_value, Op op,
  409. int root);
  410. /**
  411. * \overload
  412. */
  413. template<typename T, typename Op>
  414. void reduce(const communicator& comm, const T& in_value, Op op, int root);
  415. /**
  416. * \overload
  417. */
  418. template<typename T, typename Op>
  419. void
  420. reduce(const communicator& comm, const T* in_values, int n, T* out_values,
  421. Op op, int root);
  422. /**
  423. * \overload
  424. */
  425. template<typename T, typename Op>
  426. void
  427. reduce(const communicator& comm, const T* in_values, int n, Op op, int root);
  428. /**
  429. * @brief Compute a prefix reduction of values from all processes in
  430. * the communicator.
  431. *
  432. * @c scan is a collective algorithm that combines the values stored
  433. * by each process with the values of all processes with a smaller
  434. * rank. The values can be arbitrarily combined, specified via a
  435. * function object @p op. The type @c T of the values may be any type
  436. * that is serializable or has an associated MPI data type. One can
  437. * think of this operation as a @c gather to some process, followed
  438. * by an @c std::prefix_sum() over the gathered values using the
  439. * operation @c op. The ith process returns the ith value emitted by
  440. * @c std::prefix_sum().
  441. *
  442. * When the type @c T has an associated MPI data type, this routine
  443. * invokes @c MPI_Scan to perform the reduction. If possible,
  444. * built-in MPI operations will be used; otherwise, @c scan() will
  445. * create a custom @c MPI_Op for the call to MPI_Scan.
  446. *
  447. * @param comm The communicator over which the prefix reduction
  448. * will occur.
  449. *
  450. * @param in_value The local value to be combined with the local
  451. * values of other processes. For the array variant, the @c
  452. * in_values parameter points to the @c n local values that will be
  453. * combined.
  454. *
  455. * @param out_value If provided, the ith process will receive the
  456. * value @c op(in_value[0], op(in_value[1], op(..., in_value[i])
  457. * ... )). For the array variant, @c out_values contains a pointer
  458. * to storage for the @c n output values. The prefix reduction
  459. * occurs independently for each of the @p n values referenced by
  460. * @p in_values, e.g., calling scan on an array of @p n values is
  461. * like calling @c scan @p n separate times, one for each location
  462. * in @p in_values and @p out_values.
  463. *
  464. * @param op The binary operation that combines two values of type
  465. * @c T into a third value of type @c T. For types @c T that has
  466. * ssociated MPI data types, @c op will either be translated into
  467. * an @c MPI_Op (via @c MPI_Op_create) or, if possible, mapped
  468. * directly to a built-in MPI operation. See @c is_mpi_op in the @c
  469. * operations.hpp header for more details on this mapping. For any
  470. * non-built-in operation, commutativity will be determined by the
  471. * @c is_commmutative trait (also in @c operations.hpp).
  472. *
  473. * @returns If no @p out_value parameter is provided, returns the
  474. * result of prefix reduction.
  475. */
  476. template<typename T, typename Op>
  477. void
  478. scan(const communicator& comm, const T& in_value, T& out_value, Op op);
  479. /**
  480. * \overload
  481. */
  482. template<typename T, typename Op>
  483. T
  484. scan(const communicator& comm, const T& in_value, Op op);
  485. /**
  486. * \overload
  487. */
  488. template<typename T, typename Op>
  489. void
  490. scan(const communicator& comm, const T* in_values, int n, T* out_values, Op op);
  491. } } // end namespace boost::mpi
  492. #endif // BOOST_MPI_COLLECTIVES_HPP
  493. #ifndef BOOST_MPI_COLLECTIVES_FORWARD_ONLY
  494. // Include implementations of each of the collectives
  495. # include <boost/mpi/collectives/all_gather.hpp>
  496. # include <boost/mpi/collectives/all_reduce.hpp>
  497. # include <boost/mpi/collectives/all_to_all.hpp>
  498. # include <boost/mpi/collectives/broadcast.hpp>
  499. # include <boost/mpi/collectives/gather.hpp>
  500. # include <boost/mpi/collectives/scatter.hpp>
  501. # include <boost/mpi/collectives/reduce.hpp>
  502. # include <boost/mpi/collectives/scan.hpp>
  503. #endif