Stan  2.14.0
probability, sampling & optimization
rvalue.hpp
Go to the documentation of this file.
1 #ifndef STAN_MODEL_INDEXING_RVALUE_HPP
2 #define STAN_MODEL_INDEXING_RVALUE_HPP
3 
4 #include <boost/utility/enable_if.hpp>
5 #include <boost/type_traits/is_same.hpp>
6 #include <stan/math/prim/mat.hpp>
12 #include <vector>
13 
14 namespace stan {
15 
16  namespace model {
17 
18  // all indexing from 1
19 
30  template <typename T>
31  inline T rvalue(const T& c, const nil_index_list& /*idx*/,
32  const char* /*name*/ = "", int /*depth*/ = 0) {
33  return c;
34  }
35 
49  template <typename T>
50  inline T rvalue(const Eigen::Matrix<T, Eigen::Dynamic, 1>& v,
52  const char* name = "ANON", int depth = 0) {
53  int ones_idx = idx.head_.n_;
54  math::check_range("vector[single] indexing", name, v.size(), ones_idx);
55  return v(ones_idx - 1);
56  }
57 
72  template <typename T>
73  inline T rvalue(const Eigen::Matrix<T, 1, Eigen::Dynamic>& rv,
75  const char* name = "ANON", int depth = 0) {
76  int n = idx.head_.n_;
77  math::check_range("row_vector[single] indexing", name,
78  rv.size(), n);
79  return rv(n - 1);
80  }
81 
96  template <typename T, typename I>
97  inline
98  typename boost::disable_if<boost::is_same<I, index_uni>,
99  Eigen::Matrix<T, Eigen::Dynamic, 1> >::type
100  rvalue(const Eigen::Matrix<T, Eigen::Dynamic, 1>& v,
102  const char* name = "ANON", int depth = 0) {
103  int size = rvalue_index_size(idx.head_, v.size());
104  Eigen::Matrix<T, Eigen::Dynamic, 1> a(size);
105  for (int i = 0; i < size; ++i) {
106  int n = rvalue_at(i, idx.head_);
107  math::check_range("vector[multi] indexing", name, v.size(), n);
108  a(i) = v(n - 1);
109  }
110  return a;
111  }
112 
128  template <typename T, typename I>
129  inline
130  typename boost::disable_if<boost::is_same<I, index_uni>,
131  Eigen::Matrix<T, 1, Eigen::Dynamic> >::type
132  rvalue(const Eigen::Matrix<T, 1, Eigen::Dynamic>& rv,
134  const char* name = "ANON", int depth = 0) {
135  int size = rvalue_index_size(idx.head_, rv.size());
136  Eigen::Matrix<T, 1, Eigen::Dynamic> a(size);
137  for (int i = 0; i < size; ++i) {
138  int n = rvalue_at(i, idx.head_);
139  math::check_range("row_vector[multi] indexing", name, rv.size(), n);
140  a(i) = rv(n - 1);
141  }
142  return a;
143  }
144 
158  template <typename T>
159  inline Eigen::Matrix<T, 1, Eigen::Dynamic>
160  rvalue(const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& a,
162  const char* name = "ANON", int depth = 0) {
163  int n = idx.head_.n_;
164  math::check_range("matrix[uni] indexing", name, a.rows(), n);
165  return a.row(n - 1);
166  }
167 
182  template <typename T, typename I>
183  inline typename boost::disable_if<boost::is_same<I, index_uni>,
184  Eigen::Matrix<T, Eigen::Dynamic,
185  Eigen::Dynamic> >::type
186  rvalue(const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& a,
188  const char* name = "ANON", int depth = 0) {
189  int n_rows = rvalue_index_size(idx.head_, a.rows());
190  Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic> b(n_rows, a.cols());
191  for (int i = 0; i < n_rows; ++i) {
192  int n = rvalue_at(i, idx.head_);
193  math::check_range("matrix[multi] indexing", name, a.rows(), n);
194  b.row(i) = a.row(n - 1);
195  }
196  return b;
197  }
198 
212  template <typename T>
213  inline T
214  rvalue(const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& a,
217  nil_index_list> >& idx,
218  const char* name = "ANON", int depth = 0) {
219  int m = idx.head_.n_;
220  int n = idx.tail_.head_.n_;
221  math::check_range("matrix[uni,uni] indexing, row", name, a.rows(), m);
222  math::check_range("matrix[uni,uni] indexing, col", name, a.cols(), n);
223  return a(m - 1, n - 1);
224  }
225 
241  template <typename T, typename I>
242  inline typename boost::disable_if<boost::is_same<I, index_uni>,
243  Eigen::Matrix<T,
244  1, Eigen::Dynamic> >::type
245  rvalue(const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& a,
248  const char* name = "ANON", int depth = 0) {
249  int m = idx.head_.n_;
250  math::check_range("matrix[uni,multi] indexing, row", name, a.rows(), m);
251  Eigen::Matrix<T, 1, Eigen::Dynamic> r = a.row(m - 1);
252  return rvalue(r, idx.tail_);
253  }
254 
270  template <typename T, typename I>
271  inline
272  typename boost::disable_if<boost::is_same<I, index_uni>,
273  Eigen::Matrix<T, Eigen::Dynamic, 1> >::type
274  rvalue(const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& a,
276  nil_index_list> >& idx,
277  const char* name = "ANON", int depth = 0) {
278  int rows = rvalue_index_size(idx.head_, a.rows());
279  Eigen::Matrix<T, Eigen::Dynamic, 1> c(rows);
280  for (int i = 0; i < rows; ++i) {
281  int m = rvalue_at(i, idx.head_);
282  int n = idx.tail_.head_.n_;
283  math::check_range("matrix[multi,uni] index row", name, a.rows(), m);
284  math::check_range("matrix[multi,uni] index col", name, a.cols(), n);
285  c(i) = a(m - 1, n - 1);
286  }
287  return c;
288  }
289 
305  template <typename T, typename I1, typename I2>
306  inline
307  typename boost::disable_if_c<boost::is_same<I1, index_uni>::value
308  || boost::is_same<I2, index_uni>::value,
309  Eigen::Matrix<T, Eigen::Dynamic,
310  Eigen::Dynamic> >::type
311  rvalue(const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& a,
312  const cons_index_list<I1, cons_index_list<I2,
313  nil_index_list> >& idx,
314  const char* name = "ANON", int depth = 0) {
315  int rows = rvalue_index_size(idx.head_, a.rows());
316  int cols = rvalue_index_size(idx.tail_.head_, a.cols());
317  Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic> c(rows, cols);
318  for (int j = 0; j < cols; ++j) {
319  for (int i = 0; i < rows; ++i) {
320  int m = rvalue_at(i, idx.head_);
321  int n = rvalue_at(j, idx.tail_.head_);
322  math::check_range("matrix[multi,multi] row index", name,
323  a.rows(), m);
324  math::check_range("matrix[multi,multi] col index", name,
325  a.cols(), n);
326  c(i, j) = a(m - 1, n - 1);
327  }
328  }
329  return c;
330  }
331 
348  template <typename T, typename L>
349  inline typename rvalue_return<std::vector<T>,
351  rvalue(const std::vector<T>& c, const cons_index_list<index_uni, L>& idx,
352  const char* name = "ANON", int depth = 0) {
353  int n = idx.head_.n_;
354  math::check_range("array[uni,...] index", name, c.size(), n);
355  return rvalue(c[n - 1], idx.tail_, name, depth + 1);
356  }
357 
374  template <typename T, typename I, typename L>
375  inline typename rvalue_return<std::vector<T>, cons_index_list<I, L> >::type
376  rvalue(const std::vector<T>& c, const cons_index_list<I, L>& idx,
377  const char* name = "ANON", int depth = 0) {
379  cons_index_list<I, L> >::type result;
380  for (int i = 0; i < rvalue_index_size(idx.head_, c.size()); ++i) {
381  int n = rvalue_at(i, idx.head_);
382  math::check_range("array[multi,...] index", name, c.size(), n);
383  result.push_back(rvalue(c[n - 1], idx.tail_, name, depth + 1));
384  }
385  return result;
386  }
387 
388 
389  }
390 }
391 #endif
Primary template class for metaprogram to calculate return value for model::rvalue() for the containe...
int rvalue_index_size(const index_multi &idx, int size)
Return size of specified multi-index.
Probability, optimization and sampling library.
int rvalue_at(int n, const index_multi &idx)
Return the index in the underlying array corresponding to the specified position in the specified mul...
Definition: rvalue_at.hpp:21
T rvalue(const T &c, const nil_index_list &, const char *="", int=0)
Return the result of indexing a specified value with a nil index list, which just returns the value...
Definition: rvalue.hpp:31
Template structure for an index list consisting of a head and tail index.
Definition: index_list.hpp:23
Structure for an indexing consisting of a single index.
Definition: index.hpp:17
Structure for an empty (size zero) index list.
Definition: index_list.hpp:11

     [ Stan Home Page ] © 2011–2016, Stan Development Team.