File indexing completed on 2025-09-17 08:49:47
0001 #ifndef BOOST_QVM_MAP_MAT_MAT_HPP_INCLUDED
0002 #define BOOST_QVM_MAP_MAT_MAT_HPP_INCLUDED
0003
0004
0005
0006
0007
0008 #include <boost/qvm/config.hpp>
0009 #include <boost/qvm/deduce_mat.hpp>
0010 #include <boost/qvm/assert.hpp>
0011 #include <boost/qvm/enable_if.hpp>
0012 #include <boost/qvm/detail/transp_impl.hpp>
0013
0014 namespace boost { namespace qvm {
0015
0016 namespace
0017 qvm_detail
0018 {
0019 template <int Row,class OriginalMatrix>
0020 class
0021 del_row_
0022 {
0023 del_row_( del_row_ const & );
0024 del_row_ & operator=( del_row_ const & );
0025 ~del_row_();
0026
0027 public:
0028
0029 template <class T>
0030 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0031 del_row_ &
0032 operator=( T const & x )
0033 {
0034 assign(*this,x);
0035 return *this;
0036 }
0037
0038 template <class R
0039 #if __cplusplus >= 201103L
0040 , class = typename enable_if<is_mat<R> >::type
0041 #endif
0042 >
0043 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0044 operator R() const
0045 {
0046 R r;
0047 assign(r,*this);
0048 return r;
0049 }
0050 };
0051
0052 template <int I,class OriginalMatrix,bool WriteElementRef=mat_write_element_ref<OriginalMatrix>::value>
0053 struct del_row_write_traits;
0054
0055 template <int I,class OriginalMatrix>
0056 struct
0057 del_row_write_traits<I,OriginalMatrix,true>
0058 {
0059 typedef del_row_<I,OriginalMatrix> this_matrix;
0060 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0061 static int const rows=mat_traits<OriginalMatrix>::rows-1;
0062 static int const cols=mat_traits<OriginalMatrix>::cols;
0063
0064 template <int Row,int Col>
0065 static
0066 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0067 scalar_type &
0068 write_element( this_matrix & x )
0069 {
0070 BOOST_QVM_STATIC_ASSERT(Row>=0);
0071 BOOST_QVM_STATIC_ASSERT(Row<rows);
0072 BOOST_QVM_STATIC_ASSERT(Col>=0);
0073 BOOST_QVM_STATIC_ASSERT(Col<cols);
0074 return mat_traits<OriginalMatrix>::template write_element<Row+(Row>=I),Col>(reinterpret_cast<OriginalMatrix &>(x));
0075 }
0076
0077 static
0078 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0079 scalar_type &
0080 write_element_idx( int row, int col, this_matrix & x )
0081 {
0082 BOOST_QVM_ASSERT(row>=0);
0083 BOOST_QVM_ASSERT(row<rows);
0084 BOOST_QVM_ASSERT(col>=0);
0085 BOOST_QVM_ASSERT(col<cols);
0086 return mat_traits<OriginalMatrix>::write_element_idx(row+(row>=I),col,reinterpret_cast<OriginalMatrix &>(x));
0087 }
0088 };
0089
0090 template <int I,class OriginalMatrix>
0091 struct
0092 del_row_write_traits<I,OriginalMatrix,false>
0093 {
0094 typedef del_row_<I,OriginalMatrix> this_matrix;
0095 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0096 static int const rows=mat_traits<OriginalMatrix>::rows-1;
0097 static int const cols=mat_traits<OriginalMatrix>::cols;
0098
0099 template <int Row,int Col>
0100 static
0101 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0102 void
0103 write_element( this_matrix & x, scalar_type s )
0104 {
0105 BOOST_QVM_STATIC_ASSERT(Row>=0);
0106 BOOST_QVM_STATIC_ASSERT(Row<rows);
0107 BOOST_QVM_STATIC_ASSERT(Col>=0);
0108 BOOST_QVM_STATIC_ASSERT(Col<cols);
0109 mat_traits<OriginalMatrix>::template write_element<Row+(Row>=I),Col>(reinterpret_cast<OriginalMatrix &>(x), s);
0110 }
0111
0112 static
0113 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0114 void
0115 write_element_idx( int row, int col, this_matrix & x, scalar_type s )
0116 {
0117 BOOST_QVM_ASSERT(row>=0);
0118 BOOST_QVM_ASSERT(row<rows);
0119 BOOST_QVM_ASSERT(col>=0);
0120 BOOST_QVM_ASSERT(col<cols);
0121 mat_traits<OriginalMatrix>::write_element_idx(row+(row>=I),col,reinterpret_cast<OriginalMatrix &>(x), s);
0122 }
0123 };
0124 }
0125
0126 template <int I,class OriginalMatrix>
0127 struct
0128 mat_traits<qvm_detail::del_row_<I,OriginalMatrix> >:
0129 qvm_detail::del_row_write_traits<I,OriginalMatrix>
0130 {
0131 typedef qvm_detail::del_row_<I,OriginalMatrix> this_matrix;
0132 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0133 static int const rows=mat_traits<OriginalMatrix>::rows-1;
0134 static int const cols=mat_traits<OriginalMatrix>::cols;
0135
0136 template <int Row,int Col>
0137 static
0138 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0139 scalar_type
0140 read_element( this_matrix const & x )
0141 {
0142 BOOST_QVM_STATIC_ASSERT(Row>=0);
0143 BOOST_QVM_STATIC_ASSERT(Row<rows);
0144 BOOST_QVM_STATIC_ASSERT(Col>=0);
0145 BOOST_QVM_STATIC_ASSERT(Col<cols);
0146 return mat_traits<OriginalMatrix>::template read_element<Row+(Row>=I),Col>(reinterpret_cast<OriginalMatrix const &>(x));
0147 }
0148
0149 static
0150 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0151 scalar_type
0152 read_element_idx( int row, int col, this_matrix const & x )
0153 {
0154 BOOST_QVM_ASSERT(row>=0);
0155 BOOST_QVM_ASSERT(row<rows);
0156 BOOST_QVM_ASSERT(col>=0);
0157 BOOST_QVM_ASSERT(col<cols);
0158 return mat_traits<OriginalMatrix>::read_element_idx(row+(row>=I),col,reinterpret_cast<OriginalMatrix const &>(x));
0159 }
0160 };
0161
0162 template <int J,class OriginalMatrix,int R,int C>
0163 struct
0164 deduce_mat<qvm_detail::del_row_<J,OriginalMatrix>,R,C>
0165 {
0166 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0167 };
0168
0169 template <int J,class OriginalMatrix,int R,int C>
0170 struct
0171 deduce_mat2<qvm_detail::del_row_<J,OriginalMatrix>,qvm_detail::del_row_<J,OriginalMatrix>,R,C>
0172 {
0173 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0174 };
0175
0176 template <int Row,class A>
0177 typename enable_if_c<
0178 is_mat<A>::value,
0179 qvm_detail::del_row_<Row,A> const &>::type
0180 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0181 del_row( A const & a )
0182 {
0183 return reinterpret_cast<typename qvm_detail::del_row_<Row,A> const &>(a);
0184 }
0185
0186 template <int Row,class A>
0187 typename enable_if_c<
0188 is_mat<A>::value,
0189 qvm_detail::del_row_<Row,A> &>::type
0190 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0191 del_row( A & a )
0192 {
0193 return reinterpret_cast<typename qvm_detail::del_row_<Row,A> &>(a);
0194 }
0195
0196
0197
0198 namespace
0199 qvm_detail
0200 {
0201 template <int Col,class OriginalMatrix>
0202 class
0203 del_col_
0204 {
0205 del_col_( del_col_ const & );
0206 del_col_ & operator=( del_col_ const & );
0207 ~del_col_();
0208
0209 public:
0210
0211 template <class T>
0212 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0213 del_col_ &
0214 operator=( T const & x )
0215 {
0216 assign(*this,x);
0217 return *this;
0218 }
0219
0220 template <class R
0221 #if __cplusplus >= 201103L
0222 , class = typename enable_if<is_mat<R> >::type
0223 #endif
0224 >
0225 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0226 operator R() const
0227 {
0228 R r;
0229 assign(r,*this);
0230 return r;
0231 }
0232 };
0233
0234 template <int J,class OriginalMatrix,bool WriteElementRef=mat_write_element_ref<OriginalMatrix>::value>
0235 struct del_col_write_traits;
0236
0237 template <int J,class OriginalMatrix>
0238 struct
0239 del_col_write_traits<J,OriginalMatrix,true>
0240 {
0241 typedef del_col_<J,OriginalMatrix> this_matrix;
0242 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0243 static int const rows=mat_traits<OriginalMatrix>::rows;
0244 static int const cols=mat_traits<OriginalMatrix>::cols-1;
0245
0246 template <int Row,int Col>
0247 static
0248 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0249 scalar_type &
0250 write_element( this_matrix & x )
0251 {
0252 BOOST_QVM_STATIC_ASSERT(Row>=0);
0253 BOOST_QVM_STATIC_ASSERT(Row<rows);
0254 BOOST_QVM_STATIC_ASSERT(Col>=0);
0255 BOOST_QVM_STATIC_ASSERT(Col<cols);
0256 return mat_traits<OriginalMatrix>::template write_element<Row,Col+(Col>=J)>(reinterpret_cast<OriginalMatrix &>(x));
0257 }
0258
0259 static
0260 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0261 scalar_type &
0262 write_element_idx( int row, int col, this_matrix & x )
0263 {
0264 BOOST_QVM_ASSERT(row>=0);
0265 BOOST_QVM_ASSERT(row<rows);
0266 BOOST_QVM_ASSERT(col>=0);
0267 BOOST_QVM_ASSERT(col<cols);
0268 return mat_traits<OriginalMatrix>::write_element_idx(row,col+(col>=J),reinterpret_cast<OriginalMatrix &>(x));
0269 }
0270 };
0271
0272 template <int J,class OriginalMatrix>
0273 struct
0274 del_col_write_traits<J,OriginalMatrix,false>
0275 {
0276 typedef del_col_<J,OriginalMatrix> this_matrix;
0277 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0278 static int const rows=mat_traits<OriginalMatrix>::rows;
0279 static int const cols=mat_traits<OriginalMatrix>::cols-1;
0280
0281 template <int Row,int Col>
0282 static
0283 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0284 void
0285 write_element( this_matrix & x, scalar_type s )
0286 {
0287 BOOST_QVM_STATIC_ASSERT(Row>=0);
0288 BOOST_QVM_STATIC_ASSERT(Row<rows);
0289 BOOST_QVM_STATIC_ASSERT(Col>=0);
0290 BOOST_QVM_STATIC_ASSERT(Col<cols);
0291 mat_traits<OriginalMatrix>::template write_element<Row,Col+(Col>=J)>(reinterpret_cast<OriginalMatrix &>(x), s);
0292 }
0293
0294 static
0295 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0296 void
0297 write_element_idx( int row, int col, this_matrix & x, scalar_type s )
0298 {
0299 BOOST_QVM_ASSERT(row>=0);
0300 BOOST_QVM_ASSERT(row<rows);
0301 BOOST_QVM_ASSERT(col>=0);
0302 BOOST_QVM_ASSERT(col<cols);
0303 mat_traits<OriginalMatrix>::write_element_idx(row,col+(col>=J),reinterpret_cast<OriginalMatrix &>(x), s);
0304 }
0305 };
0306 }
0307
0308 template <int J,class OriginalMatrix>
0309 struct
0310 mat_traits<qvm_detail::del_col_<J,OriginalMatrix> >:
0311 qvm_detail::del_col_write_traits<J,OriginalMatrix>
0312 {
0313 typedef qvm_detail::del_col_<J,OriginalMatrix> this_matrix;
0314 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0315 static int const rows=mat_traits<OriginalMatrix>::rows;
0316 static int const cols=mat_traits<OriginalMatrix>::cols-1;
0317
0318 template <int Row,int Col>
0319 static
0320 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0321 scalar_type
0322 read_element( this_matrix const & x )
0323 {
0324 BOOST_QVM_STATIC_ASSERT(Row>=0);
0325 BOOST_QVM_STATIC_ASSERT(Row<rows);
0326 BOOST_QVM_STATIC_ASSERT(Col>=0);
0327 BOOST_QVM_STATIC_ASSERT(Col<cols);
0328 return mat_traits<OriginalMatrix>::template read_element<Row,Col+(Col>=J)>(reinterpret_cast<OriginalMatrix const &>(x));
0329 }
0330
0331 static
0332 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0333 scalar_type
0334 read_element_idx( int row, int col, this_matrix const & x )
0335 {
0336 BOOST_QVM_ASSERT(row>=0);
0337 BOOST_QVM_ASSERT(row<rows);
0338 BOOST_QVM_ASSERT(col>=0);
0339 BOOST_QVM_ASSERT(col<cols);
0340 return mat_traits<OriginalMatrix>::read_element_idx(row,col+(col>=J),reinterpret_cast<OriginalMatrix const &>(x));
0341 }
0342 };
0343
0344 template <int J,class OriginalMatrix,int R,int C>
0345 struct
0346 deduce_mat<qvm_detail::del_col_<J,OriginalMatrix>,R,C>
0347 {
0348 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0349 };
0350
0351 template <int J,class OriginalMatrix,int R,int C>
0352 struct
0353 deduce_mat2<qvm_detail::del_col_<J,OriginalMatrix>,qvm_detail::del_col_<J,OriginalMatrix>,R,C>
0354 {
0355 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0356 };
0357
0358 template <int Col,class A>
0359 typename enable_if_c<
0360 is_mat<A>::value,
0361 qvm_detail::del_col_<Col,A> const &>::type
0362 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0363 del_col( A const & a )
0364 {
0365 return reinterpret_cast<typename qvm_detail::del_col_<Col,A> const &>(a);
0366 }
0367
0368 template <int Col,class A>
0369 typename enable_if_c<
0370 is_mat<A>::value,
0371 qvm_detail::del_col_<Col,A> &>::type
0372 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0373 del_col( A & a )
0374 {
0375 return reinterpret_cast<typename qvm_detail::del_col_<Col,A> &>(a);
0376 }
0377
0378
0379
0380 namespace
0381 qvm_detail
0382 {
0383 template <int Row,int Col,class OriginalMatrix>
0384 class
0385 del_row_col_
0386 {
0387 del_row_col_( del_row_col_ const & );
0388 ~del_row_col_();
0389
0390 public:
0391
0392 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0393 del_row_col_ &
0394 operator=( del_row_col_ const & x )
0395 {
0396 assign(*this,x);
0397 return *this;
0398 }
0399
0400 template <class T>
0401 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0402 del_row_col_ &
0403 operator=( T const & x )
0404 {
0405 assign(*this,x);
0406 return *this;
0407 }
0408
0409 template <class R
0410 #if __cplusplus >= 201103L
0411 , class = typename enable_if<is_mat<R> >::type
0412 #endif
0413 >
0414 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0415 operator R() const
0416 {
0417 R r;
0418 assign(r,*this);
0419 return r;
0420 }
0421 };
0422
0423 template <int I,int J,class OriginalMatrix,bool WriteElementRef=mat_write_element_ref<OriginalMatrix>::value>
0424 struct del_row_col_write_traits;
0425
0426 template <int I,int J,class OriginalMatrix>
0427 struct
0428 del_row_col_write_traits<I,J,OriginalMatrix,true>
0429 {
0430 typedef del_row_col_<I,J,OriginalMatrix> this_matrix;
0431 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0432 static int const rows=mat_traits<OriginalMatrix>::rows-1;
0433 static int const cols=mat_traits<OriginalMatrix>::cols-1;
0434
0435 template <int Row,int Col>
0436 static
0437 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0438 scalar_type &
0439 write_element( this_matrix & x )
0440 {
0441 BOOST_QVM_STATIC_ASSERT(Row>=0);
0442 BOOST_QVM_STATIC_ASSERT(Row<rows);
0443 BOOST_QVM_STATIC_ASSERT(Col>=0);
0444 BOOST_QVM_STATIC_ASSERT(Col<cols);
0445 return mat_traits<OriginalMatrix>::template write_element<Row+(Row>=I),Col+(Col>=J)>(reinterpret_cast<OriginalMatrix &>(x));
0446 }
0447
0448 static
0449 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0450 scalar_type &
0451 write_element_idx( int row, int col, this_matrix & x )
0452 {
0453 BOOST_QVM_ASSERT(row>=0);
0454 BOOST_QVM_ASSERT(row<rows);
0455 BOOST_QVM_ASSERT(col>=0);
0456 BOOST_QVM_ASSERT(col<cols);
0457 return mat_traits<OriginalMatrix>::write_element_idx(row+(row>=I),col+(col>=J),reinterpret_cast<OriginalMatrix &>(x));
0458 }
0459 };
0460
0461 template <int I,int J,class OriginalMatrix>
0462 struct
0463 del_row_col_write_traits<I,J,OriginalMatrix,false>
0464 {
0465 typedef del_row_col_<I,J,OriginalMatrix> this_matrix;
0466 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0467 static int const rows=mat_traits<OriginalMatrix>::rows-1;
0468 static int const cols=mat_traits<OriginalMatrix>::cols-1;
0469
0470 template <int Row,int Col>
0471 static
0472 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0473 void
0474 write_element( this_matrix & x, scalar_type s )
0475 {
0476 BOOST_QVM_STATIC_ASSERT(Row>=0);
0477 BOOST_QVM_STATIC_ASSERT(Row<rows);
0478 BOOST_QVM_STATIC_ASSERT(Col>=0);
0479 BOOST_QVM_STATIC_ASSERT(Col<cols);
0480 mat_traits<OriginalMatrix>::template write_element<Row+(Row>=I),Col+(Col>=J)>(reinterpret_cast<OriginalMatrix &>(x), s);
0481 }
0482
0483 static
0484 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0485 void
0486 write_element_idx( int row, int col, this_matrix & x, scalar_type s )
0487 {
0488 BOOST_QVM_ASSERT(row>=0);
0489 BOOST_QVM_ASSERT(row<rows);
0490 BOOST_QVM_ASSERT(col>=0);
0491 BOOST_QVM_ASSERT(col<cols);
0492 mat_traits<OriginalMatrix>::write_element_idx(row+(row>=I),col+(col>=J),reinterpret_cast<OriginalMatrix &>(x), s);
0493 }
0494 };
0495 }
0496
0497 template <int I,int J,class OriginalMatrix>
0498 struct
0499 mat_traits<qvm_detail::del_row_col_<I,J,OriginalMatrix> >:
0500 qvm_detail::del_row_col_write_traits<I,J,OriginalMatrix>
0501 {
0502 typedef qvm_detail::del_row_col_<I,J,OriginalMatrix> this_matrix;
0503 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0504 static int const rows=mat_traits<OriginalMatrix>::rows-1;
0505 static int const cols=mat_traits<OriginalMatrix>::cols-1;
0506
0507 template <int Row,int Col>
0508 static
0509 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0510 scalar_type
0511 read_element( this_matrix const & x )
0512 {
0513 BOOST_QVM_STATIC_ASSERT(Row>=0);
0514 BOOST_QVM_STATIC_ASSERT(Row<rows);
0515 BOOST_QVM_STATIC_ASSERT(Col>=0);
0516 BOOST_QVM_STATIC_ASSERT(Col<cols);
0517 return mat_traits<OriginalMatrix>::template read_element<Row+(Row>=I),Col+(Col>=J)>(reinterpret_cast<OriginalMatrix const &>(x));
0518 }
0519
0520 static
0521 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0522 scalar_type
0523 read_element_idx( int row, int col, this_matrix const & x )
0524 {
0525 BOOST_QVM_ASSERT(row>=0);
0526 BOOST_QVM_ASSERT(row<rows);
0527 BOOST_QVM_ASSERT(col>=0);
0528 BOOST_QVM_ASSERT(col<cols);
0529 return mat_traits<OriginalMatrix>::read_element_idx(row+(row>=I),col+(col>=J),reinterpret_cast<OriginalMatrix const &>(x));
0530 }
0531 };
0532
0533 template <int I,int J,class OriginalMatrix,int R,int C>
0534 struct
0535 deduce_mat<qvm_detail::del_row_col_<I,J,OriginalMatrix>,R,C>
0536 {
0537 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0538 };
0539
0540 template <int I,int J,class OriginalMatrix,int R,int C>
0541 struct
0542 deduce_mat2<qvm_detail::del_row_col_<I,J,OriginalMatrix>,qvm_detail::del_row_col_<I,J,OriginalMatrix>,R,C>
0543 {
0544 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0545 };
0546
0547 template <int Row,int Col,class A>
0548 typename enable_if_c<
0549 is_mat<A>::value,
0550 qvm_detail::del_row_col_<Row,Col,A> const &>::type
0551 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0552 del_row_col( A const & a )
0553 {
0554 return reinterpret_cast<typename qvm_detail::del_row_col_<Row,Col,A> const &>(a);
0555 }
0556
0557 template <int Row,int Col,class A>
0558 typename enable_if_c<
0559 is_mat<A>::value,
0560 qvm_detail::del_row_col_<Row,Col,A> &>::type
0561 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0562 del_row_col( A & a )
0563 {
0564 return reinterpret_cast<typename qvm_detail::del_row_col_<Row,Col,A> &>(a);
0565 }
0566
0567
0568
0569 namespace
0570 qvm_detail
0571 {
0572 template <int Row,class OriginalMatrix>
0573 class
0574 neg_row_
0575 {
0576 neg_row_( neg_row_ const & );
0577 neg_row_ & operator=( neg_row_ const & );
0578 ~neg_row_();
0579
0580 public:
0581
0582 template <class T>
0583 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0584 neg_row_ &
0585 operator=( T const & x )
0586 {
0587 assign(*this,x);
0588 return *this;
0589 }
0590
0591 template <class R
0592 #if __cplusplus >= 201103L
0593 , class = typename enable_if<is_mat<R> >::type
0594 #endif
0595 >
0596 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0597 operator R() const
0598 {
0599 R r;
0600 assign(r,*this);
0601 return r;
0602 }
0603 };
0604 }
0605
0606 template <int I,class OriginalMatrix>
0607 struct
0608 mat_traits<qvm_detail::neg_row_<I,OriginalMatrix> >
0609 {
0610 typedef qvm_detail::neg_row_<I,OriginalMatrix> this_matrix;
0611 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0612 static int const rows=mat_traits<OriginalMatrix>::rows;
0613 static int const cols=mat_traits<OriginalMatrix>::cols;
0614
0615 template <int Row,int Col>
0616 static
0617 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0618 scalar_type
0619 read_element( this_matrix const & x )
0620 {
0621 BOOST_QVM_STATIC_ASSERT(Row>=0);
0622 BOOST_QVM_STATIC_ASSERT(Row<rows);
0623 BOOST_QVM_STATIC_ASSERT(Col>=0);
0624 BOOST_QVM_STATIC_ASSERT(Col<cols);
0625 return Row==I ?
0626 -mat_traits<OriginalMatrix>::template read_element<Row,Col>(reinterpret_cast<OriginalMatrix const &>(x)) :
0627 mat_traits<OriginalMatrix>::template read_element<Row,Col>(reinterpret_cast<OriginalMatrix const &>(x));
0628 }
0629
0630 static
0631 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0632 scalar_type
0633 read_element_idx( int row, int col, this_matrix const & x )
0634 {
0635 BOOST_QVM_ASSERT(row>=0);
0636 BOOST_QVM_ASSERT(row<rows);
0637 BOOST_QVM_ASSERT(col>=0);
0638 BOOST_QVM_ASSERT(col<cols);
0639 return row==I?
0640 -mat_traits<OriginalMatrix>::read_element_idx(row,col,reinterpret_cast<OriginalMatrix const &>(x)) :
0641 mat_traits<OriginalMatrix>::read_element_idx(row,col,reinterpret_cast<OriginalMatrix const &>(x));
0642 }
0643 };
0644
0645 template <int J,class OriginalMatrix,int R,int C>
0646 struct
0647 deduce_mat<qvm_detail::neg_row_<J,OriginalMatrix>,R,C>
0648 {
0649 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0650 };
0651
0652 template <int J,class OriginalMatrix,int R,int C>
0653 struct
0654 deduce_mat2<qvm_detail::neg_row_<J,OriginalMatrix>,qvm_detail::neg_row_<J,OriginalMatrix>,R,C>
0655 {
0656 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0657 };
0658
0659 template <int Row,class A>
0660 typename enable_if_c<
0661 is_mat<A>::value,
0662 qvm_detail::neg_row_<Row,A> const &>::type
0663 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0664 neg_row( A const & a )
0665 {
0666 return reinterpret_cast<typename qvm_detail::neg_row_<Row,A> const &>(a);
0667 }
0668
0669
0670
0671 namespace
0672 qvm_detail
0673 {
0674 template <int Col,class OriginalMatrix>
0675 class
0676 neg_col_
0677 {
0678 neg_col_( neg_col_ const & );
0679 neg_col_ & operator=( neg_col_ const & );
0680 ~neg_col_();
0681
0682 public:
0683
0684 template <class T>
0685 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0686 neg_col_ &
0687 operator=( T const & x )
0688 {
0689 assign(*this,x);
0690 return *this;
0691 }
0692
0693 template <class R
0694 #if __cplusplus >= 201103L
0695 , class = typename enable_if<is_mat<R> >::type
0696 #endif
0697 >
0698 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0699 operator R() const
0700 {
0701 R r;
0702 assign(r,*this);
0703 return r;
0704 }
0705 };
0706 }
0707
0708 template <int J,class OriginalMatrix>
0709 struct
0710 mat_traits<qvm_detail::neg_col_<J,OriginalMatrix> >
0711 {
0712 typedef qvm_detail::neg_col_<J,OriginalMatrix> this_matrix;
0713 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0714 static int const rows=mat_traits<OriginalMatrix>::rows;
0715 static int const cols=mat_traits<OriginalMatrix>::cols;
0716
0717 template <int Row,int Col>
0718 static
0719 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0720 scalar_type
0721 read_element( this_matrix const & x )
0722 {
0723 BOOST_QVM_STATIC_ASSERT(Row>=0);
0724 BOOST_QVM_STATIC_ASSERT(Row<rows);
0725 BOOST_QVM_STATIC_ASSERT(Col>=0);
0726 BOOST_QVM_STATIC_ASSERT(Col<cols);
0727 return Col==J?
0728 -mat_traits<OriginalMatrix>::template read_element<Row,Col>(reinterpret_cast<OriginalMatrix const &>(x)) :
0729 mat_traits<OriginalMatrix>::template read_element<Row,Col>(reinterpret_cast<OriginalMatrix const &>(x));
0730 }
0731
0732 static
0733 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0734 scalar_type
0735 read_element_idx( int row, int col, this_matrix const & x )
0736 {
0737 BOOST_QVM_ASSERT(row>=0);
0738 BOOST_QVM_ASSERT(row<rows);
0739 BOOST_QVM_ASSERT(col>=0);
0740 BOOST_QVM_ASSERT(col<cols);
0741 return col==J?
0742 -mat_traits<OriginalMatrix>::read_element_idx(row,col,reinterpret_cast<OriginalMatrix const &>(x)) :
0743 mat_traits<OriginalMatrix>::read_element_idx(row,col,reinterpret_cast<OriginalMatrix const &>(x));
0744 }
0745 };
0746
0747 template <int J,class OriginalMatrix,int R,int C>
0748 struct
0749 deduce_mat<qvm_detail::neg_col_<J,OriginalMatrix>,R,C>
0750 {
0751 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0752 };
0753
0754 template <int J,class OriginalMatrix,int R,int C>
0755 struct
0756 deduce_mat2<qvm_detail::neg_col_<J,OriginalMatrix>,qvm_detail::neg_col_<J,OriginalMatrix>,R,C>
0757 {
0758 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0759 };
0760
0761 template <int Col,class A>
0762 typename enable_if_c<
0763 is_mat<A>::value,
0764 qvm_detail::neg_col_<Col,A> const &>::type
0765 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0766 neg_col( A const & a )
0767 {
0768 return reinterpret_cast<typename qvm_detail::neg_col_<Col,A> const &>(a);
0769 }
0770
0771
0772
0773 template <class A>
0774 typename enable_if_c<
0775 is_mat<A>::value,
0776 qvm_detail::transposed_<A> const &>::type
0777 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0778 transposed( A const & a )
0779 {
0780 return reinterpret_cast<typename qvm_detail::transposed_<A> const &>(a);
0781 }
0782
0783 template <class A>
0784 typename enable_if_c<
0785 is_mat<A>::value,
0786 qvm_detail::transposed_<A> &>::type
0787 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0788 transposed( A & a )
0789 {
0790 return reinterpret_cast<typename qvm_detail::transposed_<A> &>(a);
0791 }
0792
0793
0794
0795 namespace
0796 qvm_detail
0797 {
0798 template <int Row1,int Row2,class OriginalMatrix>
0799 class
0800 swap_rows_
0801 {
0802 swap_rows_( swap_rows_ const & );
0803 swap_rows_ & operator=( swap_rows_ const & );
0804 ~swap_rows_();
0805
0806 public:
0807
0808 template <class T>
0809 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0810 swap_rows_ &
0811 operator=( T const & x )
0812 {
0813 assign(*this,x);
0814 return *this;
0815 }
0816
0817 template <class R
0818 #if __cplusplus >= 201103L
0819 , class = typename enable_if<is_mat<R> >::type
0820 #endif
0821 >
0822 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0823 operator R() const
0824 {
0825 R r;
0826 assign(r,*this);
0827 return r;
0828 }
0829 };
0830
0831 template <int R1,int R2,class OriginalMatrix,bool WriteElementRef=mat_write_element_ref<OriginalMatrix>::value>
0832 struct swap_rows_write_traits;
0833
0834 template <int R1,int R2,class OriginalMatrix>
0835 struct
0836 swap_rows_write_traits<R1,R2,OriginalMatrix,true>
0837 {
0838 typedef swap_rows_<R1,R2,OriginalMatrix> this_matrix;
0839 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0840 static int const rows=mat_traits<OriginalMatrix>::rows;
0841 static int const cols=mat_traits<OriginalMatrix>::cols;
0842
0843 template <int Row,int Col>
0844 static
0845 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0846 scalar_type &
0847 write_element( this_matrix & x )
0848 {
0849 BOOST_QVM_STATIC_ASSERT(Row>=0);
0850 BOOST_QVM_STATIC_ASSERT(Row<rows);
0851 BOOST_QVM_STATIC_ASSERT(Col>=0);
0852 BOOST_QVM_STATIC_ASSERT(Col<cols);
0853 return mat_traits<OriginalMatrix>::template write_element<(Row==R1 && R1!=R2)*R2+(Row==R2 && R1!=R2)*R1+((Row!=R1 && Row!=R2) || R1==R2)*Row,Col>(reinterpret_cast<OriginalMatrix &>(x));
0854 }
0855
0856 static
0857 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0858 scalar_type &
0859 write_element_idx( int row, int col, this_matrix & x )
0860 {
0861 BOOST_QVM_ASSERT(row>=0);
0862 BOOST_QVM_ASSERT(row<rows);
0863 BOOST_QVM_ASSERT(col>=0);
0864 BOOST_QVM_ASSERT(col<cols);
0865 return mat_traits<OriginalMatrix>::write_element_idx(row==R1?R2:row==R2?R1:row,col,reinterpret_cast<OriginalMatrix &>(x));
0866 }
0867 };
0868
0869 template <int R1,int R2,class OriginalMatrix>
0870 struct
0871 swap_rows_write_traits<R1,R2,OriginalMatrix,false>
0872 {
0873 typedef swap_rows_<R1,R2,OriginalMatrix> this_matrix;
0874 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0875 static int const rows=mat_traits<OriginalMatrix>::rows;
0876 static int const cols=mat_traits<OriginalMatrix>::cols;
0877
0878 template <int Row,int Col>
0879 static
0880 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0881 void
0882 write_element( this_matrix & x, scalar_type s )
0883 {
0884 BOOST_QVM_STATIC_ASSERT(Row>=0);
0885 BOOST_QVM_STATIC_ASSERT(Row<rows);
0886 BOOST_QVM_STATIC_ASSERT(Col>=0);
0887 BOOST_QVM_STATIC_ASSERT(Col<cols);
0888 mat_traits<OriginalMatrix>::template write_element<(Row==R1 && R1!=R2)*R2+(Row==R2 && R1!=R2)*R1+((Row!=R1 && Row!=R2) || R1==R2)*Row,Col>(reinterpret_cast<OriginalMatrix &>(x), s);
0889 }
0890
0891 static
0892 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0893 void
0894 write_element_idx( int row, int col, this_matrix & x, scalar_type s )
0895 {
0896 BOOST_QVM_ASSERT(row>=0);
0897 BOOST_QVM_ASSERT(row<rows);
0898 BOOST_QVM_ASSERT(col>=0);
0899 BOOST_QVM_ASSERT(col<cols);
0900 mat_traits<OriginalMatrix>::write_element_idx(row==R1?R2:row==R2?R1:row,col,reinterpret_cast<OriginalMatrix &>(x), s);
0901 }
0902 };
0903 }
0904
0905 template <int R1,int R2,class OriginalMatrix>
0906 struct
0907 mat_traits<qvm_detail::swap_rows_<R1,R2,OriginalMatrix> >:
0908 qvm_detail::swap_rows_write_traits<R1,R2,OriginalMatrix>
0909 {
0910 typedef qvm_detail::swap_rows_<R1,R2,OriginalMatrix> this_matrix;
0911 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
0912 static int const rows=mat_traits<OriginalMatrix>::rows;
0913 static int const cols=mat_traits<OriginalMatrix>::cols;
0914
0915 template <int Row,int Col>
0916 static
0917 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0918 scalar_type
0919 read_element( this_matrix const & x )
0920 {
0921 BOOST_QVM_STATIC_ASSERT(Row>=0);
0922 BOOST_QVM_STATIC_ASSERT(Row<rows);
0923 BOOST_QVM_STATIC_ASSERT(Col>=0);
0924 BOOST_QVM_STATIC_ASSERT(Col<cols);
0925 return mat_traits<OriginalMatrix>::template read_element<(Row==R1 && R1!=R2)*R2+(Row==R2 && R1!=R2)*R1+((Row!=R1 && Row!=R2) || R1==R2)*Row,Col>(reinterpret_cast<OriginalMatrix const &>(x));
0926 }
0927
0928 static
0929 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
0930 scalar_type
0931 read_element_idx( int row, int col, this_matrix const & x )
0932 {
0933 BOOST_QVM_ASSERT(row>=0);
0934 BOOST_QVM_ASSERT(row<rows);
0935 BOOST_QVM_ASSERT(col>=0);
0936 BOOST_QVM_ASSERT(col<cols);
0937 return mat_traits<OriginalMatrix>::read_element_idx(row==R1?R2:row==R2?R1:row,col,reinterpret_cast<OriginalMatrix const &>(x));
0938 }
0939 };
0940
0941 template <int R1,int R2,class OriginalMatrix,int R,int C>
0942 struct
0943 deduce_mat<qvm_detail::swap_rows_<R1,R2,OriginalMatrix>,R,C>
0944 {
0945 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0946 };
0947
0948 template <int R1,int R2,class OriginalMatrix,int R,int C>
0949 struct
0950 deduce_mat2<qvm_detail::swap_rows_<R1,R2,OriginalMatrix>,qvm_detail::swap_rows_<R1,R2,OriginalMatrix>,R,C>
0951 {
0952 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
0953 };
0954
0955 template <int R1,int R2,class A>
0956 typename enable_if_c<
0957 is_mat<A>::value,
0958 qvm_detail::swap_rows_<R1,R2,A> const &>::type
0959 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0960 swap_rows( A const & a )
0961 {
0962 return reinterpret_cast<typename qvm_detail::swap_rows_<R1,R2,A> const &>(a);
0963 }
0964
0965 template <int R1,int R2,class A>
0966 typename enable_if_c<
0967 is_mat<A>::value,
0968 qvm_detail::swap_rows_<R1,R2,A> &>::type
0969 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0970 swap_rows( A & a )
0971 {
0972 return reinterpret_cast<typename qvm_detail::swap_rows_<R1,R2,A> &>(a);
0973 }
0974
0975
0976
0977 namespace
0978 qvm_detail
0979 {
0980 template <int Row1,int Row2,class OriginalMatrix>
0981 class
0982 swap_cols_
0983 {
0984 swap_cols_( swap_cols_ const & );
0985 swap_cols_ & operator=( swap_cols_ const & );
0986 ~swap_cols_();
0987
0988 public:
0989
0990 template <class T>
0991 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0992 swap_cols_ &
0993 operator=( T const & x )
0994 {
0995 assign(*this,x);
0996 return *this;
0997 }
0998
0999 template <class R
1000 #if __cplusplus >= 201103L
1001 , class = typename enable_if<is_mat<R> >::type
1002 #endif
1003 >
1004 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
1005 operator R() const
1006 {
1007 R r;
1008 assign(r,*this);
1009 return r;
1010 }
1011 };
1012
1013 template <int C1,int C2,class OriginalMatrix,bool WriteElementRef=mat_write_element_ref<OriginalMatrix>::value>
1014 struct swap_cols_write_traits;
1015
1016 template <int C1,int C2,class OriginalMatrix>
1017 struct
1018 swap_cols_write_traits<C1,C2,OriginalMatrix,true>
1019 {
1020 typedef swap_cols_<C1,C2,OriginalMatrix> this_matrix;
1021 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
1022 static int const rows=mat_traits<OriginalMatrix>::rows;
1023 static int const cols=mat_traits<OriginalMatrix>::cols;
1024
1025 template <int Row,int Col>
1026 static
1027 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
1028 scalar_type &
1029 write_element( this_matrix & x )
1030 {
1031 BOOST_QVM_STATIC_ASSERT(Row>=0);
1032 BOOST_QVM_STATIC_ASSERT(Row<rows);
1033 BOOST_QVM_STATIC_ASSERT(Col>=0);
1034 BOOST_QVM_STATIC_ASSERT(Col<cols);
1035 return mat_traits<OriginalMatrix>::template write_element<Row,(Col==C1 && C1!=C2)*C2+(Col==C2 && C1!=C2)*C1+((Col!=C1 && Col!=C2) || C1==C2)*Col>(reinterpret_cast<OriginalMatrix &>(x));
1036 }
1037
1038 static
1039 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
1040 scalar_type &
1041 write_element_idx( int row, int col, this_matrix & x )
1042 {
1043 BOOST_QVM_ASSERT(row>=0);
1044 BOOST_QVM_ASSERT(row<rows);
1045 BOOST_QVM_ASSERT(col>=0);
1046 BOOST_QVM_ASSERT(col<cols);
1047 return mat_traits<OriginalMatrix>::write_element_idx(row,col==C1?C2:col==C2?C1:col,reinterpret_cast<OriginalMatrix &>(x));
1048 }
1049 };
1050
1051 template <int C1,int C2,class OriginalMatrix>
1052 struct
1053 swap_cols_write_traits<C1,C2,OriginalMatrix,false>
1054 {
1055 typedef swap_cols_<C1,C2,OriginalMatrix> this_matrix;
1056 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
1057 static int const rows=mat_traits<OriginalMatrix>::rows;
1058 static int const cols=mat_traits<OriginalMatrix>::cols;
1059
1060 template <int Row,int Col>
1061 static
1062 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
1063 void
1064 write_element( this_matrix & x, scalar_type s )
1065 {
1066 BOOST_QVM_STATIC_ASSERT(Row>=0);
1067 BOOST_QVM_STATIC_ASSERT(Row<rows);
1068 BOOST_QVM_STATIC_ASSERT(Col>=0);
1069 BOOST_QVM_STATIC_ASSERT(Col<cols);
1070 mat_traits<OriginalMatrix>::template write_element<Row,(Col==C1 && C1!=C2)*C2+(Col==C2 && C1!=C2)*C1+((Col!=C1 && Col!=C2) || C1==C2)*Col>(reinterpret_cast<OriginalMatrix &>(x), s);
1071 }
1072
1073 static
1074 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
1075 void
1076 write_element_idx( int row, int col, this_matrix & x, scalar_type s )
1077 {
1078 BOOST_QVM_ASSERT(row>=0);
1079 BOOST_QVM_ASSERT(row<rows);
1080 BOOST_QVM_ASSERT(col>=0);
1081 BOOST_QVM_ASSERT(col<cols);
1082 mat_traits<OriginalMatrix>::write_element_idx(row,col==C1?C2:col==C2?C1:col,reinterpret_cast<OriginalMatrix &>(x), s);
1083 }
1084 };
1085 }
1086
1087 template <int C1,int C2,class OriginalMatrix>
1088 struct
1089 mat_traits<qvm_detail::swap_cols_<C1,C2,OriginalMatrix> >:
1090 qvm_detail::swap_cols_write_traits<C1,C2,OriginalMatrix>
1091 {
1092 typedef qvm_detail::swap_cols_<C1,C2,OriginalMatrix> this_matrix;
1093 typedef typename mat_traits<OriginalMatrix>::scalar_type scalar_type;
1094 static int const rows=mat_traits<OriginalMatrix>::rows;
1095 static int const cols=mat_traits<OriginalMatrix>::cols;
1096
1097 template <int Row,int Col>
1098 static
1099 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
1100 scalar_type
1101 read_element( this_matrix const & x )
1102 {
1103 BOOST_QVM_STATIC_ASSERT(Row>=0);
1104 BOOST_QVM_STATIC_ASSERT(Row<rows);
1105 BOOST_QVM_STATIC_ASSERT(Col>=0);
1106 BOOST_QVM_STATIC_ASSERT(Col<cols);
1107 return mat_traits<OriginalMatrix>::template read_element<Row,(Col==C1 && C1!=C2)*C2+(Col==C2 && C1!=C2)*C1+((Col!=C1 && Col!=C2) || C1==C2)*Col>(reinterpret_cast<OriginalMatrix const &>(x));
1108 }
1109
1110 static
1111 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_CRITICAL
1112 scalar_type
1113 read_element_idx( int row, int col, this_matrix const & x )
1114 {
1115 BOOST_QVM_ASSERT(row>=0);
1116 BOOST_QVM_ASSERT(row<rows);
1117 BOOST_QVM_ASSERT(col>=0);
1118 BOOST_QVM_ASSERT(col<cols);
1119 return mat_traits<OriginalMatrix>::read_element_idx(row,col==C1?C2:col==C2?C1:col,reinterpret_cast<OriginalMatrix const &>(x));
1120 }
1121 };
1122
1123 template <int C1,int C2,class OriginalMatrix,int R,int C>
1124 struct
1125 deduce_mat<qvm_detail::swap_cols_<C1,C2,OriginalMatrix>,R,C>
1126 {
1127 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
1128 };
1129
1130 template <int C1,int C2,class OriginalMatrix,int R,int C>
1131 struct
1132 deduce_mat2<qvm_detail::swap_cols_<C1,C2,OriginalMatrix>,qvm_detail::swap_cols_<C1,C2,OriginalMatrix>,R,C>
1133 {
1134 typedef mat<typename mat_traits<OriginalMatrix>::scalar_type,R,C> type;
1135 };
1136
1137 template <int C1,int C2,class A>
1138 typename enable_if_c<
1139 is_mat<A>::value,
1140 qvm_detail::swap_cols_<C1,C2,A> const &>::type
1141 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
1142 swap_cols( A const & a )
1143 {
1144 return reinterpret_cast<typename qvm_detail::swap_cols_<C1,C2,A> const &>(a);
1145 }
1146
1147 template <int C1,int C2,class A>
1148 typename enable_if_c<
1149 is_mat<A>::value,
1150 qvm_detail::swap_cols_<C1,C2,A> &>::type
1151 BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
1152 swap_cols( A & a )
1153 {
1154 return reinterpret_cast<typename qvm_detail::swap_cols_<C1,C2,A> &>(a);
1155 }
1156
1157 } }
1158
1159 #endif