22 #ifndef _BLAZE_MATH_EXPRESSIONS_SMATSVECMULTEXPR_H_
23 #define _BLAZE_MATH_EXPRESSIONS_SMATSVECMULTEXPR_H_
31 #include <boost/type_traits/remove_reference.hpp>
80 typedef typename MT::ResultType
MRT;
81 typedef typename VT::ResultType
VRT;
82 typedef typename MT::CompositeType
MCT;
83 typedef typename VT::CompositeType
VCT;
139 typedef typename boost::remove_reference<MCT>::type::ConstIterator MatrixIterator;
140 typedef typename boost::remove_reference<VCT>::type::ConstIterator VectorIterator;
145 if(
vec_.size() == 0UL )
155 MatrixIterator melem( A.begin(index) );
156 const MatrixIterator mend( A.end(index) );
157 if( melem == mend ) {
161 VectorIterator velem( x.begin() );
162 const VectorIterator vend( x.end() );
163 if( velem == vend ) {
168 if( melem->index() < velem->index() ) {
170 if( melem == mend )
break;
172 else if( velem->index() < melem->index() ) {
174 if( velem == vend )
break;
177 res = melem->value() * velem->value();
184 if( melem != mend && velem != vend )
187 if( melem->index() < velem->index() ) {
189 if( melem == mend )
break;
191 else if( velem->index() < melem->index() ) {
193 if( velem == vend )
break;
196 res += melem->value() * velem->value();
198 if( melem == mend )
break;
200 if( velem == vend )
break;
211 MatrixIterator melem( A.begin(index) );
212 const MatrixIterator mend( A.end(index) );
217 res = melem->value() *
vec_[melem->index()];
219 for( ; melem!=mend; ++melem ) {
220 res += melem->value() *
vec_[melem->index()];
229 VectorIterator velem( x.begin() );
230 const VectorIterator vend( x.end() );
235 res =
mat_(index,velem->index()) * velem->value();
237 for( ; velem!=vend; ++velem ) {
238 res +=
mat_(index,velem->index()) * velem->value();
245 for(
size_t j=1UL; j<
vec_.size(); ++j ) {
300 template<
typename T >
326 template<
typename VT1 >
331 typedef typename boost::remove_reference<LT>::type::ConstIterator MatrixIterator;
332 typedef typename boost::remove_reference<RT>::type::ConstIterator VectorIterator;
339 if( x.nonZeros() == 0UL )
return;
351 const VectorIterator vend( x.end() );
353 for(
size_t i=0UL; i<(~lhs).
size(); ++i )
355 const MatrixIterator mend ( A.end(i) );
356 MatrixIterator melem( A.begin(i) );
358 if( melem == mend )
continue;
360 VectorIterator velem( x.begin() );
363 if( melem->index() < velem->index() ) {
365 if( melem == mend )
break;
367 else if( velem->index() < melem->index() ) {
369 if( velem == vend )
break;
372 (~lhs)[i] = melem->value() * velem->value();
379 if( melem != mend && velem != vend )
382 if( melem->index() < velem->index() ) {
384 if( melem == mend )
break;
386 else if( velem->index() < melem->index() ) {
388 if( velem == vend )
break;
391 (~lhs)[i] += melem->value() * velem->value();
393 if( melem == mend )
break;
395 if( velem == vend )
break;
416 template<
typename VT1 >
421 typedef typename boost::remove_reference<LT>::type::ConstIterator MatrixIterator;
422 typedef typename boost::remove_reference<RT>::type::ConstIterator VectorIterator;
425 if( x.nonZeros() == 0UL )
return;
435 const VectorIterator vend( x.end() );
437 for(
size_t i=0UL; i<(~lhs).
size(); ++i )
439 const MatrixIterator mend ( A.end(i) );
440 MatrixIterator melem( A.begin(i) );
442 if( melem == mend )
continue;
444 VectorIterator velem( x.begin() );
449 if( melem->index() < velem->index() ) {
451 if( melem == mend )
break;
453 else if( velem->index() < melem->index() ) {
455 if( velem == vend )
break;
458 accu = melem->value() * velem->value();
465 if( melem != mend && velem != vend )
468 if( melem->index() < velem->index() ) {
470 if( melem == mend )
break;
472 else if( velem->index() < melem->index() ) {
474 if( velem == vend )
break;
477 accu += melem->value() * velem->value();
479 if( melem == mend )
break;
481 if( velem == vend )
break;
487 (~lhs).insert( i, accu );
505 template<
typename VT1 >
510 typedef typename boost::remove_reference<LT>::type::ConstIterator MatrixIterator;
511 typedef typename boost::remove_reference<RT>::type::ConstIterator VectorIterator;
515 if( x.nonZeros() == 0UL )
return;
527 const VectorIterator vend( x.end() );
529 for(
size_t i=0UL; i<(~lhs).
size(); ++i )
531 const MatrixIterator mend ( A.end(i) );
532 MatrixIterator melem( A.begin(i) );
534 if( melem == mend )
continue;
536 VectorIterator velem( x.begin() );
539 if( melem->index() < velem->index() ) {
541 if( melem == mend )
break;
543 else if( velem->index() < melem->index() ) {
545 if( velem == vend )
break;
548 (~lhs)[i] += melem->value() * velem->value();
550 if( melem == mend )
break;
552 if( velem == vend )
break;
576 template<
typename VT1 >
581 typedef typename boost::remove_reference<LT>::type::ConstIterator MatrixIterator;
582 typedef typename boost::remove_reference<RT>::type::ConstIterator VectorIterator;
586 if( x.nonZeros() == 0UL )
return;
598 const VectorIterator vend( x.end() );
600 for(
size_t i=0UL; i<(~lhs).
size(); ++i )
602 const MatrixIterator mend ( A.end(i) );
603 MatrixIterator melem( A.begin(i) );
605 if( melem == mend )
continue;
607 VectorIterator velem( x.begin() );
610 if( melem->index() < velem->index() ) {
612 if( melem == mend )
break;
614 else if( velem->index() < melem->index() ) {
616 if( velem == vend )
break;
619 (~lhs)[i] -= melem->value() * velem->value();
621 if( melem == mend )
break;
623 if( velem == vend )
break;
647 template<
typename VT1 >
717 template<
typename T1
722 if( (~mat).
columns() != (~vec).size() )
723 throw std::invalid_argument(
"Matrix and vector sizes do not match" );
751 template<
typename T1
754 inline const typename EnableIf< IsMatMatMultExpr<T1>, MultExprTrait<T1,T2> >::Type::Type
757 return (~mat).leftOperand() * ( (~mat).rightOperand() * vec );