arma_hot inline typename T1::elem_type accu_proxy_at(const Proxy<T1>& P) { typedef typename T1::elem_type eT; const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); eT val = eT(0); if(n_rows != 1) { for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { val += P.at(row,col); } } else { for(uword col=0; col < n_cols; ++col) { val += P.at(0,col); } } return val; }
arma_hot inline void op_fft_cx::copy_vec_proxy(typename Proxy<T1>::elem_type* dest, const Proxy<T1>& P, const uword N) { arma_extra_debug_sigprint(); if(Proxy<T1>::use_at == false) { typename Proxy<T1>::ea_type X = P.get_ea(); for(uword i=0; i < N; ++i) { dest[i] = X[i]; } } else { if(P.get_n_cols() == 1) { for(uword i=0; i < N; ++i) { dest[i] = P.at(i,0); } } else { for(uword i=0; i < N; ++i) { dest[i] = P.at(0,i); } } } }
arma_warn_unused inline typename T1::elem_type det ( const Op<T1, op_trimat>& X ) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const Proxy<T1> P(X.m); const uword N = P.get_n_rows(); arma_debug_check( (N != P.get_n_cols()), "det(): given matrix must be square sized" ); eT val1 = eT(1); eT val2 = eT(1); uword i,j; for(i=0, j=1; j<N; i+=2, j+=2) { val1 *= P.at(i,i); val2 *= P.at(j,j); } if(i < N) { val1 *= P.at(i,i); } return val1 * val2; }
arma_hot inline typename T1::pod_type arma_vec_norm_k ( const Proxy<T1>& P, const int k ) { arma_extra_debug_sigprint(); typedef typename T1::pod_type T; T acc = T(0); if(Proxy<T1>::prefer_at_accessor == false) { typename Proxy<T1>::ea_type A = P.get_ea(); const uword N = P.get_n_elem(); uword i,j; for(i=0, j=1; j<N; i+=2, j+=2) { acc += std::pow(std::abs(A[i]), k); acc += std::pow(std::abs(A[j]), k); } if(i < N) { acc += std::pow(std::abs(A[i]), k); } } else { const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); if(n_rows != 1) { for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { acc += std::pow(std::abs(P.at(row,col)), k); } } else { for(uword col=0; col < n_cols; ++col) { acc += std::pow(std::abs(P.at(0,col)), k); } } } return std::pow(acc, T(1)/T(k)); }
inline podarray<eT>::podarray(const Proxy<T1>& P) : n_elem(P.get_n_elem()) { arma_extra_debug_sigprint_this(this); const uword P_n_elem = P.get_n_elem(); init_cold(P_n_elem); eT* out_mem = (*this).memptr(); if(Proxy<T1>::use_at == false) { typename Proxy<T1>::ea_type A = P.get_ea(); uword i,j; for(i=0, j=1; j < P_n_elem; i+=2, j+=2) { const eT val_i = A[i]; const eT val_j = A[j]; out_mem[i] = val_i; out_mem[j] = val_j; } if(i < P_n_elem) { out_mem[i] = A[i]; } } else { const uword P_n_rows = P.get_n_rows(); const uword P_n_cols = P.get_n_cols(); if(P_n_rows != 1) { uword count = 0; for(uword col=0; col < P_n_cols; ++col) for(uword row=0; row < P_n_rows; ++row, ++count) { out_mem[count] = P.at(row,col); } } else { for(uword col=0; col < P_n_cols; ++col) { out_mem[col] = P.at(0,col); } } } }
arma_hot inline typename T1::pod_type arma_vec_norm_1(const Proxy<T1>& A) { arma_extra_debug_sigprint(); typedef typename T1::pod_type T; T acc = T(0); if(Proxy<T1>::prefer_at_accessor == false) { typename Proxy<T1>::ea_type P = A.get_ea(); const uword N = A.get_n_elem(); uword i,j; for(i=0, j=1; j<N; i+=2, j+=2) { acc += std::abs(P[i]); acc += std::abs(P[j]); } if(i < N) { acc += std::abs(P[i]); } } else { const uword n_rows = A.get_n_rows(); const uword n_cols = A.get_n_cols(); for(uword col=0; col<n_cols; ++col) { uword i,j; for(i=0, j=1; j<n_rows; i+=2, j+=2) { acc += std::abs(A.at(i,col)); acc += std::abs(A.at(j,col)); } if(i < n_rows) { acc += std::abs(A.at(i,col)); } } } return acc; }
arma_hot inline typename T1::pod_type arma_vec_norm_2 ( const Proxy<T1>& P, const typename arma_cx_only<typename T1::elem_type>::result* junk = 0 ) { arma_extra_debug_sigprint(); arma_ignore(junk); typedef typename T1::pod_type T; T acc = T(0); if(Proxy<T1>::prefer_at_accessor == false) { typename Proxy<T1>::ea_type A = P.get_ea(); const uword N = P.get_n_elem(); for(uword i=0; i<N; ++i) { const T tmp = std::abs(A[i]); acc += tmp*tmp; } } else { const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); if(n_rows == 1) { for(uword col=0; col<n_cols; ++col) { const T tmp = std::abs(P.at(0,col)); acc += tmp*tmp; } } else { for(uword col=0; col<n_cols; ++col) for(uword row=0; row<n_rows; ++row) { const T tmp = std::abs(P.at(row,col)); acc += tmp*tmp; } } } return std::sqrt(acc); }
arma_hot inline void op_sum::apply_noalias_proxy(Mat<typename T1::elem_type>& out, const Proxy<T1>& P, const uword dim) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const uword P_n_rows = P.get_n_rows(); const uword P_n_cols = P.get_n_cols(); if(dim == 0) { out.set_size(1, P_n_cols); eT* out_mem = out.memptr(); for(uword col=0; col < P_n_cols; ++col) { eT val1 = eT(0); eT val2 = eT(0); uword i,j; for(i=0, j=1; j < P_n_rows; i+=2, j+=2) { val1 += P.at(i,col); val2 += P.at(j,col); } if(i < P_n_rows) { val1 += P.at(i,col); } out_mem[col] = (val1 + val2); } } else { out.zeros(P_n_rows, 1); eT* out_mem = out.memptr(); for(uword col=0; col < P_n_cols; ++col) for(uword row=0; row < P_n_rows; ++row) { out_mem[row] += P.at(row,col); } } }
inline arma_warn_unused uword accu(const mtOp<uword,T1,op_rel_noteq>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const eT val = X.aux; const Proxy<T1> P(X.m); uword n_nonzero = 0; if(Proxy<T1>::prefer_at_accessor == false) { typedef typename Proxy<T1>::ea_type ea_type; ea_type A = P.get_ea(); const uword n_elem = P.get_n_elem(); for(uword i=0; i<n_elem; ++i) { if(A[i] != val) { ++n_nonzero; } } } else { const uword P_n_cols = P.get_n_cols(); const uword P_n_rows = P.get_n_rows(); if(P_n_rows == 1) { for(uword col=0; col < P_n_cols; ++col) { if(P.at(0,col) != val) { ++n_nonzero; } } } else { for(uword col=0; col < P_n_cols; ++col) for(uword row=0; row < P_n_rows; ++row) { if(P.at(row,col) != val) { ++n_nonzero; } } } } return n_nonzero; }
inline arma_warn_unused typename enable_if2 <(is_arma_type<T1>::value) && (is_arma_sparse_type<T2>::value) && (is_same_type<typename T1::elem_type, typename T2::elem_type>::value), typename T1::elem_type >::result dot ( const Base<typename T1::elem_type, T1>& x, const SpBase<typename T2::elem_type, T2>& y ) { arma_extra_debug_sigprint(); const Proxy<T1> pa(x.get_ref()); const SpProxy<T2> pb(y.get_ref()); arma_debug_assert_same_size(pa.get_n_rows(), pa.get_n_cols(), pb.get_n_rows(), pb.get_n_cols(), "dot()"); typedef typename T1::elem_type eT; eT result = eT(0); typename SpProxy<T2>::const_iterator_type it = pb.begin(); // prefer_at_accessor won't save us operations while(it.pos() < pb.get_n_nonzero()) { result += (*it) * pa.at(it.row(), it.col()); ++it; } return result; }
inline bool op_any::any_vec_helper(const Base<typename T1::elem_type, T1>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const Proxy<T1> P(X.get_ref()); const uword n_elem = P.get_n_elem(); if(Proxy<T1>::prefer_at_accessor == false) { typename Proxy<T1>::ea_type Pea = P.get_ea(); for(uword i=0; i<n_elem; ++i) { if(Pea[i] != eT(0)) { return true; } } } else { const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { if(P.at(row,col) != eT(0)) { return true; } } } return false; }
inline void op_vectorise_row::apply_proxy(Mat<typename T1::elem_type>& out, const Proxy<T1>& P) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; if(P.is_alias(out) == false) { out.set_size( 1, P.get_n_elem() ); eT* outmem = out.memptr(); const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); for(uword row=0; row < n_rows; ++row) { uword i,j; for(i=0, j=1; j < n_cols; i+=2, j+=2) { const eT tmp_i = P.at(row,i); const eT tmp_j = P.at(row,j); *outmem = tmp_i; outmem++; *outmem = tmp_j; outmem++; } if(i < n_cols) { *outmem = P.at(row,i); outmem++; } } } else // we have aliasing { arma_extra_debug_print("op_vectorise_row::apply(): aliasing detected"); Mat<eT> tmp; op_vectorise_row::apply_proxy(tmp, P); out.steal_mem(tmp); } }
inline void op_diagmat2::apply(Mat<typename T1::elem_type>& out, const Proxy<T1>& P, const uword row_offset, const uword col_offset) { arma_extra_debug_sigprint(); const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); const uword n_elem = P.get_n_elem(); if(n_elem == 0) { out.reset(); return; } const bool P_is_vec = (T1::is_row) || (T1::is_col) || (n_rows == 1) || (n_cols == 1); if(P_is_vec) { const uword n_pad = (std::max)(row_offset, col_offset); out.zeros(n_elem + n_pad, n_elem + n_pad); if(Proxy<T1>::prefer_at_accessor == false) { typename Proxy<T1>::ea_type Pea = P.get_ea(); for(uword i=0; i < n_elem; ++i) { out.at(row_offset + i, col_offset + i) = Pea[i]; } } else { const unwrap<typename Proxy<T1>::stored_type> U(P.Q); const Proxy<typename unwrap<typename Proxy<T1>::stored_type>::stored_type> PP(U.M); op_diagmat2::apply(out, PP, row_offset, col_offset); } } else // P represents a matrix { arma_debug_check ( ((row_offset > 0) && (row_offset >= n_rows)) || ((col_offset > 0) && (col_offset >= n_cols)), "diagmat(): requested diagonal out of bounds" ); out.zeros(n_rows, n_cols); const uword N = (std::min)(n_rows - row_offset, n_cols - col_offset); for(uword i=0; i<N; ++i) { const uword row = i + row_offset; const uword col = i + col_offset; out.at(row,col) = P.at(row,col); } } }
inline void glue_max::apply(Mat< std::complex<T> >& out, const Proxy<T1>& PA, const Proxy<T2>& PB) { arma_extra_debug_sigprint(); typedef typename std::complex<T> eT; const uword n_rows = PA.get_n_rows(); const uword n_cols = PA.get_n_cols(); arma_debug_assert_same_size(n_rows, n_cols, PB.get_n_rows(), PB.get_n_cols(), "max(): given matrices must have the same size"); out.set_size(n_rows, n_cols); eT* out_mem = out.memptr(); if( (Proxy<T1>::use_at == false) && (Proxy<T2>::use_at == false) ) { typename Proxy<T1>::ea_type A = PA.get_ea(); typename Proxy<T2>::ea_type B = PB.get_ea(); const uword N = PA.get_n_elem(); for(uword i=0; i<N; ++i) { const eT A_val = A[i]; const eT B_val = B[i]; out_mem[i] = ( std::abs(A_val) > std::abs(B_val) ) ? A_val : B_val; } } else { for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { const eT A_val = PA.at(row,col); const eT B_val = PB.at(row,col); *out_mem = ( std::abs(A_val) > std::abs(B_val) ) ? A_val : B_val; ++out_mem; } } }
inline void op_clamp::apply_noalias(Mat<typename T1::elem_type>& out, const Proxy<T1>& P, const typename T1::elem_type min_val, const typename T1::elem_type max_val) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); out.set_size(n_rows, n_cols); eT* out_mem = out.memptr(); if(Proxy<T1>::use_at == false) { const uword N = P.get_n_elem(); typename Proxy<T1>::ea_type A = P.get_ea(); uword j; for(j=1; j<N; j+=2) { eT val_i = A[j-1]; eT val_j = A[j ]; val_i = (val_i < min_val) ? min_val : ((val_i > max_val) ? max_val : val_i); val_j = (val_j < min_val) ? min_val : ((val_j > max_val) ? max_val : val_j); (*out_mem) = val_i; out_mem++; (*out_mem) = val_j; out_mem++; } const uword i = j-1; if(i < N) { eT val_i = A[i]; val_i = (val_i < min_val) ? min_val : ((val_i > max_val) ? max_val : val_i); (*out_mem) = val_i; } } else { for(uword col=0; col<n_cols; ++col) for(uword row=0; row<n_rows; ++row) { eT val = P.at(row,col); val = (val < min_val) ? min_val : ((val > max_val) ? max_val : val); (*out_mem) = val; out_mem++; } } }
arma_hot inline typename T1::elem_type accu(const Base<typename T1::elem_type,T1>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; typedef typename Proxy<T1>::ea_type ea_type; const Proxy<T1> A(X.get_ref()); if(Proxy<T1>::prefer_at_accessor == false) { ea_type P = A.get_ea(); const uword n_elem = A.get_n_elem(); eT val1 = eT(0); eT val2 = eT(0); uword i,j; for(i=0, j=1; j<n_elem; i+=2, j+=2) { val1 += P[i]; val2 += P[j]; } if(i < n_elem) { val1 += P[i]; } return val1 + val2; } else { const uword n_rows = A.get_n_rows(); const uword n_cols = A.get_n_cols(); eT val = eT(0); for(uword col=0; col<n_cols; ++col) { for(uword row=0; row<n_rows; ++row) { val += A.at(row,col); } } return val; } }
inline void glue_max::apply(Mat<eT>& out, const Proxy<T1>& PA, const Proxy<T2>& PB) { arma_extra_debug_sigprint(); const uword n_rows = PA.get_n_rows(); const uword n_cols = PA.get_n_cols(); arma_debug_assert_same_size(n_rows, n_cols, PB.get_n_rows(), PB.get_n_cols(), "max(): given matrices must have the same size"); out.set_size(n_rows, n_cols); eT* out_mem = out.memptr(); if( (Proxy<T1>::use_at == false) && (Proxy<T2>::use_at == false) ) { typename Proxy<T1>::ea_type A = PA.get_ea(); typename Proxy<T2>::ea_type B = PB.get_ea(); const uword N = PA.get_n_elem(); for(uword i=0; i<N; ++i) { out_mem[i] = (std::max)(A[i], B[i]); } } else { for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { *out_mem = (std::max)( PA.at(row,col), PB.at(row,col) ); ++out_mem; } } }
inline void glue_mixed_plus::apply(Mat<typename eT_promoter<T1,T2>::eT>& out, const mtGlue<typename eT_promoter<T1,T2>::eT, T1, T2, glue_mixed_plus>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT1; typedef typename T2::elem_type eT2; typedef typename promote_type<eT1,eT2>::result out_eT; promote_type<eT1,eT2>::check(); const Proxy<T1> A(X.A); const Proxy<T2> B(X.B); arma_debug_assert_same_size(A, B, "addition"); const uword n_rows = A.get_n_rows(); const uword n_cols = A.get_n_cols(); out.set_size(n_rows, n_cols); out_eT* out_mem = out.memptr(); const uword n_elem = out.n_elem; const bool prefer_at_accessor = (Proxy<T1>::prefer_at_accessor || Proxy<T2>::prefer_at_accessor); if(prefer_at_accessor == false) { typename Proxy<T1>::ea_type AA = A.get_ea(); typename Proxy<T2>::ea_type BB = B.get_ea(); for(uword i=0; i<n_elem; ++i) { out_mem[i] = upgrade_val<eT1,eT2>::apply(AA[i]) + upgrade_val<eT1,eT2>::apply(BB[i]); } } else { uword i = 0; for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { out_mem[i] = upgrade_val<eT1,eT2>::apply(A.at(row,col)) + upgrade_val<eT1,eT2>::apply(B.at(row,col)); ++i; } } }
inline arma_warn_unused typename T1::elem_type det ( const Op<T1, op_trimat>& X, const bool slow = false ) { arma_extra_debug_sigprint(); arma_ignore(slow); typedef typename T1::elem_type eT; const Proxy<T1> P(X.m); const uword N = P.get_n_rows(); arma_debug_check( (N != P.get_n_cols()), "det(): matrix is not square" ); eT val1 = eT(1); eT val2 = eT(1); uword i,j; for(i=0, j=1; j<N; i+=2, j+=2) { val1 *= P.at(i,i); val2 *= P.at(j,j); } if(i < N) { val1 *= P.at(i,i); } return val1 * val2; }
inline uword op_find::helper ( Mat<uword>& indices, const Base<typename T1::elem_type, T1>& X ) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const Proxy<T1> A(X.get_ref()); const uword n_elem = A.get_n_elem(); indices.set_size(n_elem, 1); uword* indices_mem = indices.memptr(); uword n_nz = 0; if(Proxy<T1>::prefer_at_accessor == false) { typename Proxy<T1>::ea_type PA = A.get_ea(); for(uword i=0; i<n_elem; ++i) { if(PA[i] != eT(0)) { indices_mem[n_nz] = i; ++n_nz; } } } else { const uword n_rows = A.get_n_rows(); const uword n_cols = A.get_n_cols(); uword i = 0; for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { if(A.at(row,col) != eT(0)) { indices_mem[n_nz] = i; ++n_nz; } ++i; } } return n_nz; }
inline typename enable_if2 < (is_arma_type<T1>::value && is_arma_sparse_type<T2>::value && is_same_type<typename T1::elem_type, typename T2::elem_type>::value), Mat<typename T1::elem_type> >::result operator/ ( const Base<typename T1::elem_type, T1>& x, const SpBase<typename T2::elem_type, T2>& y ) { arma_extra_debug_sigprint(); const Proxy<T1> pa(x.get_ref()); const SpProxy<T2> pb(y.get_ref()); arma_debug_assert_same_size(pa.get_n_rows(), pa.get_n_cols(), pb.get_n_rows(), pb.get_n_cols(), "element-wise division"); Mat<typename T1::elem_type> result(pa.get_n_rows(), pa.get_n_cols()); result.fill(Datum<typename T1::elem_type>::inf); // Now divide each element typename SpProxy<T2>::const_iterator_type it = pb.begin(); while(it.pos() < pb.get_n_nonzero()) { if(Proxy<T1>::prefer_at_accessor == false) { const uword index = (it.col() * result.n_rows) + it.row(); result[index] = pa[index] / (*it); } else { result.at(it.row(), it.col()) = pa.at(it.row(), it.col()) / (*it); } ++it; } return result; }
inline void op_nonzeros::apply_noalias(Mat<typename T1::elem_type>& out, const Proxy<T1>& P) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const uword N_max = P.get_n_elem(); Mat<eT> tmp(N_max, 1); eT* tmp_mem = tmp.memptr(); uword N_nz = 0; if(Proxy<T1>::use_at == false) { typename Proxy<T1>::ea_type Pea = P.get_ea(); for(uword i=0; i<N_max; ++i) { const eT val = Pea[i]; if(val != eT(0)) { tmp_mem[N_nz] = val; ++N_nz; } } } else { const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { const eT val = P.at(row,col); if(val != eT(0)) { tmp_mem[N_nz] = val; ++N_nz; } } } out.steal_mem_col(tmp, N_nz); }
inline void op_cx_scalar_plus::apply ( Mat< typename std::complex<typename T1::pod_type> >& out, const mtOp<typename std::complex<typename T1::pod_type>, T1, op_cx_scalar_plus>& X ) { arma_extra_debug_sigprint(); typedef typename std::complex<typename T1::pod_type> eT; const Proxy<T1> A(X.m); const uword n_rows = A.get_n_rows(); const uword n_cols = A.get_n_cols(); out.set_size(n_rows, n_cols); const eT k = X.aux_out_eT; eT* out_mem = out.memptr(); if(Proxy<T1>::prefer_at_accessor == false) { const uword n_elem = A.get_n_elem(); for(uword i=0; i<n_elem; ++i) { out_mem[i] = A[i] + k; } } else { for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { *out_mem = A.at(row,col) + k; ++out_mem; } } }
inline void op_abs::apply( Mat<typename T1::pod_type>& out, const mtOp<typename T1::pod_type, T1, op_abs>& X ) { arma_extra_debug_sigprint(); typedef typename T1::pod_type T; const Proxy<T1> P(X.m); const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); out.set_size(n_rows, n_cols); T* out_mem = out.memptr(); if(Proxy<T1>::prefer_at_accessor == false) { typedef typename Proxy<T1>::ea_type ea_type; const uword n_elem = P.get_n_elem(); ea_type A = P.get_ea(); for(uword i=0; i < n_elem; ++i) { out_mem[i] = std::abs( A[i] ); } } else { for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { *out_mem = std::abs( P.at(row,col) ); out_mem++; } } }
inline void op_fliplr::apply_proxy_noalias(Mat<typename T1::elem_type>& out, const Proxy<T1>& P) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const uword P_n_rows = P.get_n_rows(); const uword P_n_cols = P.get_n_cols(); const uword P_n_cols_m1 = P_n_cols - 1; out.set_size(P_n_rows, P_n_cols); if( ((T1::is_row) || (P_n_rows == 1)) && (Proxy<T1>::use_at == false) ) { eT* out_mem = out.memptr(); const typename Proxy<T1>::ea_type P_ea = P.get_ea(); for(uword col=0; col < P_n_cols; ++col) { out_mem[P_n_cols_m1 - col] = P_ea[col]; } } else { for(uword col=0; col < P_n_cols; ++col) { eT* out_colmem = out.colptr(P_n_cols_m1 - col); for(uword row=0; row < P_n_rows; ++row) { out_colmem[row] = P.at(row,col); } } } }
inline bool op_all::all_vec_helper(const Base<typename T1::elem_type, T1>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const Proxy<T1> P(X.get_ref()); const uword n_elem = P.get_n_elem(); uword count = 0; if(Proxy<T1>::prefer_at_accessor == false) { typename Proxy<T1>::ea_type Pea = P.get_ea(); for(uword i=0; i<n_elem; ++i) { if(Pea[i] != eT(0)) { ++count; } } } else { const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { if(P.at(row,col) != eT(0)) { ++count; } } } // NOTE: for empty vectors it makes more sense to return false, but we need to return true for compatability with Octave return (n_elem == count); }
inline arma_warn_unused typename T1::elem_type trace(const Base<typename T1::elem_type,T1>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const Proxy<T1> A(X.get_ref()); arma_debug_check( (A.get_n_rows() != A.get_n_cols()), "trace(): matrix must be square sized" ); const uword N = A.get_n_rows(); eT val = eT(0); for(uword i=0; i<N; ++i) { val += A.at(i,i); } return val; }
inline typename T1::elem_type op_prod::prod(const Base<typename T1::elem_type,T1>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const Proxy<T1> P(X.get_ref()); eT val = eT(1); if(Proxy<T1>::prefer_at_accessor == false) { typedef typename Proxy<T1>::ea_type ea_type; const ea_type A = P.get_ea(); const uword n_elem = P.get_n_elem(); uword i,j; for(i=0, j=1; j < n_elem; i+=2, j+=2) { val *= A[i]; val *= A[j]; } if(i < n_elem) { val *= A[i]; } } else { const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); if(n_rows == 1) { uword i,j; for(i=0, j=1; j < n_cols; i+=2, j+=2) { val *= P.at(0,i); val *= P.at(0,j); } if(i < n_cols) { val *= P.at(0,i); } } else { for(uword col=0; col < n_cols; ++col) { uword i,j; for(i=0, j=1; j < n_rows; i+=2, j+=2) { val *= P.at(i,col); val *= P.at(j,col); } if(i < n_rows) { val *= P.at(i,col); } } } } return val; }
inline typename arma_cx_only<typename T1::elem_type>::result op_min::min(const Base<typename T1::elem_type,T1>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; typedef typename get_pod_type<eT>::result T; const Proxy<T1> P(X.get_ref()); const uword n_elem = P.get_n_elem(); arma_debug_check( (n_elem == 0), "min(): given object has no elements" ); T min_val = priv::most_pos<T>(); if(Proxy<T1>::prefer_at_accessor == false) { typedef typename Proxy<T1>::ea_type ea_type; ea_type A = P.get_ea(); uword index = 0; for(uword i=0; i<n_elem; ++i) { const T tmp = std::abs(A[i]); if(tmp < min_val) { min_val = tmp; index = i; } } return( A[index] ); } else { const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); uword best_row = 0; uword best_col = 0; if(n_rows == 1) { for(uword col=0; col < n_cols; ++col) { const T tmp = std::abs(P.at(0,col)); if(tmp < min_val) { min_val = tmp; best_col = col; } } } else { for(uword col=0; col < n_cols; ++col) for(uword row=0; row < n_rows; ++row) { const T tmp = std::abs(P.at(row,col)); if(tmp < min_val) { min_val = tmp; best_row = row; best_col = col; } } } return P.at(best_row, best_col); } }
inline typename arma_not_cx<typename T1::elem_type>::result op_min::min(const Base<typename T1::elem_type,T1>& X) { arma_extra_debug_sigprint(); typedef typename T1::elem_type eT; const Proxy<T1> P(X.get_ref()); const uword n_elem = P.get_n_elem(); arma_debug_check( (n_elem == 0), "min(): given object has no elements" ); eT min_val = priv::most_pos<eT>(); if(Proxy<T1>::prefer_at_accessor == false) { typedef typename Proxy<T1>::ea_type ea_type; ea_type A = P.get_ea(); uword i,j; for(i=0, j=1; j<n_elem; i+=2, j+=2) { const eT tmp_i = A[i]; const eT tmp_j = A[j]; if(tmp_i < min_val) { min_val = tmp_i; } if(tmp_j < min_val) { min_val = tmp_j; } } if(i < n_elem) { const eT tmp_i = A[i]; if(tmp_i < min_val) { min_val = tmp_i; } } } else { const uword n_rows = P.get_n_rows(); const uword n_cols = P.get_n_cols(); if(n_rows == 1) { uword i,j; for(i=0, j=1; j < n_cols; i+=2, j+=2) { const eT tmp_i = P.at(0,i); const eT tmp_j = P.at(0,j); if(tmp_i < min_val) { min_val = tmp_i; } if(tmp_j < min_val) { min_val = tmp_j; } } if(i < n_cols) { const eT tmp_i = P.at(0,i); if(tmp_i < min_val) { min_val = tmp_i; } } } else { for(uword col=0; col < n_cols; ++col) { uword i,j; for(i=0, j=1; j < n_rows; i+=2, j+=2) { const eT tmp_i = P.at(i,col); const eT tmp_j = P.at(j,col); if(tmp_i < min_val) { min_val = tmp_i; } if(tmp_j < min_val) { min_val = tmp_j; } } if(i < n_rows) { const eT tmp_i = P.at(i,col); if(tmp_i < min_val) { min_val = tmp_i; } } } } } return min_val; }