26 #ifndef MLN_METAL_MAT_HH
27 # define MLN_METAL_MAT_HH
37 # include <mln/core/concept/object.hh>
38 # include <mln/core/concept/function.hh>
39 # include <mln/core/contract.hh>
40 # include <mln/trait/all.hh>
41 # include <mln/trait/value_.hh>
42 # include <mln/metal/vec.hh>
55 template <
unsigned n,
unsigned m,
typename T>
class mat;
62 template <
unsigned n,
unsigned m,
typename T>
63 struct value_< metal::
mat<n,m,T> >
65 typedef trait::value::nature::matrix
nature;
66 typedef trait::value::kind::data
kind;
69 nbits = n * m * mln_nbits(
T),
70 card = n * m * mln_card(
T)
72 typedef mln_value_quant_from_(card) quant;
74 typedef metal::mat<n, m, mln_sum(
T)>
sum;
84 template <
unsigned n,
unsigned m,
typename T>
85 class mat :
public Object< mat<n,m,T> >
94 static const mat<n,m,T> Id;
100 template <
typename U>
101 mat(
const mat<n,m,U>&
rhs);
104 template <
typename F>
105 mat(
const Function_v2v<F>& f);
107 template <
typename U>
108 mat& operator=(
const mat<n,m,U>&
rhs);
110 const T& operator()(
unsigned i,
unsigned j)
const;
112 T& operator()(
unsigned i,
unsigned j);
114 void set_all(
const T& val);
116 unsigned size()
const;
132 template <
template<
class>
class Name,
133 unsigned n,
unsigned m,
typename T >
134 struct set_precise_unary_< Name, metal::
mat<n,m,T> >
136 typedef metal::mat<n, m, mln_trait_unary(Name, T)>
ret;
141 template <
template<
class,
class>
class Name,
142 unsigned n,
unsigned m,
typename T,
typename U>
143 struct set_precise_binary_< Name, metal::
mat<n,m,T>, metal::mat<n,m,U> >
145 typedef metal::mat<n, m, mln_trait_binary(Name, T, U)>
ret;
150 template <
unsigned n,
unsigned o,
typename T,
151 unsigned m,
typename U >
152 struct set_precise_binary_< op::
times, metal::mat<n,o,T>, metal::mat<o,m,U> >
154 typedef metal::mat<n, m, mln_sum_product(T, U)>
ret;
157 template <
unsigned n,
typename T,
typename U >
158 struct set_precise_binary_< op::
times, metal::mat<n,n,T>, metal::mat<n,n,U> >
160 typedef metal::mat<n, n, mln_sum_product(T, U)>
ret;
165 template <
unsigned n,
unsigned m,
typename T,
167 struct set_precise_binary_< op::
times, metal::mat<n,m,T>, metal::vec<m,U> >
169 typedef metal::vec<n, mln_sum_product(T, U)>
ret;
174 template <
template<
class,
class>
class Name,
175 unsigned n,
unsigned m,
typename T,
179 typedef metal::mat<n, m, mln_trait_binary(Name, T, S)>
ret;
182 template <
template<
class,
class>
class Name,
183 unsigned n,
unsigned m,
typename T,
185 struct set_binary_< Name,
186 mln::Object, metal::mat<n,m,T>,
189 typedef metal::mat<n, m, mln_trait_binary(Name, T, S)>
ret;
201 template <
unsigned n,
unsigned m,
typename T,
typename U>
207 template <
unsigned n,
unsigned m,
typename T,
typename U>
208 mat<n, m, mln_trait_op_plus(T,U)>
213 template <
unsigned n,
unsigned m,
typename T,
typename U>
214 mat<n, m, mln_trait_op_minus(T,U)>
215 operator-(
const mat<n,m,T>& lhs,
const mat<n,m,U>&
rhs);
219 template <
unsigned n,
unsigned m,
typename T>
220 mat<n, m, mln_trait_op_uminus(T)>
225 template <
unsigned n,
unsigned o,
typename T,
226 unsigned m,
typename U>
227 mat<n, m, mln_sum_product(T,U)>
228 operator*(
const mat<n,o,T>& lhs,
const mat<o,m,U>&
rhs);
232 template <
unsigned n,
unsigned m,
typename T,
234 vec<n, mln_sum_product(T,U)>
239 template <
unsigned n,
unsigned m,
typename T,
241 mat<n, m, mln_trait_op_times(T,S)>
242 operator*(
const mat<n,m,T>& lhs,
const value::scalar_<S>& s);
246 template <
unsigned n,
unsigned m,
typename T,
typename S>
247 mat<n, m, mln_trait_op_div(T,S)>
248 operator/(
const mat<n,m,T>& lhs,
const value::scalar_<S>& s);
252 template <
unsigned n,
unsigned m,
typename T>
254 operator<<(std::ostream& ostr, const mat<n,m,T>& v);
258 # ifndef MLN_INCLUDE_ONLY
260 template <
unsigned n,
unsigned m,
typename T>
261 const mat<n,m,T> mat<n,m,T>::Id = mat<n,m,T>::identity();
263 template <
unsigned n,
unsigned m,
typename T>
265 mat<n,m,T> mat<n,m,T>::identity()
267 static mat<n,m,T> id_;
268 static bool flower =
true;
271 for (
unsigned i = 0; i < n; ++i)
272 for (
unsigned j = 0; j < m; ++j)
273 id_(i, j) = (i == j);
279 template <
unsigned n,
unsigned m,
typename T>
280 template <
typename U>
282 mat<n,m,T>::mat(
const mat<n,m,U>&
rhs)
284 for (
unsigned i = 0; i < n; ++i)
285 for (
unsigned j = 0; j < m; ++j)
286 data_[i][j] =
rhs(i, j);
289 template <
unsigned n,
unsigned m,
typename T>
290 template <
typename F>
292 mat<n,m,T>::mat(
const Function_v2v<F>& f_)
294 mlc_converts_to(mln_result(F),
T)::check();
295 const F& f =
exact(f_);
296 for (
unsigned i = 0; i < n; ++i)
297 for (
unsigned j = 0; j < m; ++j)
298 data_[i][j] = f(i * n + j);
301 template <
unsigned n,
unsigned m,
typename T>
302 template <
typename U>
305 mat<n,m,T>::operator=(
const mat<n,m,U>& rhs)
307 for (
unsigned i = 0; i < n; ++i)
308 for (
unsigned j = 0; j < m; ++j)
309 data_[i][j] =
rhs(i, j);
313 template <
unsigned n,
unsigned m,
typename T>
316 mat<n,m,T>::operator()(
unsigned i,
unsigned j)
const
318 mln_precondition(i < n && j < m);
322 template <
unsigned n,
unsigned m,
typename T>
325 mat<n,m,T>::operator()(
unsigned i,
unsigned j)
327 mln_precondition(i < n && j < m);
331 template <
unsigned n,
unsigned m,
typename T>
333 void mat<n,m,T>::set_all(
const T& val)
335 for (
unsigned i = 0; i < n; ++i)
336 for (
unsigned j = 0; j < m; ++j)
340 template <
unsigned n,
unsigned m,
typename T>
342 unsigned mat<n,m,T>::size()
const
351 template <
unsigned n,
unsigned m,
typename T,
typename U>
354 operator==(
const mat<n,m,T>& lhs,
const mat<n,m,U>& rhs)
356 for (
unsigned i = 0; i < n; ++i)
357 for (
unsigned j = 0; j < m; ++j)
358 if (lhs(i, j) !=
rhs(i, j))
363 template <
unsigned n,
unsigned m,
typename T,
typename U>
365 mat<n, m, mln_trait_op_plus(T,U)>
366 operator+(
const mat<n,m,T>& lhs,
const mat<n,m,U>& rhs)
368 mat<n, m, mln_trait_op_plus(T,U)> tmp;
369 for (
unsigned i = 0; i < n; ++i)
370 for (
unsigned j = 0; j < m; ++j)
371 tmp[i][j] = lhs(i, j) +
rhs(i, j);
375 template <
unsigned n,
unsigned m,
typename T,
typename U>
377 mat<n,m, mln_trait_op_minus(T,U)>
378 operator-(
const mat<n,m,T>& lhs,
const mat<n,m,U>& rhs)
380 mat<n,m, mln_trait_op_minus(T,U)> tmp;
381 for (
unsigned i = 0; i < n; ++i)
382 for (
unsigned j = 0; j < m; ++j)
383 tmp(i, j) = lhs(i, j) -
rhs(i, j);
387 template <
unsigned n,
unsigned m,
typename T>
389 mat<n,m, mln_trait_op_uminus(T)>
392 mat<n,m, mln_trait_op_uminus(T)> tmp;
393 for (
unsigned i = 0; i < n; ++i)
394 for (
unsigned j = 0; i < m; ++i)
395 tmp(i, j) = -
rhs(i, j);
399 template <
unsigned n,
unsigned o,
typename T,
400 unsigned m,
typename U>
402 mat<n, m, mln_sum_product(T,U)>
403 operator*(
const mat<n,o,T>& lhs,
const mat<o,m,U>& rhs)
405 mat<n,m, mln_sum_product(T,U)> tmp;
406 for (
unsigned i = 0; i < n; ++i)
407 for (
unsigned j = 0; j < m; ++j)
410 for (
unsigned k = 0; k <
o; ++k)
411 tmp(i, j) += lhs(i, k) *
rhs(k, j);
416 template <
unsigned n,
unsigned m,
typename T,
419 vec<n, mln_sum_product(T,U)>
420 operator*(
const mat<n,m,T>& lhs,
const vec<m,U>& rhs)
422 vec<n, mln_sum_product(T,U)> tmp;
423 for (
unsigned i = 0; i < n; ++i)
425 mln_sum_product(
T,U)
sum(literal::zero);
426 for (
unsigned j = 0; j < m; ++j)
427 sum += lhs(i, j) * rhs[j];
433 template <
unsigned n,
unsigned m, typename
T, typename S>
435 mat<n, m, mln_trait_op_times(T,S)>
436 operator*(const mat<n,m,T>& lhs, const
value::scalar_<S>& s_)
439 mat<n, m, mln_trait_op_times(T,S)> tmp;
440 for (
unsigned i = 0; i < n; ++i)
441 for (
unsigned j = 0; j < m; ++j)
442 tmp(i, j) = lhs(i, j) * s;
446 template <
unsigned n,
unsigned m,
typename T,
typename S>
448 mat<n,m, mln_trait_op_div(T,S)>
449 operator/(
const mat<n,m,T>& lhs,
const value::scalar_<S>& s_)
452 mat<n,m, mln_trait_op_times(T,S)> tmp;
453 for (
unsigned i = 0; i < n; ++i)
454 for (
unsigned j = 0; j < m; ++j)
455 tmp[i][j] = lhs(i, j) / s;
461 template <
unsigned n,
unsigned m,
typename T>
464 operator<<(std::ostream& ostr, const mat<n,m,T>& v)
466 for (
unsigned i = 0; i < n; ++i)
469 for (
unsigned j = 0; j < m; ++j)
476 # endif // ! MLN_INCLUDE_ONLY
482 # include <mln/make/mat.hh>
484 #endif // ! MLN_METAL_MAT_HH