Blaze 3.9
Dense.h
Go to the documentation of this file.
1//=================================================================================================
33//=================================================================================================
34
35#ifndef _BLAZE_MATH_VIEWS_ELEMENTS_DENSE_H_
36#define _BLAZE_MATH_VIEWS_ELEMENTS_DENSE_H_
37
38
39//*************************************************************************************************
40// Includes
41//*************************************************************************************************
42
43#include <iterator>
44#include <blaze/math/Aliases.h>
73#include <blaze/util/Assert.h>
74#include <blaze/util/mpl/If.h>
77
78
79namespace blaze {
80
81//=================================================================================================
82//
83// CLASS TEMPLATE SPECIALIZATION FOR DENSE VECTORS
84//
85//=================================================================================================
86
87//*************************************************************************************************
94template< typename VT // Type of the dense vector
95 , bool TF // Transpose flag
96 , typename... CEAs > // Compile time element arguments
97class Elements<VT,TF,true,CEAs...>
98 : public View< DenseVector< Elements<VT,TF,true,CEAs...>, TF > >
99 , private ElementsData<CEAs...>
100{
101 private:
102 //**Type definitions****************************************************************************
103 using DataType = ElementsData<CEAs...>;
104 using Operand = If_t< IsExpression_v<VT>, VT, VT& >;
105 //**********************************************************************************************
106
107 //**Compile time flags**************************************************************************
108 using DataType::N;
109 //**********************************************************************************************
110
111 public:
112 //**Type definitions****************************************************************************
114 using This = Elements<VT,TF,true,CEAs...>;
115
117 using BaseType = View< DenseVector<This,TF> >;
118
119 using ViewedType = VT;
120 using ResultType = ElementsTrait_t<VT,N>;
121 using TransposeType = TransposeType_t<ResultType>;
122 using ElementType = ElementType_t<VT>;
123 using ReturnType = ReturnType_t<VT>;
124 using CompositeType = const Elements&;
125
127 using ConstReference = ConstReference_t<VT>;
128
130 using Reference = If_t< IsConst_v<VT>, ConstReference, Reference_t<VT> >;
131
133 using ConstPointer = ConstPointer_t<VT>;
134
136 using Pointer = If_t< IsConst_v<VT> || !HasMutableDataAccess_v<VT>, ConstPointer, Pointer_t<VT> >;
137 //**********************************************************************************************
138
139 //**ElementsIterator class definition***********************************************************
142 template< typename ElementsType // Type of the element selection
143 , typename IteratorType > // Type of the dense vector iterator
144 class ElementsIterator
145 {
146 public:
147 //**Type definitions*************************************************************************
149 using IteratorCategory = typename std::iterator_traits<IteratorType>::iterator_category;
150
152 using ValueType = typename std::iterator_traits<IteratorType>::value_type;
153
155 using PointerType = typename std::iterator_traits<IteratorType>::pointer;
156
158 using ReferenceType = typename std::iterator_traits<IteratorType>::reference;
159
161 using DifferenceType = typename std::iterator_traits<IteratorType>::difference_type;
162
163 // STL iterator requirements
164 using iterator_category = IteratorCategory;
165 using value_type = ValueType;
166 using pointer = PointerType;
167 using reference = ReferenceType;
168 using difference_type = DifferenceType;
169 //*******************************************************************************************
170
171 //**Constructor******************************************************************************
174 inline ElementsIterator()
175 : elements_( nullptr ) // Pointer to the element selection
176 , index_ ( 0UL ) // Index of the current element of the element selection
177 , pos_ () // Iterator to the current element
178 {}
179 //*******************************************************************************************
180
181 //**Constructor******************************************************************************
187 inline ElementsIterator( ElementsType* elements, size_t index )
188 : elements_( elements ) // Pointer to the element selection
189 , index_ ( index ) // Index of the current element of the element selection
190 , pos_ () // Iterator to the current element
191 {
192 if( index_ < elements_->size() )
193 pos_ = elements_->operand().begin() + elements_->idx( index_ );
194 }
195 //*******************************************************************************************
196
197 //**Constructor******************************************************************************
202 template< typename ElementsType2, typename IteratorType2 >
203 inline ElementsIterator( const ElementsIterator<ElementsType2,IteratorType2>& it )
204 : elements_( it.elements_ ) // Pointer to the element selection
205 , index_ ( it.index_ ) // Index of the current element of the element selection
206 , pos_ ( it.pos_ ) // Iterator to the current element
207 {}
208 //*******************************************************************************************
209
210 //**Addition assignment operator*************************************************************
216 inline ElementsIterator& operator+=( size_t inc ) {
217 using blaze::reset;
218 index_ += inc;
219 if( index_ < elements_->size() )
220 pos_ = elements_->operand().begin() + elements_->idx( index_ );
221 else reset( pos_ );
222 return *this;
223 }
224 //*******************************************************************************************
225
226 //**Subtraction assignment operator**********************************************************
232 inline ElementsIterator& operator-=( size_t dec ) {
233 using blaze::reset;
234 index_ -= dec;
235 if( index_ < elements_->size() )
236 pos_ = elements_->operand().begin() + elements_->idx( index_ );
237 else reset( pos_ );
238 return *this;
239 }
240 //*******************************************************************************************
241
242 //**Prefix increment operator****************************************************************
247 inline ElementsIterator& operator++() {
248 using blaze::reset;
249 ++index_;
250 if( index_ < elements_->size() )
251 pos_ = elements_->operand().begin() + elements_->idx( index_ );
252 else reset( pos_ );
253 return *this;
254 }
255 //*******************************************************************************************
256
257 //**Postfix increment operator***************************************************************
262 inline const ElementsIterator operator++( int ) {
263 const ElementsIterator tmp( *this );
264 ++(*this);
265 return tmp;
266 }
267 //*******************************************************************************************
268
269 //**Prefix decrement operator****************************************************************
274 inline ElementsIterator& operator--() {
275 using blaze::reset;
276 --index_;
277 if( index_ < elements_->size() )
278 pos_ = elements_->operand().begin() + elements_->idx( index_ );
279 else reset( pos_ );
280 return *this;
281 }
282 //*******************************************************************************************
283
284 //**Postfix decrement operator***************************************************************
289 inline const ElementsIterator operator--( int ) {
290 const ElementsIterator tmp( *this );
291 --(*this);
292 return tmp;
293 }
294 //*******************************************************************************************
295
296 //**Subscript operator***********************************************************************
302 inline ReferenceType operator[]( size_t index ) const {
303 const IteratorType pos( elements_->operand().begin() + elements_->idx( index_ + index ) );
304 return *pos;
305 }
306 //*******************************************************************************************
307
308 //**Element access operator******************************************************************
313 inline ReferenceType operator*() const {
314 return *pos_;
315 }
316 //*******************************************************************************************
317
318 //**Element access operator******************************************************************
323 inline PointerType operator->() const {
324 return pos_;
325 }
326 //*******************************************************************************************
327
328 //**Equality operator************************************************************************
334 inline bool operator==( const ElementsIterator& rhs ) const {
335 return index_ == rhs.index_;
336 }
337 //*******************************************************************************************
338
339 //**Inequality operator**********************************************************************
345 inline bool operator!=( const ElementsIterator& rhs ) const {
346 return index_ != rhs.index_;
347 }
348 //*******************************************************************************************
349
350 //**Less-than operator***********************************************************************
356 inline bool operator<( const ElementsIterator& rhs ) const {
357 return index_ < rhs.index_;
358 }
359 //*******************************************************************************************
360
361 //**Greater-than operator********************************************************************
367 inline bool operator>( const ElementsIterator& rhs ) const {
368 return index_ > rhs.index_;
369 }
370 //*******************************************************************************************
371
372 //**Less-or-equal-than operator**************************************************************
378 inline bool operator<=( const ElementsIterator& rhs ) const {
379 return index_ <= rhs.index_;
380 }
381 //*******************************************************************************************
382
383 //**Greater-or-equal-than operator***********************************************************
389 inline bool operator>=( const ElementsIterator& rhs ) const {
390 return index_ >= rhs.index_;
391 }
392 //*******************************************************************************************
393
394 //**Subtraction operator*********************************************************************
400 inline DifferenceType operator-( const ElementsIterator& rhs ) const {
401 return index_ - rhs.index_;
402 }
403 //*******************************************************************************************
404
405 //**Addition operator************************************************************************
412 friend inline const ElementsIterator operator+( const ElementsIterator& it, size_t inc ) {
413 return ElementsIterator( it.elements_, it.index_ + inc );
414 }
415 //*******************************************************************************************
416
417 //**Addition operator************************************************************************
424 friend inline const ElementsIterator operator+( size_t inc, const ElementsIterator& it ) {
425 return ElementsIterator( it.elements_, it.index_ + inc );
426 }
427 //*******************************************************************************************
428
429 //**Subtraction operator*********************************************************************
436 friend inline const ElementsIterator operator-( const ElementsIterator& it, size_t dec ) {
437 return ElementsIterator( it.elements_, it.index_ - dec );
438 }
439 //*******************************************************************************************
440
441 private:
442 //**Member variables*************************************************************************
443 ElementsType* elements_;
444 size_t index_;
445 IteratorType pos_;
446 //*******************************************************************************************
447
448 //**Friend declarations**********************************************************************
449 template< typename ElementsType2, typename IteratorType2 > friend class ElementsIterator;
450 //*******************************************************************************************
451 };
452 //**********************************************************************************************
453
454 //**Type definitions****************************************************************************
456 using ConstIterator = ElementsIterator< const This, ConstIterator_t<VT> >;
457
459 using Iterator = If_t< IsConst_v<VT>, ConstIterator, ElementsIterator< This, Iterator_t<VT> > >;
460 //**********************************************************************************************
461
462 //**Compilation flags***************************************************************************
464 static constexpr bool simdEnabled = false;
465
467 static constexpr bool smpAssignable = VT::smpAssignable;
468
470 static constexpr bool compileTimeArgs = DataType::compileTimeArgs;
471 //**********************************************************************************************
472
473 //**Constructors********************************************************************************
476 template< typename... REAs >
477 explicit inline Elements( VT& vector, REAs... args );
478
479 Elements( const Elements& ) = default;
480 Elements( Elements&& ) = default;
482 //**********************************************************************************************
483
484 //**Destructor**********************************************************************************
487 ~Elements() = default;
489 //**********************************************************************************************
490
491 //**Data access functions***********************************************************************
494 inline Reference operator[]( size_t index );
495 inline ConstReference operator[]( size_t index ) const;
496 inline Reference at( size_t index );
497 inline ConstReference at( size_t index ) const;
498 inline Pointer data () noexcept;
499 inline ConstPointer data () const noexcept;
500 inline Iterator begin ();
501 inline ConstIterator begin () const;
502 inline ConstIterator cbegin() const;
503 inline Iterator end ();
504 inline ConstIterator end () const;
505 inline ConstIterator cend () const;
507 //**********************************************************************************************
508
509 //**Assignment operators************************************************************************
512 inline Elements& operator= ( const ElementType& rhs );
513 inline Elements& operator= ( initializer_list<ElementType> list );
514 inline Elements& operator= ( const Elements& rhs );
515 template< typename VT2 > inline Elements& operator= ( const Vector<VT2,TF>& rhs );
516 template< typename VT2 > inline Elements& operator+=( const Vector<VT2,TF>& rhs );
517 template< typename VT2 > inline Elements& operator-=( const Vector<VT2,TF>& rhs );
518 template< typename VT2 > inline Elements& operator*=( const Vector<VT2,TF>& rhs );
519 template< typename VT2 > inline Elements& operator/=( const DenseVector<VT2,TF>& rhs );
520 template< typename VT2 > inline Elements& operator%=( const Vector<VT2,TF>& rhs );
522 //**********************************************************************************************
523
524 //**Utility functions***************************************************************************
527 using DataType::idces;
528 using DataType::idx;
529 using DataType::size;
530
531 inline VT& operand() noexcept;
532 inline const VT& operand() const noexcept;
533
534 inline size_t spacing() const noexcept;
535 inline size_t capacity() const noexcept;
536 inline size_t nonZeros() const;
537 inline void reset();
539 //**********************************************************************************************
540
541 //**Numeric functions***************************************************************************
544 template< typename Other > inline Elements& scale( const Other& scalar );
546 //**********************************************************************************************
547
548 //**Expression template evaluation functions****************************************************
551 template< typename Other >
552 inline bool canAlias( const Other* alias ) const noexcept;
553
554 template< typename Other >
555 inline bool isAliased( const Other* alias ) const noexcept;
556
557 inline bool isAligned () const noexcept;
558 inline bool canSMPAssign() const noexcept;
559
560 template< typename VT2 > inline void assign ( const DenseVector <VT2,TF>& rhs );
561 template< typename VT2 > inline void assign ( const SparseVector<VT2,TF>& rhs );
562 template< typename VT2 > inline void addAssign ( const DenseVector <VT2,TF>& rhs );
563 template< typename VT2 > inline void addAssign ( const SparseVector<VT2,TF>& rhs );
564 template< typename VT2 > inline void subAssign ( const DenseVector <VT2,TF>& rhs );
565 template< typename VT2 > inline void subAssign ( const SparseVector<VT2,TF>& rhs );
566 template< typename VT2 > inline void multAssign( const DenseVector <VT2,TF>& rhs );
567 template< typename VT2 > inline void multAssign( const SparseVector<VT2,TF>& rhs );
568 template< typename VT2 > inline void divAssign ( const DenseVector <VT2,TF>& rhs );
570 //**********************************************************************************************
571
572 private:
573 //**Member variables****************************************************************************
576 Operand vector_;
578 //**********************************************************************************************
579
580 //**Compile time checks*************************************************************************
587 //**********************************************************************************************
588};
590//*************************************************************************************************
591
592
593
594
595//=================================================================================================
596//
597// CONSTRUCTORS
598//
599//=================================================================================================
600
601//*************************************************************************************************
614template< typename VT // Type of the dense vector
615 , bool TF // Transpose flag
616 , typename... CEAs > // Compile time element arguments
617template< typename... REAs > // Optional arguments
618inline Elements<VT,TF,true,CEAs...>::Elements( VT& vector, REAs... args )
619 : DataType( args... ) // Base class initialization
620 , vector_ ( vector ) // The vector containing the elements
621{
622 if( isChecked( args... ) ) {
623 for( size_t i=0UL; i<size(); ++i ) {
624 if( vector_.size() <= idx(i) ) {
625 BLAZE_THROW_INVALID_ARGUMENT( "Invalid element access index" );
626 }
627 }
628 }
629}
631//*************************************************************************************************
632
633
634
635
636//=================================================================================================
637//
638// DATA ACCESS FUNCTIONS
639//
640//=================================================================================================
641
642//*************************************************************************************************
652template< typename VT // Type of the dense vector
653 , bool TF // Transpose flag
654 , typename... CEAs > // Compile time element arguments
655inline typename Elements<VT,TF,true,CEAs...>::Reference
656 Elements<VT,TF,true,CEAs...>::operator[]( size_t index )
657{
658 BLAZE_USER_ASSERT( index < size(), "Invalid element access index" );
659 return vector_[idx(index)];
660}
662//*************************************************************************************************
663
664
665//*************************************************************************************************
675template< typename VT // Type of the dense vector
676 , bool TF // Transpose flag
677 , typename... CEAs > // Compile time element arguments
678inline typename Elements<VT,TF,true,CEAs...>::ConstReference
679 Elements<VT,TF,true,CEAs...>::operator[]( size_t index ) const
680{
681 BLAZE_USER_ASSERT( index < size(), "Invalid element access index" );
682 return const_cast<const VT&>( vector_ )[idx(index)];
683}
685//*************************************************************************************************
686
687
688//*************************************************************************************************
699template< typename VT // Type of the dense vector
700 , bool TF // Transpose flag
701 , typename... CEAs > // Compile time element arguments
702inline typename Elements<VT,TF,true,CEAs...>::Reference
703 Elements<VT,TF,true,CEAs...>::at( size_t index )
704{
705 if( index >= size() ) {
706 BLAZE_THROW_OUT_OF_RANGE( "Invalid element access index" );
707 }
708 return (*this)[index];
709}
711//*************************************************************************************************
712
713
714//*************************************************************************************************
725template< typename VT // Type of the dense vector
726 , bool TF // Transpose flag
727 , typename... CEAs > // Compile time element arguments
728inline typename Elements<VT,TF,true,CEAs...>::ConstReference
729 Elements<VT,TF,true,CEAs...>::at( size_t index ) const
730{
731 if( index >= size() ) {
732 BLAZE_THROW_OUT_OF_RANGE( "Invalid element access index" );
733 }
734 return (*this)[index];
735}
737//*************************************************************************************************
738
739
740//*************************************************************************************************
748template< typename VT // Type of the dense vector
749 , bool TF // Transpose flag
750 , typename... CEAs > // Compile time element arguments
751inline typename Elements<VT,TF,true,CEAs...>::Pointer
753{
754 return vector_.data() + idx(0UL);
755}
757//*************************************************************************************************
758
759
760//*************************************************************************************************
768template< typename VT // Type of the dense vector
769 , bool TF // Transpose flag
770 , typename... CEAs > // Compile time element arguments
771inline typename Elements<VT,TF,true,CEAs...>::ConstPointer
773{
774 return vector_.data() + idx(0UL);
775}
777//*************************************************************************************************
778
779
780//*************************************************************************************************
788template< typename VT // Type of the dense vector
789 , bool TF // Transpose flag
790 , typename... CEAs > // Compile time element arguments
791inline typename Elements<VT,TF,true,CEAs...>::Iterator
793{
794 return Iterator( this, 0UL );
795}
797//*************************************************************************************************
798
799
800//*************************************************************************************************
808template< typename VT // Type of the dense vector
809 , bool TF // Transpose flag
810 , typename... CEAs > // Compile time element arguments
811inline typename Elements<VT,TF,true,CEAs...>::ConstIterator
813{
814 return ConstIterator( this, 0UL );
815}
817//*************************************************************************************************
818
819
820//*************************************************************************************************
828template< typename VT // Type of the dense vector
829 , bool TF // Transpose flag
830 , typename... CEAs > // Compile time element arguments
831inline typename Elements<VT,TF,true,CEAs...>::ConstIterator
833{
834 return ConstIterator( this, 0UL );
835}
837//*************************************************************************************************
838
839
840//*************************************************************************************************
848template< typename VT // Type of the dense vector
849 , bool TF // Transpose flag
850 , typename... CEAs > // Compile time element arguments
851inline typename Elements<VT,TF,true,CEAs...>::Iterator
853{
854 return Iterator( this, size() );
855}
857//*************************************************************************************************
858
859
860//*************************************************************************************************
868template< typename VT // Type of the dense vector
869 , bool TF // Transpose flag
870 , typename... CEAs > // Compile time element arguments
871inline typename Elements<VT,TF,true,CEAs...>::ConstIterator
873{
874 return ConstIterator( this, size() );
875}
877//*************************************************************************************************
878
879
880//*************************************************************************************************
888template< typename VT // Type of the dense vector
889 , bool TF // Transpose flag
890 , typename... CEAs > // Compile time element arguments
891inline typename Elements<VT,TF,true,CEAs...>::ConstIterator
893{
894 return ConstIterator( this, size() );
895}
897//*************************************************************************************************
898
899
900
901
902//=================================================================================================
903//
904// ASSIGNMENT OPERATORS
905//
906//=================================================================================================
907
908//*************************************************************************************************
915template< typename VT // Type of the dense vector
916 , bool TF // Transpose flag
917 , typename... CEAs > // Compile time element arguments
918inline Elements<VT,TF,true,CEAs...>&
919 Elements<VT,TF,true,CEAs...>::operator=( const ElementType& rhs )
920{
921 decltype(auto) left( derestrict( vector_ ) );
922
923 for( size_t i=0UL; i<size(); ++i ) {
924 const size_t index( idx(i) );
925 if( !IsRestricted_v<VT> || trySet( vector_, index, rhs ) )
926 left[index] = rhs;
927 }
928
929 return *this;
930}
932//*************************************************************************************************
933
934
935//*************************************************************************************************
951template< typename VT // Type of the dense vector
952 , bool TF // Transpose flag
953 , typename... CEAs > // Compile time element arguments
954inline Elements<VT,TF,true,CEAs...>&
955 Elements<VT,TF,true,CEAs...>::operator=( initializer_list<ElementType> list )
956{
957 if( list.size() > size() ) {
958 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to elements" );
959 }
960
961 const InitializerVector<ElementType,TF> tmp( list, size() );
962
963 if( IsRestricted_v<VT> ) {
964 for( size_t i=0UL; i<size(); ++i ) {
965 if( !trySet( vector_, idx(i), tmp[i] ) ) {
966 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted vector" );
967 }
968 }
969 }
970
971 decltype(auto) left( derestrict( vector_ ) );
972 for( size_t i=0UL; i<size(); ++i ) {
973 left[idx(i)] = tmp[i];
974 }
975
976 BLAZE_INTERNAL_ASSERT( isIntact( vector_ ), "Invariant violation detected" );
977
978 return *this;
979}
981//*************************************************************************************************
982
983
984//*************************************************************************************************
996template< typename VT // Type of the dense vector
997 , bool TF // Transpose flag
998 , typename... CEAs > // Compile time element arguments
999inline Elements<VT,TF,true,CEAs...>&
1000 Elements<VT,TF,true,CEAs...>::operator=( const Elements& rhs )
1001{
1004
1005 if( &rhs == this || ( &vector_ == &rhs.vector_ && compareIndices( *this, rhs ) ) )
1006 return *this;
1007
1008 if( size() != rhs.size() ) {
1009 BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
1010 }
1011
1012 if( IsRestricted_v<VT> ) {
1013 for( size_t i=0UL; i<size(); ++i ) {
1014 if( !trySet( vector_, idx(i), rhs[i] ) ) {
1015 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted vector" );
1016 }
1017 }
1018 }
1019
1020 decltype(auto) left( derestrict( *this ) );
1021
1022 if( rhs.canAlias( this ) ) {
1023 const ResultType tmp( rhs );
1024 smpAssign( left, tmp );
1025 }
1026 else {
1027 smpAssign( left, rhs );
1028 }
1029
1030 BLAZE_INTERNAL_ASSERT( isIntact( vector_ ), "Invariant violation detected" );
1031
1032 return *this;
1033}
1035//*************************************************************************************************
1036
1037
1038//*************************************************************************************************
1050template< typename VT // Type of the dense vector
1051 , bool TF // Transpose flag
1052 , typename... CEAs > // Compile time element arguments
1053template< typename VT2 > // Type of the right-hand side vector
1054inline Elements<VT,TF,true,CEAs...>&
1055 Elements<VT,TF,true,CEAs...>::operator=( const Vector<VT2,TF>& rhs )
1056{
1059
1060 if( size() != (*rhs).size() ) {
1061 BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
1062 }
1063
1064 using Right = If_t< IsRestricted_v<VT>, CompositeType_t<VT2>, const VT2& >;
1065 Right right( *rhs );
1066
1067 if( IsRestricted_v<VT> ) {
1068 for( size_t i=0UL; i<size(); ++i ) {
1069 if( !trySet( vector_, idx(i), right[i] ) ) {
1070 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted vector" );
1071 }
1072 }
1073 }
1074
1075 decltype(auto) left( derestrict( *this ) );
1076
1077 if( IsReference_v<Right> && right.canAlias( this ) ) {
1078 const ResultType_t<VT2> tmp( right );
1079 smpAssign( left, tmp );
1080 }
1081 else {
1082 if( IsSparseVector_v<VT2> )
1083 reset();
1084 smpAssign( left, right );
1085 }
1086
1087 BLAZE_INTERNAL_ASSERT( isIntact( vector_ ), "Invariant violation detected" );
1088
1089 return *this;
1090}
1092//*************************************************************************************************
1093
1094
1095//*************************************************************************************************
1107template< typename VT // Type of the dense vector
1108 , bool TF // Transpose flag
1109 , typename... CEAs > // Compile time element arguments
1110template< typename VT2 > // Type of the right-hand side vector
1111inline Elements<VT,TF,true,CEAs...>&
1112 Elements<VT,TF,true,CEAs...>::operator+=( const Vector<VT2,TF>& rhs )
1113{
1116
1117 if( size() != (*rhs).size() ) {
1118 BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
1119 }
1120
1121 using Right = If_t< IsRestricted_v<VT>, CompositeType_t<VT2>, const VT2& >;
1122 Right right( *rhs );
1123
1124 if( IsRestricted_v<VT> ) {
1125 for( size_t i=0UL; i<size(); ++i ) {
1126 if( !tryAdd( vector_, idx(i), right[i] ) ) {
1127 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted vector" );
1128 }
1129 }
1130 }
1131
1132 decltype(auto) left( derestrict( *this ) );
1133
1134 if( IsReference_v<Right> && right.canAlias( this ) ) {
1135 const ResultType_t<VT2> tmp( right );
1136 smpAddAssign( left, tmp );
1137 }
1138 else {
1139 smpAddAssign( left, right );
1140 }
1141
1142 BLAZE_INTERNAL_ASSERT( isIntact( vector_ ), "Invariant violation detected" );
1143
1144 return *this;
1145}
1147//*************************************************************************************************
1148
1149
1150//*************************************************************************************************
1162template< typename VT // Type of the dense vector
1163 , bool TF // Transpose flag
1164 , typename... CEAs > // Compile time element arguments
1165template< typename VT2 > // Type of the right-hand side vector
1166inline Elements<VT,TF,true,CEAs...>&
1167 Elements<VT,TF,true,CEAs...>::operator-=( const Vector<VT2,TF>& rhs )
1168{
1171
1172 if( size() != (*rhs).size() ) {
1173 BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
1174 }
1175
1176 using Right = If_t< IsRestricted_v<VT>, CompositeType_t<VT2>, const VT2& >;
1177 Right right( *rhs );
1178
1179 if( IsRestricted_v<VT> ) {
1180 for( size_t i=0UL; i<size(); ++i ) {
1181 if( !trySub( vector_, idx(i), right[i] ) ) {
1182 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted vector" );
1183 }
1184 }
1185 }
1186
1187 decltype(auto) left( derestrict( *this ) );
1188
1189 if( IsReference_v<Right> && right.canAlias( this ) ) {
1190 const ResultType_t<VT2> tmp( right );
1191 smpSubAssign( left, tmp );
1192 }
1193 else {
1194 smpSubAssign( left, right );
1195 }
1196
1197 BLAZE_INTERNAL_ASSERT( isIntact( vector_ ), "Invariant violation detected" );
1198
1199 return *this;
1200}
1202//*************************************************************************************************
1203
1204
1205//*************************************************************************************************
1218template< typename VT // Type of the dense vector
1219 , bool TF // Transpose flag
1220 , typename... CEAs > // Compile time element arguments
1221template< typename VT2 > // Type of the right-hand side vector
1222inline Elements<VT,TF,true,CEAs...>&
1223 Elements<VT,TF,true,CEAs...>::operator*=( const Vector<VT2,TF>& rhs )
1224{
1227
1228 if( size() != (*rhs).size() ) {
1229 BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
1230 }
1231
1232 using Right = If_t< IsRestricted_v<VT>, CompositeType_t<VT2>, const VT2& >;
1233 Right right( *rhs );
1234
1235 if( IsRestricted_v<VT> ) {
1236 for( size_t i=0UL; i<size(); ++i ) {
1237 if( !tryMult( vector_, idx(i), right[i] ) ) {
1238 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted vector" );
1239 }
1240 }
1241 }
1242
1243 decltype(auto) left( derestrict( *this ) );
1244
1245 if( IsReference_v<Right> && right.canAlias( this ) ) {
1246 const ResultType_t<VT2> tmp( right );
1247 smpMultAssign( left, tmp );
1248 }
1249 else {
1250 smpMultAssign( left, right );
1251 }
1252
1253 BLAZE_INTERNAL_ASSERT( isIntact( vector_ ), "Invariant violation detected" );
1254
1255 return *this;
1256}
1258//*************************************************************************************************
1259
1260
1261//*************************************************************************************************
1273template< typename VT // Type of the dense vector
1274 , bool TF // Transpose flag
1275 , typename... CEAs > // Compile time element arguments
1276template< typename VT2 > // Type of the right-hand side dense vector
1277inline Elements<VT,TF,true,CEAs...>&
1278 Elements<VT,TF,true,CEAs...>::operator/=( const DenseVector<VT2,TF>& rhs )
1279{
1282
1283 if( size() != (*rhs).size() ) {
1284 BLAZE_THROW_INVALID_ARGUMENT( "Vector sizes do not match" );
1285 }
1286
1287 using Right = If_t< IsRestricted_v<VT>, CompositeType_t<VT2>, const VT2& >;
1288 Right right( *rhs );
1289
1290 if( IsRestricted_v<VT> ) {
1291 for( size_t i=0UL; i<size(); ++i ) {
1292 if( !tryDiv( vector_, idx(i), right[i] ) ) {
1293 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted vector" );
1294 }
1295 }
1296 }
1297
1298 decltype(auto) left( derestrict( *this ) );
1299
1300 if( IsReference_v<Right> && right.canAlias( this ) ) {
1301 const ResultType_t<VT2> tmp( right );
1302 smpDivAssign( left, tmp );
1303 }
1304 else {
1305 smpDivAssign( left, right );
1306 }
1307
1308 BLAZE_INTERNAL_ASSERT( isIntact( vector_ ), "Invariant violation detected" );
1309
1310 return *this;
1311}
1313//*************************************************************************************************
1314
1315
1316//*************************************************************************************************
1329template< typename VT // Type of the dense vector
1330 , bool TF // Transpose flag
1331 , typename... CEAs > // Compile time element arguments
1332template< typename VT2 > // Type of the right-hand side vector
1333inline Elements<VT,TF,true,CEAs...>&
1334 Elements<VT,TF,true,CEAs...>::operator%=( const Vector<VT2,TF>& rhs )
1335{
1336 using blaze::assign;
1337
1340
1341 using CrossType = CrossTrait_t< ResultType, ResultType_t<VT2> >;
1342
1346
1347 if( size() != 3UL || (*rhs).size() != 3UL ) {
1348 BLAZE_THROW_INVALID_ARGUMENT( "Invalid vector size for cross product" );
1349 }
1350
1351 const CrossType tmp( *this % (*rhs) );
1352
1353 if( IsRestricted_v<VT> ) {
1354 for( size_t i=0UL; i<size(); ++i ) {
1355 if( !trySet( vector_, idx(i), tmp[i] ) ) {
1356 BLAZE_THROW_INVALID_ARGUMENT( "Invalid assignment to restricted vector" );
1357 }
1358 }
1359 }
1360
1361 decltype(auto) left( derestrict( *this ) );
1362
1363 assign( left, tmp );
1364
1365 BLAZE_INTERNAL_ASSERT( isIntact( vector_ ), "Invariant violation detected" );
1366
1367 return *this;
1368}
1370//*************************************************************************************************
1371
1372
1373
1374
1375//=================================================================================================
1376//
1377// UTILITY FUNCTIONS
1378//
1379//=================================================================================================
1380
1381//*************************************************************************************************
1387template< typename VT // Type of the dense vector
1388 , bool TF // Transpose flag
1389 , typename... CEAs > // Compile time element arguments
1390inline VT& Elements<VT,TF,true,CEAs...>::operand() noexcept
1391{
1392 return vector_;
1393}
1395//*************************************************************************************************
1396
1397
1398//*************************************************************************************************
1404template< typename VT // Type of the dense vector
1405 , bool TF // Transpose flag
1406 , typename... CEAs > // Compile time element arguments
1407inline const VT& Elements<VT,TF,true,CEAs...>::operand() const noexcept
1408{
1409 return vector_;
1410}
1412//*************************************************************************************************
1413
1414
1415//*************************************************************************************************
1421template< typename VT // Type of the dense vector
1422 , bool TF // Transpose flag
1423 , typename... CEAs > // Compile time element arguments
1424inline size_t Elements<VT,TF,true,CEAs...>::spacing() const noexcept
1425{
1426 return size();
1427}
1429//*************************************************************************************************
1430
1431
1432//*************************************************************************************************
1438template< typename VT // Type of the dense vector
1439 , bool TF // Transpose flag
1440 , typename... CEAs > // Compile time element arguments
1441inline size_t Elements<VT,TF,true,CEAs...>::capacity() const noexcept
1442{
1443 return size();
1444}
1446//*************************************************************************************************
1447
1448
1449//*************************************************************************************************
1458template< typename VT // Type of the dense vector
1459 , bool TF // Transpose flag
1460 , typename... CEAs > // Compile time element arguments
1461inline size_t Elements<VT,TF,true,CEAs...>::nonZeros() const
1462{
1463 size_t nonzeros( 0 );
1464
1465 for( size_t i=0UL; i<size(); ++i ) {
1466 if( !isDefault( vector_[idx(i)] ) )
1467 ++nonzeros;
1468 }
1469
1470 return nonzeros;
1471}
1473//*************************************************************************************************
1474
1475
1476//*************************************************************************************************
1482template< typename VT // Type of the dense vector
1483 , bool TF // Transpose flag
1484 , typename... CEAs > // Compile time element arguments
1486{
1487 using blaze::clear;
1488
1489 for( size_t i=0UL; i<size(); ++i )
1490 clear( vector_[idx(i)] );
1491}
1493//*************************************************************************************************
1494
1495
1496
1497
1498//=================================================================================================
1499//
1500// NUMERIC FUNCTIONS
1501//
1502//=================================================================================================
1503
1504//*************************************************************************************************
1515template< typename VT // Type of the dense vector
1516 , bool TF // Transpose flag
1517 , typename... CEAs > // Compile time element arguments
1518template< typename Other > // Data type of the scalar value
1519inline Elements<VT,TF,true,CEAs...>&
1520 Elements<VT,TF,true,CEAs...>::scale( const Other& scalar )
1521{
1522 for( size_t i=0UL; i<size(); ++i )
1523 vector_[idx(i)] *= scalar;
1524 return *this;
1525}
1527//*************************************************************************************************
1528
1529
1530
1531
1532//=================================================================================================
1533//
1534// EXPRESSION TEMPLATE EVALUATION FUNCTIONS
1535//
1536//=================================================================================================
1537
1538//*************************************************************************************************
1549template< typename VT // Type of the dense vector
1550 , bool TF // Transpose flag
1551 , typename... CEAs > // Compile time element arguments
1552template< typename Other > // Data type of the foreign expression
1553inline bool Elements<VT,TF,true,CEAs...>::canAlias( const Other* alias ) const noexcept
1554{
1555 return vector_.isAliased( &unview( *alias ) );
1556}
1558//*************************************************************************************************
1559
1560
1561//*************************************************************************************************
1572template< typename VT // Type of the dense vector
1573 , bool TF // Transpose flag
1574 , typename... CEAs > // Compile time element arguments
1575template< typename Other > // Data type of the foreign expression
1576inline bool Elements<VT,TF,true,CEAs...>::isAliased( const Other* alias ) const noexcept
1577{
1578 return vector_.isAliased( &unview( *alias ) );
1579}
1581//*************************************************************************************************
1582
1583
1584//*************************************************************************************************
1594template< typename VT // Type of the dense vector
1595 , bool TF // Transpose flag
1596 , typename... CEAs > // Compile time element arguments
1597inline bool Elements<VT,TF,true,CEAs...>::isAligned() const noexcept
1598{
1599 return false;
1600}
1602//*************************************************************************************************
1603
1604
1605//*************************************************************************************************
1616template< typename VT // Type of the dense vector
1617 , bool TF // Transpose flag
1618 , typename... CEAs > // Compile time element arguments
1619inline bool Elements<VT,TF,true,CEAs...>::canSMPAssign() const noexcept
1620{
1621 return ( size() > SMP_DVECASSIGN_THRESHOLD );
1622}
1624//*************************************************************************************************
1625
1626
1627//*************************************************************************************************
1639template< typename VT // Type of the dense vector
1640 , bool TF // Transpose flag
1641 , typename... CEAs > // Compile time element arguments
1642template< typename VT2 > // Type of the right-hand side dense vector
1643inline void Elements<VT,TF,true,CEAs...>::assign( const DenseVector<VT2,TF>& rhs )
1644{
1645 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1646
1647 const size_t ipos( prevMultiple( size(), 2UL ) );
1648 BLAZE_INTERNAL_ASSERT( ipos <= size(), "Invalid end calculation" );
1649
1650 for( size_t i=0UL; i<ipos; i+=2UL ) {
1651 vector_[idx(i )] = (*rhs)[i ];
1652 vector_[idx(i+1UL)] = (*rhs)[i+1UL];
1653 }
1654 if( ipos < size() ) {
1655 vector_[idx(ipos)] = (*rhs)[ipos];
1656 }
1657}
1659//*************************************************************************************************
1660
1661
1662//*************************************************************************************************
1674template< typename VT // Type of the dense vector
1675 , bool TF // Transpose flag
1676 , typename... CEAs > // Compile time element arguments
1677template< typename VT2 > // Type of the right-hand side sparse vector
1678inline void Elements<VT,TF,true,CEAs...>::assign( const SparseVector<VT2,TF>& rhs )
1679{
1680 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1681
1682 for( ConstIterator_t<VT2> element=(*rhs).begin(); element!=(*rhs).end(); ++element )
1683 vector_[idx(element->index())] = element->value();
1684}
1686//*************************************************************************************************
1687
1688
1689//*************************************************************************************************
1701template< typename VT // Type of the dense vector
1702 , bool TF // Transpose flag
1703 , typename... CEAs > // Compile time element arguments
1704template< typename VT2 > // Type of the right-hand side dense vector
1705inline void Elements<VT,TF,true,CEAs...>::addAssign( const DenseVector<VT2,TF>& rhs )
1706{
1707 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1708
1709 const size_t ipos( prevMultiple( size(), 2UL ) );
1710 BLAZE_INTERNAL_ASSERT( ipos <= size(), "Invalid end calculation" );
1711
1712 for( size_t i=0UL; i<ipos; i+=2UL ) {
1713 vector_[idx(i )] += (*rhs)[i ];
1714 vector_[idx(i+1UL)] += (*rhs)[i+1UL];
1715 }
1716 if( ipos < size() ) {
1717 vector_[idx(ipos)] += (*rhs)[ipos];
1718 }
1719}
1721//*************************************************************************************************
1722
1723
1724//*************************************************************************************************
1736template< typename VT // Type of the dense vector
1737 , bool TF // Transpose flag
1738 , typename... CEAs > // Compile time element arguments
1739template< typename VT2 > // Type of the right-hand side sparse vector
1740inline void Elements<VT,TF,true,CEAs...>::addAssign( const SparseVector<VT2,TF>& rhs )
1741{
1742 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1743
1744 for( ConstIterator_t<VT2> element=(*rhs).begin(); element!=(*rhs).end(); ++element )
1745 vector_[idx(element->index())] += element->value();
1746}
1748//*************************************************************************************************
1749
1750
1751//*************************************************************************************************
1763template< typename VT // Type of the dense vector
1764 , bool TF // Transpose flag
1765 , typename... CEAs > // Compile time element arguments
1766template< typename VT2 > // Type of the right-hand side dense vector
1767inline void Elements<VT,TF,true,CEAs...>::subAssign( const DenseVector<VT2,TF>& rhs )
1768{
1769 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1770
1771 const size_t ipos( prevMultiple( size(), 2UL ) );
1772 BLAZE_INTERNAL_ASSERT( ipos <= size(), "Invalid end calculation" );
1773
1774 for( size_t i=0UL; i<ipos; i+=2UL ) {
1775 vector_[idx(i )] -= (*rhs)[i ];
1776 vector_[idx(i+1UL)] -= (*rhs)[i+1UL];
1777 }
1778 if( ipos < size() ) {
1779 vector_[idx(ipos)] -= (*rhs)[ipos];
1780 }
1781}
1783//*************************************************************************************************
1784
1785
1786//*************************************************************************************************
1798template< typename VT // Type of the dense vector
1799 , bool TF // Transpose flag
1800 , typename... CEAs > // Compile time element arguments
1801template< typename VT2 > // Type of the right-hand side sparse vector
1802inline void Elements<VT,TF,true,CEAs...>::subAssign( const SparseVector<VT2,TF>& rhs )
1803{
1804 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1805
1806 for( ConstIterator_t<VT2> element=(*rhs).begin(); element!=(*rhs).end(); ++element )
1807 vector_[idx(element->index())] -= element->value();
1808}
1810//*************************************************************************************************
1811
1812
1813//*************************************************************************************************
1825template< typename VT // Type of the dense vector
1826 , bool TF // Transpose flag
1827 , typename... CEAs > // Compile time element arguments
1828template< typename VT2 > // Type of the right-hand side dense vector
1829inline void Elements<VT,TF,true,CEAs...>::multAssign( const DenseVector<VT2,TF>& rhs )
1830{
1831 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1832
1833 const size_t ipos( prevMultiple( size(), 2UL ) );
1834 BLAZE_INTERNAL_ASSERT( ipos <= size(), "Invalid end calculation" );
1835
1836 for( size_t i=0UL; i<ipos; i+=2UL ) {
1837 vector_[idx(i )] *= (*rhs)[i ];
1838 vector_[idx(i+1UL)] *= (*rhs)[i+1UL];
1839 }
1840 if( ipos < size() ) {
1841 vector_[idx(ipos)] *= (*rhs)[ipos];
1842 }
1843}
1845//*************************************************************************************************
1846
1847
1848//*************************************************************************************************
1860template< typename VT // Type of the dense vector
1861 , bool TF // Transpose flag
1862 , typename... CEAs > // Compile time element arguments
1863template< typename VT2 > // Type of the right-hand side sparse vector
1864inline void Elements<VT,TF,true,CEAs...>::multAssign( const SparseVector<VT2,TF>& rhs )
1865{
1866 using blaze::reset;
1867
1868 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1869
1870 size_t i( 0UL );
1871
1872 for( ConstIterator_t<VT2> element=(*rhs).begin(); element!=(*rhs).end(); ++element ) {
1873 const size_t index( element->index() );
1874 for( ; i<index; ++i )
1875 reset( vector_[idx(i)] );
1876 vector_[idx(i)] *= element->value();
1877 ++i;
1878 }
1879
1880 for( ; i<size(); ++i ) {
1881 reset( vector_[idx(i)] );
1882 }
1883}
1885//*************************************************************************************************
1886
1887
1888//*************************************************************************************************
1900template< typename VT // Type of the dense vector
1901 , bool TF // Transpose flag
1902 , typename... CEAs > // Compile time element arguments
1903template< typename VT2 > // Type of the right-hand side dense vector
1904inline void Elements<VT,TF,true,CEAs...>::divAssign( const DenseVector<VT2,TF>& rhs )
1905{
1906 BLAZE_INTERNAL_ASSERT( size() == (*rhs).size(), "Invalid vector sizes" );
1907
1908 const size_t ipos( prevMultiple( size(), 2UL ) );
1909 BLAZE_INTERNAL_ASSERT( ipos <= size(), "Invalid end calculation" );
1910
1911 for( size_t i=0UL; i<ipos; i+=2UL ) {
1912 vector_[idx(i )] /= (*rhs)[i ];
1913 vector_[idx(i+1UL)] /= (*rhs)[i+1UL];
1914 }
1915 if( ipos < size() ) {
1916 vector_[idx(ipos)] /= (*rhs)[ipos];
1917 }
1918}
1920//*************************************************************************************************
1921
1922
1923
1924
1925
1926
1927
1928
1929//=================================================================================================
1930//
1931// CLASS TEMPLATE SPECIALIZATION FOR DVECDVECCROSSEXPR
1932//
1933//=================================================================================================
1934
1935//*************************************************************************************************
1943template< typename VT1 // Type of the left-hand side dense vector
1944 , typename VT2 // Type of the right-hand side dense vector
1945 , bool TF // Transpose flag
1946 , typename... CEAs > // Compile time element arguments
1947class Elements< const DVecDVecCrossExpr<VT1,VT2,TF>, TF, true, CEAs... >
1948 : public View< DenseVector< Elements< const DVecDVecCrossExpr<VT1,VT2,TF>, TF, true, CEAs... >, TF > >
1949 , private ElementsData<CEAs...>
1950{
1951 private:
1952 //**Type definitions****************************************************************************
1953 using CPE = DVecDVecCrossExpr<VT1,VT2,TF>;
1954 using RT = ResultType_t<CPE>;
1955 using DataType = ElementsData<CEAs...>;
1956 //**********************************************************************************************
1957
1958 //**Compile time flags**************************************************************************
1959 using DataType::N;
1960 //**********************************************************************************************
1961
1962 public:
1963 //**Type definitions****************************************************************************
1965 using This = Elements<const CPE,TF,true,CEAs...>;
1966
1968 using BaseType = View< DenseVector<This,TF> >;
1969
1970 using ViewedType = CPE;
1971 using ResultType = ElementsTrait_t<RT,N>;
1972 using TransposeType = TransposeType_t<ResultType>;
1973 using ElementType = ElementType_t<CPE>;
1974 using ReturnType = ReturnType_t<CPE>;
1975 using CompositeType = const ResultType;
1976 //**********************************************************************************************
1977
1978 //**Compilation flags***************************************************************************
1980 static constexpr bool simdEnabled = false;
1981
1983 static constexpr bool smpAssignable = false;
1984
1986 static constexpr bool compileTimeArgs = DataType::compileTimeArgs;
1987 //**********************************************************************************************
1988
1989 //**Constructor*********************************************************************************
1996 template< typename... REAs > // Optional element arguments
1997 explicit inline Elements( const CPE& vector, REAs... args )
1998 : DataType( args... ) // Base class initialization
1999 , vector_ ( vector ) // The dense vector/dense vector cross product expression
2000 {
2001 if( isChecked( args... ) ) {
2002 for( size_t i=0UL; i<size(); ++i ) {
2003 if( vector_.size() <= idx(i) ) {
2004 BLAZE_THROW_INVALID_ARGUMENT( "Invalid element access index" );
2005 }
2006 }
2007 }
2008 }
2009 //**********************************************************************************************
2010
2011 //**Subscript operator**************************************************************************
2017 inline ReturnType operator[]( size_t index ) const {
2018 BLAZE_INTERNAL_ASSERT( index < size(), "Invalid vector access index" );
2019 return vector_[idx(index)];
2020 }
2021 //**********************************************************************************************
2022
2023 //**At function*********************************************************************************
2030 inline ReturnType at( size_t index ) const {
2031 if( index >= size() ) {
2032 BLAZE_THROW_OUT_OF_RANGE( "Invalid vector access index" );
2033 }
2034 return (*this)[index];
2035 }
2036 //**********************************************************************************************
2037
2038 //**********************************************************************************************
2039 using DataType::idces;
2040 using DataType::idx;
2041 using DataType::size;
2042 //**********************************************************************************************
2043
2044 //**Operand access******************************************************************************
2049 inline CPE operand() const noexcept {
2050 return vector_;
2051 }
2052 //**********************************************************************************************
2053
2054 //**********************************************************************************************
2060 template< typename T >
2061 inline bool canAlias( const T* alias ) const noexcept {
2062 return vector_.canAlias( &unview( *alias ) );
2063 }
2064 //**********************************************************************************************
2065
2066 //**********************************************************************************************
2072 template< typename T >
2073 inline bool isAliased( const T* alias ) const noexcept {
2074 return vector_.isAliased( &unview( *alias ) );
2075 }
2076 //**********************************************************************************************
2077
2078 private:
2079 //**Member variables****************************************************************************
2080 CPE vector_;
2081 //**********************************************************************************************
2082};
2084//*************************************************************************************************
2085
2086
2087
2088
2089
2090
2091
2092
2093//=================================================================================================
2094//
2095// CLASS TEMPLATE SPECIALIZATION FOR DVECSVECCROSSEXPR
2096//
2097//=================================================================================================
2098
2099//*************************************************************************************************
2107template< typename VT1 // Type of the left-hand side dense vector
2108 , typename VT2 // Type of the right-hand side sparse vector
2109 , bool TF // Transpose flag
2110 , typename... CEAs > // Compile time element arguments
2111class Elements< const DVecSVecCrossExpr<VT1,VT2,TF>, TF, true, CEAs... >
2112 : public View< DenseVector< Elements< const DVecSVecCrossExpr<VT1,VT2,TF>, TF, true, CEAs... >, TF > >
2113 , private ElementsData<CEAs...>
2114{
2115 private:
2116 //**Type definitions****************************************************************************
2117 using CPE = DVecSVecCrossExpr<VT1,VT2,TF>;
2118 using RT = ResultType_t<CPE>;
2119 using DataType = ElementsData<CEAs...>;
2120 //**********************************************************************************************
2121
2122 //**Compile time flags**************************************************************************
2123 using DataType::N;
2124 //**********************************************************************************************
2125
2126 public:
2127 //**Type definitions****************************************************************************
2129 using This = Elements<const CPE,TF,true,CEAs...>;
2130
2132 using BaseType = View< DenseVector<This,TF> >;
2133
2134 using ViewedType = CPE;
2135 using ResultType = ElementsTrait_t<RT,N>;
2136 using TransposeType = TransposeType_t<ResultType>;
2137 using ElementType = ElementType_t<CPE>;
2138 using ReturnType = ReturnType_t<CPE>;
2139 using CompositeType = const ResultType;
2140 //**********************************************************************************************
2141
2142 //**Compilation flags***************************************************************************
2144 static constexpr bool simdEnabled = false;
2145
2147 static constexpr bool smpAssignable = false;
2148
2150 static constexpr bool compileTimeArgs = DataType::compileTimeArgs;
2151 //**********************************************************************************************
2152
2153 //**Constructor*********************************************************************************
2160 template< typename... REAs > // Optional element arguments
2161 explicit inline Elements( const CPE& vector, REAs... args )
2162 : DataType( args... ) // Base class initialization
2163 , vector_ ( vector ) // The dense vector/sparse vector cross product expression
2164 {
2165 if( isChecked( args... ) ) {
2166 for( size_t i=0UL; i<size(); ++i ) {
2167 if( vector_.size() <= idx(i) ) {
2168 BLAZE_THROW_INVALID_ARGUMENT( "Invalid element access index" );
2169 }
2170 }
2171 }
2172 }
2173 //**********************************************************************************************
2174
2175 //**Subscript operator**************************************************************************
2181 inline ReturnType operator[]( size_t index ) const {
2182 BLAZE_INTERNAL_ASSERT( index < size(), "Invalid vector access index" );
2183 return vector_[idx(index)];
2184 }
2185 //**********************************************************************************************
2186
2187 //**At function*********************************************************************************
2194 inline ReturnType at( size_t index ) const {
2195 if( index >= size() ) {
2196 BLAZE_THROW_OUT_OF_RANGE( "Invalid vector access index" );
2197 }
2198 return (*this)[index];
2199 }
2200 //**********************************************************************************************
2201
2202 //**********************************************************************************************
2203 using DataType::idces;
2204 using DataType::idx;
2205 using DataType::size;
2206 //**********************************************************************************************
2207
2208 //**Operand access******************************************************************************
2213 inline CPE operand() const noexcept {
2214 return vector_;
2215 }
2216 //**********************************************************************************************
2217
2218 //**********************************************************************************************
2224 template< typename T >
2225 inline bool canAlias( const T* alias ) const noexcept {
2226 return vector_.canAlias( &unview( *alias ) );
2227 }
2228 //**********************************************************************************************
2229
2230 //**********************************************************************************************
2236 template< typename T >
2237 inline bool isAliased( const T* alias ) const noexcept {
2238 return vector_.isAliased( &unview( *alias ) );
2239 }
2240 //**********************************************************************************************
2241
2242 private:
2243 //**Member variables****************************************************************************
2244 CPE vector_;
2245 //**********************************************************************************************
2246};
2248//*************************************************************************************************
2249
2250
2251
2252
2253
2254
2255
2256
2257//=================================================================================================
2258//
2259// CLASS TEMPLATE SPECIALIZATION FOR SVECDVECCROSSEXPR
2260//
2261//=================================================================================================
2262
2263//*************************************************************************************************
2271template< typename VT1 // Type of the left-hand side sparse vector
2272 , typename VT2 // Type of the right-hand side dense vector
2273 , bool TF // Transpose flag
2274 , typename... CEAs > // Compile time element arguments
2275class Elements< const SVecDVecCrossExpr<VT1,VT2,TF>, TF, true, CEAs... >
2276 : public View< DenseVector< Elements< const SVecDVecCrossExpr<VT1,VT2,TF>, TF, true, CEAs... >, TF > >
2277 , private ElementsData<CEAs...>
2278{
2279 private:
2280 //**Type definitions****************************************************************************
2281 using CPE = SVecDVecCrossExpr<VT1,VT2,TF>;
2282 using RT = ResultType_t<CPE>;
2283 using DataType = ElementsData<CEAs...>;
2284 //**********************************************************************************************
2285
2286 //**Compile time flags**************************************************************************
2287 using DataType::N;
2288 //**********************************************************************************************
2289
2290 public:
2291 //**Type definitions****************************************************************************
2293 using This = Elements<const CPE,TF,true,CEAs...>;
2294
2296 using BaseType = View< DenseVector<This,TF> >;
2297
2298 using ViewedType = CPE;
2299 using ResultType = ElementsTrait_t<RT,N>;
2300 using TransposeType = TransposeType_t<ResultType>;
2301 using ElementType = ElementType_t<CPE>;
2302 using ReturnType = ReturnType_t<CPE>;
2303 using CompositeType = const ResultType;
2304 //**********************************************************************************************
2305
2306 //**Compilation flags***************************************************************************
2308 static constexpr bool simdEnabled = false;
2309
2311 static constexpr bool smpAssignable = false;
2312
2314 static constexpr bool compileTimeArgs = DataType::compileTimeArgs;
2315 //**********************************************************************************************
2316
2317 //**Constructor*********************************************************************************
2324 template< typename... REAs > // Optional element arguments
2325 explicit inline Elements( const CPE& vector, REAs... args )
2326 : DataType( args... ) // Base class initialization
2327 , vector_ ( vector ) // The sparse vector/dense vector cross product expression
2328 {
2329 if( isChecked( args... ) ) {
2330 for( size_t i=0UL; i<size(); ++i ) {
2331 if( vector_.size() <= idx(i) ) {
2332 BLAZE_THROW_INVALID_ARGUMENT( "Invalid element access index" );
2333 }
2334 }
2335 }
2336 }
2337 //**********************************************************************************************
2338
2339 //**Subscript operator**************************************************************************
2345 inline ReturnType operator[]( size_t index ) const {
2346 BLAZE_INTERNAL_ASSERT( index < size(), "Invalid vector access index" );
2347 return vector_[idx(index)];
2348 }
2349 //**********************************************************************************************
2350
2351 //**At function*********************************************************************************
2358 inline ReturnType at( size_t index ) const {
2359 if( index >= size() ) {
2360 BLAZE_THROW_OUT_OF_RANGE( "Invalid vector access index" );
2361 }
2362 return (*this)[index];
2363 }
2364 //**********************************************************************************************
2365
2366 //**********************************************************************************************
2367 using DataType::idces;
2368 using DataType::idx;
2369 using DataType::size;
2370 //**********************************************************************************************
2371
2372 //**Operand access******************************************************************************
2377 inline CPE operand() const noexcept {
2378 return vector_;
2379 }
2380 //**********************************************************************************************
2381
2382 //**********************************************************************************************
2388 template< typename T >
2389 inline bool canAlias( const T* alias ) const noexcept {
2390 return vector_.canAlias( &unview( *alias ) );
2391 }
2392 //**********************************************************************************************
2393
2394 //**********************************************************************************************
2400 template< typename T >
2401 inline bool isAliased( const T* alias ) const noexcept {
2402 return vector_.isAliased( &unview( *alias ) );
2403 }
2404 //**********************************************************************************************
2405
2406 private:
2407 //**Member variables****************************************************************************
2408 CPE vector_;
2409 //**********************************************************************************************
2410};
2412//*************************************************************************************************
2413
2414
2415
2416
2417
2418
2419
2420
2421//=================================================================================================
2422//
2423// CLASS TEMPLATE SPECIALIZATION FOR SVECSVECCROSSEXPR
2424//
2425//=================================================================================================
2426
2427//*************************************************************************************************
2435template< typename VT1 // Type of the left-hand side sparse vector
2436 , typename VT2 // Type of the right-hand side sparse vector
2437 , bool TF // Transpose flag
2438 , typename... CEAs > // Compile time element arguments
2439class Elements< const SVecSVecCrossExpr<VT1,VT2,TF>, TF, true, CEAs... >
2440 : public View< DenseVector< Elements< const SVecSVecCrossExpr<VT1,VT2,TF>, TF, true, CEAs... >, TF > >
2441 , private ElementsData<CEAs...>
2442{
2443 private:
2444 //**Type definitions****************************************************************************
2445 using CPE = SVecSVecCrossExpr<VT1,VT2,TF>;
2446 using RT = ResultType_t<CPE>;
2447 using DataType = ElementsData<CEAs...>;
2448 //**********************************************************************************************
2449
2450 //**Compile time flags**************************************************************************
2451 using DataType::N;
2452 //**********************************************************************************************
2453
2454 public:
2455 //**Type definitions****************************************************************************
2457 using This = Elements<const CPE,TF,true,CEAs...>;
2458
2460 using BaseType = View< DenseVector<This,TF> >;
2461
2462 using ViewedType = CPE;
2463 using ResultType = ElementsTrait_t<RT,N>;
2464 using TransposeType = TransposeType_t<ResultType>;
2465 using ElementType = ElementType_t<CPE>;
2466 using ReturnType = ReturnType_t<CPE>;
2467 using CompositeType = const ResultType;
2468 //**********************************************************************************************
2469
2470 //**Compilation flags***************************************************************************
2472 static constexpr bool simdEnabled = false;
2473
2475 static constexpr bool smpAssignable = false;
2476
2478 static constexpr bool compileTimeArgs = DataType::compileTimeArgs;
2479 //**********************************************************************************************
2480
2481 //**Constructor*********************************************************************************
2488 template< typename... REAs > // Optional element arguments
2489 explicit inline Elements( const CPE& vector, REAs... args )
2490 : DataType( args... ) // Base class initialization
2491 , vector_ ( vector ) // The sparse vector/sparse vector cross product expression
2492 {
2493 if( isChecked( args... ) ) {
2494 for( size_t i=0UL; i<size(); ++i ) {
2495 if( vector_.size() <= idx(i) ) {
2496 BLAZE_THROW_INVALID_ARGUMENT( "Invalid element access index" );
2497 }
2498 }
2499 }
2500 }
2501 //**********************************************************************************************
2502
2503 //**Subscript operator**************************************************************************
2509 inline ReturnType operator[]( size_t index ) const {
2510 BLAZE_INTERNAL_ASSERT( index < size(), "Invalid vector access index" );
2511 return vector_[idx(index)];
2512 }
2513 //**********************************************************************************************
2514
2515 //**At function*********************************************************************************
2522 inline ReturnType at( size_t index ) const {
2523 if( index >= size() ) {
2524 BLAZE_THROW_OUT_OF_RANGE( "Invalid vector access index" );
2525 }
2526 return (*this)[index];
2527 }
2528 //**********************************************************************************************
2529
2530 //**********************************************************************************************
2531 using DataType::idces;
2532 using DataType::idx;
2533 using DataType::size;
2534 //**********************************************************************************************
2535
2536 //**Operand access******************************************************************************
2541 inline CPE operand() const noexcept {
2542 return vector_;
2543 }
2544 //**********************************************************************************************
2545
2546 //**********************************************************************************************
2552 template< typename T >
2553 inline bool canAlias( const T* alias ) const noexcept {
2554 return vector_.canAlias( &unview( *alias ) );
2555 }
2556 //**********************************************************************************************
2557
2558 //**********************************************************************************************
2564 template< typename T >
2565 inline bool isAliased( const T* alias ) const noexcept {
2566 return vector_.isAliased( &unview( *alias ) );
2567 }
2568 //**********************************************************************************************
2569
2570 private:
2571 //**Member variables****************************************************************************
2572 CPE vector_;
2573 //**********************************************************************************************
2574};
2576//*************************************************************************************************
2577
2578} // namespace blaze
2579
2580#endif
Header file for auxiliary alias declarations.
Header file for run time assertion macros.
Header file for the blaze::checked and blaze::unchecked instances.
Header file for the cross product trait.
constexpr const DenseIterator< Type, AF > operator-(const DenseIterator< Type, AF > &it, ptrdiff_t inc) noexcept
Subtraction between a DenseIterator and an integral value.
Definition: DenseIterator.h:751
constexpr const DenseIterator< Type, AF > operator+(const DenseIterator< Type, AF > &it, ptrdiff_t inc) noexcept
Addition between a DenseIterator and an integral value.
Definition: DenseIterator.h:719
Header file for the implementation of the ElementsData class template.
Header file for the elements trait.
Header file for the HasMutableDataAccess type trait.
Header file for the If class template.
Header file for the IsConst type trait.
Header file for the isDefault shim.
Header file for the IsExpression type trait class.
Header file for the IsReference type trait.
Header file for the IsRestricted type trait.
Header file for the IsSparseVector type trait.
Deactivation of problematic macros.
Header file for the prevMultiple shim.
Initializer list type of the Blaze library.
Constraint on the data type.
Constraint on the data type.
Constraint on the data type.
Constraint on the data type.
Constraint on the data type.
Constraint on the data type.
Header file for the implementation of a vector representation of an initializer list.
Header file for the DenseVector base class.
Header file for the View base class.
auto operator/=(DenseMatrix< MT, SO > &mat, ST scalar) -> EnableIf_t< IsScalar_v< ST >, MT & >
Division assignment operator for the division of a dense matrix by a scalar value ( ).
Definition: DenseMatrix.h:574
MT::ElementType * data(DenseMatrix< MT, SO > &dm) noexcept
Low-level data access to the dense matrix elements.
Definition: DenseMatrix.h:182
auto operator+=(DenseMatrix< MT, SO > &mat, ST scalar) -> EnableIf_t< IsScalar_v< ST >, MT & >
Addition assignment operator for the addition of a dense matrix and a scalar value ( ).
Definition: DenseMatrix.h:386
auto operator*=(DenseMatrix< MT, SO > &mat, ST scalar) -> EnableIf_t< IsScalar_v< ST >, MT & >
Multiplication assignment operator for the multiplication of a dense matrix and a scalar value ( ).
Definition: DenseMatrix.h:510
size_t spacing(const DenseMatrix< MT, SO > &dm) noexcept
Returns the spacing between the beginning of two rows/columns.
Definition: DenseMatrix.h:265
decltype(auto) operator*(const DenseMatrix< MT1, false > &lhs, const DenseMatrix< MT2, false > &rhs)
Multiplication operator for the multiplication of two row-major dense matrices ( ).
Definition: DMatDMatMultExpr.h:9640
auto operator-=(DenseMatrix< MT, SO > &mat, ST scalar) -> EnableIf_t< IsScalar_v< ST >, MT & >
Subtraction assignment operator for the subtraction of a dense matrix and a scalar value ( ).
Definition: DenseMatrix.h:448
bool isIntact(const DiagonalMatrix< MT, SO, DF > &m)
Returns whether the invariants of the given diagonal matrix are intact.
Definition: DiagonalMatrix.h:207
bool isDefault(const DiagonalMatrix< MT, SO, DF > &m)
Returns whether the given diagonal matrix is in default state.
Definition: DiagonalMatrix.h:169
decltype(auto) elements(Vector< VT, TF > &vector, REAs... args)
Creating a view on a selection of elements of the given vector.
Definition: Elements.h:143
#define BLAZE_CONSTRAINT_MUST_NOT_REQUIRE_EVALUATION(T)
Constraint on the data type.
Definition: RequiresEvaluation.h:81
#define BLAZE_CONSTRAINT_MUST_NOT_BE_TRANSEXPR_TYPE(T)
Constraint on the data type.
Definition: TransExpr.h:81
#define BLAZE_CONSTRAINT_MUST_BE_VECTOR_WITH_TRANSPOSE_FLAG(T, TF)
Constraint on the data type.
Definition: TransposeFlag.h:63
#define BLAZE_CONSTRAINT_MUST_NOT_BE_ELEMENTS_TYPE(T)
Constraint on the data type.
Definition: Elements.h:81
#define BLAZE_CONSTRAINT_MUST_NOT_BE_COMPUTATION_TYPE(T)
Constraint on the data type.
Definition: Computation.h:81
#define BLAZE_CONSTRAINT_MUST_BE_DENSE_VECTOR_TYPE(T)
Constraint on the data type.
Definition: DenseVector.h:61
#define BLAZE_CONSTRAINT_MUST_NOT_BE_SUBVECTOR_TYPE(T)
Constraint on the data type.
Definition: Subvector.h:81
BLAZE_ALWAYS_INLINE constexpr auto prevMultiple(T1 value, T2 factor) noexcept
Rounds down an integral value to the previous multiple of a given factor.
Definition: PrevMultiple.h:68
constexpr bool operator>(const NegativeAccuracy< A > &lhs, const T &rhs)
Greater-than comparison between a NegativeAccuracy object and a floating point value.
Definition: Accuracy.h:370
constexpr bool operator==(const NegativeAccuracy< A > &lhs, const T &rhs)
Equality comparison between a NegativeAccuracy object and a floating point value.
Definition: Accuracy.h:253
constexpr bool operator<(const NegativeAccuracy< A > &lhs, const T &rhs)
Less-than comparison between a NegativeAccuracy object and a floating point value.
Definition: Accuracy.h:332
constexpr bool operator>=(const NegativeAccuracy< A > &, const T &rhs)
Greater-or-equal-than comparison between a NegativeAccuracy object and a floating point value.
Definition: Accuracy.h:446
constexpr bool operator!=(const NegativeAccuracy< A > &lhs, const T &rhs)
Inequality comparison between a NegativeAccuracy object and a floating point value.
Definition: Accuracy.h:293
constexpr bool operator<=(const NegativeAccuracy< A > &, const T &rhs)
Less-or-equal-than comparison between a NegativeAccuracy object and a floating point value.
Definition: Accuracy.h:408
constexpr void clear(Matrix< MT, SO > &matrix)
Clearing the given matrix.
Definition: Matrix.h:960
MT::ConstIterator cend(const Matrix< MT, SO > &matrix, size_t i)
Returns an iterator just past the last element of row/column i.
Definition: Matrix.h:628
size_t nonZeros(const Matrix< MT, SO > &matrix)
Returns the total number of non-zero elements in the matrix.
Definition: Matrix.h:730
MT::ConstIterator cbegin(const Matrix< MT, SO > &matrix, size_t i)
Returns an iterator to the first element of row/column i.
Definition: Matrix.h:562
size_t capacity(const Matrix< MT, SO > &matrix) noexcept
Returns the maximum capacity of the matrix.
Definition: Matrix.h:692
constexpr void reset(Matrix< MT, SO > &matrix)
Resetting the given matrix.
Definition: Matrix.h:806
MT::Iterator end(Matrix< MT, SO > &matrix, size_t i)
Returns an iterator just past the last element of row/column i.
Definition: Matrix.h:584
MT::Iterator begin(Matrix< MT, SO > &matrix, size_t i)
Returns an iterator to the first element of row/column i.
Definition: Matrix.h:518
constexpr size_t size(const Matrix< MT, SO > &matrix) noexcept
Returns the total number of elements of the matrix.
Definition: Matrix.h:676
#define BLAZE_INTERNAL_ASSERT(expr, msg)
Run time assertion macro for internal checks.
Definition: Assert.h:101
#define BLAZE_USER_ASSERT(expr, msg)
Run time assertion macro for user checks.
Definition: Assert.h:117
auto smpDivAssign(Vector< VT1, TF1 > &lhs, const Vector< VT2, TF2 > &rhs) -> EnableIf_t< IsDenseVector_v< VT1 > >
Default implementation of the SMP division assignment of a vector to a dense vector.
Definition: DenseVector.h:221
auto smpSubAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs) -> EnableIf_t< IsDenseMatrix_v< MT1 > >
Default implementation of the SMP subtraction assignment of a matrix to dense matrix.
Definition: DenseMatrix.h:162
auto smpAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs) -> EnableIf_t< IsDenseMatrix_v< MT1 > >
Default implementation of the SMP assignment of a matrix to a dense matrix.
Definition: DenseMatrix.h:100
auto smpMultAssign(Vector< VT1, TF1 > &lhs, const Vector< VT2, TF2 > &rhs) -> EnableIf_t< IsDenseVector_v< VT1 > >
Default implementation of the SMP multiplication assignment of a vector to a dense vector.
Definition: DenseVector.h:192
auto smpAddAssign(Matrix< MT1, SO1 > &lhs, const Matrix< MT2, SO2 > &rhs) -> EnableIf_t< IsDenseMatrix_v< MT1 > >
Default implementation of the SMP addition assignment of a matrix to a dense matrix.
Definition: DenseMatrix.h:131
#define BLAZE_THROW_OUT_OF_RANGE(MESSAGE)
Macro for the emission of a std::out_of_range exception.
Definition: Exception.h:331
#define BLAZE_THROW_INVALID_ARGUMENT(MESSAGE)
Macro for the emission of a std::invalid_argument exception.
Definition: Exception.h:235
constexpr bool isChecked(const Ts &... args)
Extracting blaze::Check arguments from a given list of arguments.
Definition: Check.h:225
Header file for the exception macros of the math module.
Header file for the extended initializer_list functionality.
Constraint on the data type.
Header file for all forward declarations for expression class templates.
Header file for the clear shim.
Header file for the reset shim.
Header file for the thresholds for matrix/vector and matrix/matrix multiplications.
Header file for the implementation of the Elements base template.