Loading...
Searching...
No Matches
MatrixCSR-Impl.hpp
Go to the documentation of this file.
1// This code is based on Jet framework.
2// Copyright (c) 2018 Doyub Kim
3// CubbyFlow is voxel-based fluid simulation engine for computer games.
4// Copyright (c) 2020 CubbyFlow Team
5// Core Part: Chris Ohk, Junwoo Hwang, Jihong Sin, Seungwoo Yoo
6// AI Part: Dongheon Cho, Minseo Kim
7// We are making my contributions/submissions to this project solely in our
8// personal capacity and are not conveying any rights to any intellectual
9// property of any third parties.
10
11#ifndef CUBBYFLOW_MATRIX_CSR_IMPL_HPP
12#define CUBBYFLOW_MATRIX_CSR_IMPL_HPP
13
17
18#include <utility>
19
20namespace CubbyFlow
21{
22template <typename T, typename ME>
24 const ME& m2)
25 : m_m1(m1),
26 m_m2(m2),
27 m_nnz(m1.NonZeroData()),
28 m_rp(m1.RowPointersData()),
29 m_ci(m1.ColumnIndicesData())
30{
31 // Do nothing
32}
33
34template <typename T, typename ME>
36{
37 return m_m1.GetRows();
38}
39
40template <typename T, typename ME>
42{
43 return m_m2.GetCols();
44}
45
46template <typename T, typename ME>
48{
49 const size_t colBegin = m_rp[i];
50 const size_t colEnd = m_rp[i + 1];
51
52 T sum = 0;
53
54 for (size_t kk = colBegin; kk < colEnd; ++kk)
55 {
56 size_t k = m_ci[kk];
57 sum += m_nnz[kk] * m_m2(k, j);
58 }
59
60 return sum;
61}
62
63template <typename T>
64MatrixCSR<T>::Element::Element() : i(0), j(0), value(0)
65{
66 // Do nothing
67}
68
69template <typename T>
71 : i(i_), j(j_), value(value_)
72{
73 // Do nothing
74}
75
76template <typename T>
81
82template <typename T>
84 const std::initializer_list<std::initializer_list<T>>& lst, T epsilon)
85{
87}
88
89template <typename T>
90template <size_t R, size_t C, typename ME>
95
96template <typename T>
101
102template <typename T>
104 : m_size(std::exchange(other.m_size, Vector2UZ{})),
105 m_nonZeros(std::move(other.m_nonZeros)),
106 m_rowPointers(std::move(other.m_rowPointers)),
107 m_columnIndices(std::move(other.m_columnIndices))
108{
109 // Do nothing
110}
111
112template <typename T>
114{
115 Set(other);
116
117 return *this;
119
120template <typename T>
122{
123 m_size = other.m_size;
124 other.m_size = Vector2UZ{};
125 m_nonZeros = std::move(other.m_nonZeros);
126 m_rowPointers = std::move(other.m_rowPointers);
127 m_columnIndices = std::move(other.m_columnIndices);
128
129 return *this;
130}
131
132template <typename T>
134{
135 m_size = { 0, 0 };
136 m_nonZeros.clear();
137 m_rowPointers.clear();
138 m_columnIndices.clear();
139 m_rowPointers.push_back(0);
140}
141
142template <typename T>
144{
145 std::fill(m_nonZeros.begin(), m_nonZeros.end(), s);
146}
147
148template <typename T>
150{
151 m_size = other.m_size;
152 m_nonZeros = other.m_nonZeros;
153 m_rowPointers = other.m_rowPointers;
154 m_columnIndices = other.m_columnIndices;
155}
156
157template <typename T>
158void MatrixCSR<T>::Reserve(size_t rows, size_t cols, size_t numNonZeros)
159{
160 m_size = Vector2UZ(rows, cols);
161 m_rowPointers.resize(m_size.x + 1);
162 m_nonZeros.resize(numNonZeros);
163 m_columnIndices.resize(numNonZeros);
164}
165
166template <typename T>
168 const std::initializer_list<std::initializer_list<T>>& lst, T epsilon)
169{
170 const size_t numRows = lst.size();
171 const size_t numCols = (numRows > 0) ? lst.begin()->size() : 0;
172
173 m_size = { numRows, numCols };
174 m_nonZeros.clear();
175 m_rowPointers.clear();
176 m_columnIndices.clear();
177
178 auto rowIter = lst.begin();
179 for (size_t i = 0; i < numRows; ++i)
181 assert(numCols == rowIter->size());
182
183 m_rowPointers.push_back(m_nonZeros.size());
184
185 auto colIter = rowIter->begin();
186 for (size_t j = 0; j < numCols; ++j)
187 {
188 if (std::fabs(*colIter) > epsilon)
189 {
190 m_nonZeros.push_back(*colIter);
191 m_columnIndices.push_back(j);
192 }
193
194 ++colIter;
196
197 ++rowIter;
199
200 m_rowPointers.push_back(m_nonZeros.size());
201}
202
203template <typename T>
204template <size_t R, size_t C, typename E>
207{
208 const size_t numRows = other.GetRows();
209 const size_t numCols = other.GetCols();
211 m_size = { numRows, numCols };
212 m_nonZeros.clear();
213 m_columnIndices.clear();
214
216
217 for (size_t i = 0; i < numRows; ++i)
218 {
219 m_rowPointers.push_back(m_nonZeros.size());
220
221 for (size_t j = 0; j < numCols; ++j)
222 {
223 if (T val = expression(i, j); std::fabs(val) > epsilon)
225 m_nonZeros.push_back(val);
226 m_columnIndices.push_back(j);
228 }
229 }
231 m_rowPointers.push_back(m_nonZeros.size());
232}
234template <typename T>
235void MatrixCSR<T>::AddElement(size_t i, size_t j, const T& value)
237 AddElement({ i, j, value });
238}
240template <typename T>
243 if (const ssize_t numRowsToAdd = static_cast<ssize_t>(element.i) -
244 static_cast<ssize_t>(m_size.x) + 1;
246 {
247 for (ssize_t i = 0; i < numRowsToAdd; ++i)
249 AddRow({}, {});
250 }
252
253 m_size.y = std::max(m_size.y, element.j + 1);
255 const size_t rowBegin = m_rowPointers[element.i];
256 const size_t rowEnd = m_rowPointers[element.i + 1];
258 auto colIdxIter =
259 std::lower_bound(m_columnIndices.begin() + rowBegin,
260 m_columnIndices.begin() + rowEnd, element.j);
261 auto offset = colIdxIter - m_columnIndices.begin();
262
263 m_columnIndices.insert(colIdxIter, element.j);
264 m_nonZeros.insert(m_nonZeros.begin() + offset, element.value);
265
266 for (size_t i = element.i + 1; i < m_rowPointers.size(); ++i)
267 {
268 ++m_rowPointers[i];
270}
271
272template <typename T>
276 assert(nonZeros.size() == columnIndices.size());
277
278 ++m_size.x;
279
280 // TODO: Implement zip iterator
281 std::vector<std::pair<T, size_t>> zipped;
282 for (size_t i = 0; i < nonZeros.size(); ++i)
283 {
284 zipped.emplace_back(nonZeros[i], columnIndices[i]);
285 m_size.y = std::max(m_size.y, columnIndices[i] + 1);
286 }
288 std::sort(zipped.begin(), zipped.end(),
289 [](std::pair<T, size_t> a, std::pair<T, size_t> b) {
290 return a.second < b.second;
291 });
292
293 for (size_t i = 0; i < zipped.size(); ++i)
294 {
295 m_nonZeros.push_back(zipped[i].first);
296 m_columnIndices.push_back(zipped[i].second);
297 }
298
299 m_rowPointers.push_back(m_nonZeros.size());
300}
301
302template <typename T>
303void MatrixCSR<T>::SetElement(size_t i, size_t j, const T& value)
304{
305 SetElement({ i, j, value });
306}
307
308template <typename T>
310{
311 if (size_t nzIndex = HasElement(element.i, element.j);
312 nzIndex == std::numeric_limits<size_t>::max())
313 {
316 else
317 {
318 m_nonZeros[nzIndex] = element.value;
320}
321
322template <typename T>
324{
325 if (m_size != other.m_size)
326 {
327 return false;
329
330 if (m_nonZeros.size() != other.m_nonZeros.size())
332 return false;
333 }
335 for (size_t i = 0; i < m_nonZeros.size(); ++i)
336 {
337 if (m_nonZeros[i] != other.m_nonZeros[i])
338 {
339 return false;
341
342 if (m_columnIndices[i] != other.m_columnIndices[i])
344 return false;
345 }
347
348 for (size_t i = 0; i < m_rowPointers.size(); ++i)
350 if (m_rowPointers[i] != other.m_rowPointers[i])
351 {
352 return false;
353 }
354 }
355
356 return true;
357}
358
359template <typename T>
360bool MatrixCSR<T>::IsSimilar(const MatrixCSR& other, double tol) const
361{
362 if (m_size != other.m_size)
363 {
364 return false;
366
367 if (m_nonZeros.size() != other.m_nonZeros.size())
369 return false;
370 }
372 for (size_t i = 0; i < m_nonZeros.size(); ++i)
373 {
374 if (std::fabs(m_nonZeros[i] - other.m_nonZeros[i]) > tol)
375 {
376 return false;
378
379 if (m_columnIndices[i] != other.m_columnIndices[i])
380 {
381 return false;
382 }
383 }
384
385 for (size_t i = 0; i < m_rowPointers.size(); ++i)
386 {
387 if (m_rowPointers[i] != other.m_rowPointers[i])
388 {
389 return false;
390 }
391 }
392
393 return true;
394}
395
396template <typename T>
399 return GetRows() == GetCols();
400}
402template <typename T>
405 return m_size;
406}
408template <typename T>
411 return m_size.x;
412}
413
414template <typename T>
416{
417 return m_size.y;
418}
419
420template <typename T>
422{
423 return m_nonZeros.size();
424}
425
426template <typename T>
427const T& MatrixCSR<T>::NonZero(size_t i) const
428{
429 return m_nonZeros[i];
431
432template <typename T>
434{
435 return m_nonZeros[i];
436}
437
438template <typename T>
439const size_t& MatrixCSR<T>::RowPointer(size_t i) const
440{
441 return m_rowPointers[i];
442}
443
444template <typename T>
445const size_t& MatrixCSR<T>::ColumnIndex(size_t i) const
446{
447 return m_columnIndices[i];
448}
449
450template <typename T>
452{
453 return m_nonZeros.data();
454}
455
456template <typename T>
458{
459 return m_nonZeros.data();
460}
461
462template <typename T>
463const size_t* MatrixCSR<T>::RowPointersData() const
464{
465 return m_rowPointers.data();
466}
467
468template <typename T>
470{
471 return m_columnIndices.data();
472}
473
474template <typename T>
476{
477 return m_nonZeros.begin();
478}
479
480template <typename T>
482{
483 return m_nonZeros.cbegin();
484}
485
486template <typename T>
488{
489 return m_nonZeros.end();
490}
491
492template <typename T>
494{
495 return m_nonZeros.cend();
496}
497
498template <typename T>
500{
501 return m_rowPointers.begin();
502}
503
504template <typename T>
506{
507 return m_rowPointers.cbegin();
508}
509
510template <typename T>
512{
513 return m_rowPointers.end();
514}
515
516template <typename T>
518{
519 return m_rowPointers.cend();
520}
521
522template <typename T>
524{
525 return m_columnIndices.begin();
526}
527
528template <typename T>
530 const
531{
532 return m_columnIndices.cbegin();
533}
534
535template <typename T>
537{
538 return m_columnIndices.end();
539}
540
541template <typename T>
543{
544 return m_columnIndices.cend();
545}
546
547template <typename T>
549{
550 MatrixCSR ret(*this);
551
552 ParallelFor(ZERO_SIZE, ret.m_nonZeros.size(),
553 [&](size_t i) { ret.m_nonZeros[i] += s; });
554
555 return ret;
556}
557
558template <typename T>
560{
561 return BinaryOp(m, std::plus<T>());
562}
563
564template <typename T>
566{
567 MatrixCSR ret(*this);
568
569 ParallelFor(ZERO_SIZE, ret.m_nonZeros.size(),
570 [&](size_t i) { ret.m_nonZeros[i] -= s; });
571
572 return ret;
573}
574
575template <typename T>
577{
578 return BinaryOp(m, std::minus<T>());
579}
580
581template <typename T>
583{
584 MatrixCSR ret(*this);
585
586 ParallelFor(ZERO_SIZE, ret.m_nonZeros.size(),
587 [&](size_t i) { ret.m_nonZeros[i] *= s; });
588
589 return ret;
590}
591
592template <typename T>
593template <size_t R, size_t C, typename ME>
599
600template <typename T>
602{
603 MatrixCSR ret(*this);
604
605 ParallelFor(ZERO_SIZE, ret.m_nonZeros.size(),
606 [&](size_t i) { ret.m_nonZeros[i] /= s; });
607
608 return ret;
609}
610
611template <typename T>
613{
614 return Add(s);
615}
616
617template <typename T>
619{
620 return Add(m);
621}
622
623template <typename T>
625{
626 MatrixCSR ret(*this);
627
628 ParallelFor(ZERO_SIZE, ret.m_nonZeros.size(),
629 [&](size_t i) { ret.m_nonZeros[i] = s - ret.m_nonZeros[i]; });
630
631 return ret;
632}
633
634template <typename T>
636{
637 return m.Sub(*this);
638}
639
640template <typename T>
642{
643 return Mul(s);
644}
645
646template <typename T>
648{
649 MatrixCSR ret(*this);
650
651 ParallelFor(ZERO_SIZE, ret.m_nonZeros.size(),
652 [&](size_t i) { ret.m_nonZeros[i] = s / ret.m_nonZeros[i]; });
653
654 return ret;
655}
656
657template <typename T>
659{
660 ParallelFor(ZERO_SIZE, m_nonZeros.size(),
661 [&](size_t i) { m_nonZeros[i] += s; });
662}
663
664template <typename T>
666{
667 Set(Add(m));
668}
669
670template <typename T>
672{
673 ParallelFor(ZERO_SIZE, m_nonZeros.size(),
674 [&](size_t i) { m_nonZeros[i] -= s; });
675}
676
677template <typename T>
679{
680 Set(Sub(m));
681}
682
683template <typename T>
685{
686 ParallelFor(ZERO_SIZE, m_nonZeros.size(),
687 [&](size_t i) { m_nonZeros[i] *= s; });
688}
689
690template <typename T>
691template <size_t R, size_t C, typename ME>
693{
695
696 *this = std::move(result);
697}
698
699template <typename T>
701{
702 ParallelFor(ZERO_SIZE, m_nonZeros.size(),
703 [&](size_t i) { m_nonZeros[i] /= s; });
704}
705
706template <typename T>
708{
709 return ParallelReduce(
711 [&](size_t start, size_t end, T init) {
712 T result = init;
713
714 for (size_t i = start; i < end; ++i)
715 {
716 result += m_nonZeros[i];
717 }
718
719 return result;
720 },
721 std::plus<T>());
722}
723
724template <typename T>
726{
727 return Sum() / NumberOfNonZeros();
728}
729
730template <typename T>
732{
733 const T& (*_min)(const T&, const T&) = std::min<T>;
734
735 return ParallelReduce(
736 ZERO_SIZE, NumberOfNonZeros(), std::numeric_limits<T>::max(),
737 [&](size_t start, size_t end, T init) {
738 T result = init;
739
740 for (size_t i = start; i < end; ++i)
741 {
742 result = std::min(result, m_nonZeros[i]);
743 }
744
745 return result;
746 },
747 _min);
748}
749
750template <typename T>
752{
753 const T& (*_max)(const T&, const T&) = std::max<T>;
754
755 return ParallelReduce(
756 ZERO_SIZE, NumberOfNonZeros(), std::numeric_limits<T>::min(),
757 [&](size_t start, size_t end, T init) {
758 T result = init;
759
760 for (size_t i = start; i < end; ++i)
761 {
762 result = std::max(result, m_nonZeros[i]);
763 }
764
765 return result;
766 },
767 _max);
768}
769
770template <typename T>
772{
773 return ParallelReduce(
774 ZERO_SIZE, NumberOfNonZeros(), std::numeric_limits<T>::max(),
775 [&](size_t start, size_t end, T init) {
776 T result = init;
777
778 for (size_t i = start; i < end; ++i)
779 {
780 result = CubbyFlow::AbsMin(result, m_nonZeros[i]);
781 }
782
783 return result;
784 },
786}
787
788template <typename T>
790{
791 return ParallelReduce(
793 [&](size_t start, size_t end, T init) {
794 T result = init;
795
796 for (size_t i = start; i < end; ++i)
797 {
798 result = CubbyFlow::AbsMax(result, m_nonZeros[i]);
799 }
800
801 return result;
802 },
804}
805
806template <typename T>
808{
809 assert(IsSquare());
810
811 return ParallelReduce(
812 ZERO_SIZE, GetRows(), T(0),
813 [&](size_t start, size_t end, T init) {
814 T result = init;
815
816 for (size_t i = start; i < end; ++i)
817 {
818 result += (*this)(i, i);
819 }
820
821 return result;
822 },
823 std::plus<T>());
824}
825
826template <typename T>
827template <typename U>
829{
831 ret.Reserve(GetRows(), GetCols(), NumberOfNonZeros());
832
833 auto nnz = ret.NonZeroBegin();
834 auto ci = ret.ColumnIndicesBegin();
835 auto rp = ret.RowPointersBegin();
836
837 ParallelFor(ZERO_SIZE, m_nonZeros.size(), [&](size_t i) {
838 nnz[i] = static_cast<U>(m_nonZeros[i]);
839 ci[i] = m_columnIndices[i];
840 });
841
842 ParallelFor(ZERO_SIZE, m_rowPointers.size(),
843 [&](size_t i) { rp[i] = m_rowPointers[i]; });
844
845 return ret;
846}
847
848template <typename T>
849template <size_t R, size_t C, typename E>
851{
852 Set(m);
853
854 return *this;
855}
856
857template <typename T>
859{
860 IAdd(s);
861
862 return *this;
863}
864
865template <typename T>
867{
868 IAdd(m);
869
870 return *this;
871}
872
873template <typename T>
875{
876 ISub(s);
877
878 return *this;
879}
880
881template <typename T>
883{
884 ISub(m);
885
886 return *this;
887}
888
889template <typename T>
891{
892 IMul(s);
893
894 return *this;
895}
896
897template <typename T>
898template <size_t R, size_t C, typename ME>
900{
901 IMul(m);
902
903 return *this;
904}
905
906template <typename T>
908{
909 IDiv(s);
910
911 return *this;
912}
913
914template <typename T>
915T MatrixCSR<T>::operator()(size_t i, size_t j) const
916{
917 size_t nzIndex = HasElement(i, j);
918
919 if (nzIndex == std::numeric_limits<size_t>::max())
920 {
921 return 0.0;
922 }
923
924 return m_nonZeros[nzIndex];
925}
926
927template <typename T>
929{
930 return IsEqual(m);
931}
932
933template <typename T>
935{
936 return !IsEqual(m);
937}
938
939template <typename T>
941{
943
944 ret.m_size = Vector2UZ(m, m);
945 ret.m_nonZeros.resize(m, 1.0);
946 ret.m_columnIndices.resize(m);
947 std::iota(ret.m_columnIndices.begin(), ret.m_columnIndices.end(), 0);
948 ret.m_rowPointers.resize(m + 1);
949 std::iota(ret.m_rowPointers.begin(), ret.m_rowPointers.end(), 0);
950
951 return ret;
952}
953
954template <typename T>
955size_t MatrixCSR<T>::HasElement(size_t i, size_t j) const
956{
957 if (i >= m_size.x || j >= m_size.y)
958 {
959 return std::numeric_limits<size_t>::max();
960 }
961
962 const size_t rowBegin = m_rowPointers[i];
963 const size_t rowEnd = m_rowPointers[i + 1];
964
965 if (const auto iter = BinaryFind(m_columnIndices.begin() + rowBegin,
966 m_columnIndices.begin() + rowEnd, j);
967 iter != m_columnIndices.begin() + rowEnd)
968 {
969 return static_cast<size_t>(iter - m_columnIndices.begin());
970 }
971
972 return std::numeric_limits<size_t>::max();
973}
974
975template <typename T>
976template <typename Op>
978{
979 assert(m_size == m.m_size);
980
982
983 for (size_t i = 0; i < m_size.x; ++i)
984 {
985 std::vector<size_t> col;
986 std::vector<double> nnz;
987
988 auto colIterA = m_columnIndices.begin() + m_rowPointers[i];
989 auto colIterB = m.m_columnIndices.begin() + m.m_rowPointers[i];
990 auto colEndA = m_columnIndices.begin() + m_rowPointers[i + 1];
991 auto colEndB = m.m_columnIndices.begin() + m.m_rowPointers[i + 1];
992 auto nnzIterA = m_nonZeros.begin() + m_rowPointers[i];
993 auto nnzIterB = m.m_nonZeros.begin() + m.m_rowPointers[i];
994
995 while (colIterA != colEndA || colIterB != colEndB)
996 {
997 if (colIterB == colEndB || *colIterA < *colIterB)
998 {
999 col.push_back(*colIterA);
1000 nnz.push_back(op(*nnzIterA, 0));
1001 ++colIterA;
1002 ++nnzIterA;
1003 }
1004 else if (colIterA == colEndA || *colIterA > *colIterB)
1005 {
1006 col.push_back(*colIterB);
1007 nnz.push_back(op(0, *nnzIterB));
1008 ++colIterB;
1009 ++nnzIterB;
1010 }
1011 else
1012 {
1013 assert(*colIterA == *colIterB);
1014
1015 col.push_back(*colIterB);
1016 nnz.push_back(op(*nnzIterA, *nnzIterB));
1017 ++colIterA;
1018 ++nnzIterA;
1019 ++colIterB;
1020 ++nnzIterB;
1021 }
1022 }
1023
1024 ret.AddRow(nnz, col);
1025 }
1026
1027 return ret;
1028}
1029
1030template <typename T>
1032{
1033 return a.Mul(-1);
1034}
1035
1036template <typename T>
1038{
1039 return a.Add(b);
1040}
1041
1042template <typename T>
1044{
1045 return a.Add(b);
1046}
1047
1048template <typename T>
1050{
1051 return b.Add(a);
1052}
1053
1054template <typename T>
1056{
1057 return a.Sub(b);
1058}
1059
1060template <typename T>
1062{
1063 return a.Sub(b);
1064}
1065
1066template <typename T>
1068{
1069 return b.RSub(a);
1070}
1071
1072template <typename T>
1074{
1075 return a.Mul(b);
1076}
1077
1078template <typename T>
1080{
1081 return b.RMul(a);
1082}
1083
1084template <typename T, size_t R, size_t C, typename ME>
1087{
1088 return a.Mul(b);
1089}
1090
1091template <typename T>
1093{
1094 return a.Div(b);
1095}
1096
1097template <typename T>
1099{
1100 return b.RDiv(a);
1101}
1102} // namespace CubbyFlow
1103
1104#endif
Compressed Sparse Row (CSR) matrix class.
Definition MatrixCSR.hpp:70
MatrixCSR< U > CastTo() const
Type-casts to different value-typed matrix.
Definition MatrixCSR-Impl.hpp:828
bool IsEqual(const MatrixCSR &other) const
Definition MatrixCSR-Impl.hpp:323
typename NonZeroContainerType::const_iterator ConstNonZeroIterator
Definition MatrixCSR.hpp:89
MatrixCSR RSub(const T &s) const
Returns input scalar - this matrix.
Definition MatrixCSR-Impl.hpp:624
T AbsMax() const
Returns absolute maximum among all elements.
Definition MatrixCSR-Impl.hpp:789
IndexContainerType::iterator IndexIterator
Definition MatrixCSR.hpp:92
IndexContainerType::const_iterator ConstIndexIterator
Definition MatrixCSR.hpp:93
MatrixCSR Add(const T &s) const
Returns this matrix + input scalar.
Definition MatrixCSR-Impl.hpp:548
void AddElement(size_t i, size_t j, const T &value)
Adds non-zero element to (i, j).
Definition MatrixCSR-Impl.hpp:235
void IAdd(const T &s)
Adds input scalar to this matrix.
Definition MatrixCSR-Impl.hpp:658
void Set(const T &s)
Sets whole matrix with input scalar.
Definition MatrixCSR-Impl.hpp:143
IndexIterator RowPointersBegin()
Returns the begin iterator of the row pointers.
Definition MatrixCSR-Impl.hpp:499
size_t NumberOfNonZeros() const
Returns the number of non-zero elements.
Definition MatrixCSR-Impl.hpp:421
size_t GetRows() const
Returns number of rows of this matrix.
Definition MatrixCSR-Impl.hpp:409
const size_t & RowPointer(size_t i) const
Returns i-th row pointer.
Definition MatrixCSR-Impl.hpp:439
IndexIterator ColumnIndicesEnd()
Returns the end iterator of the column indices.
Definition MatrixCSR-Impl.hpp:536
const T & NonZero(size_t i) const
Returns i-th non-zero element.
Definition MatrixCSR-Impl.hpp:427
T Sum() const
Returns sum of all elements.
Definition MatrixCSR-Impl.hpp:707
void Compress(const std::initializer_list< std::initializer_list< T > > &lst, T epsilon=std::numeric_limits< T >::epsilon())
Compresses given initializer list lst into a sparse matrix.
Definition MatrixCSR-Impl.hpp:167
std::vector< T > NonZeroContainerType
Definition MatrixCSR.hpp:87
void IDiv(const T &s)
Divides this matrix with input scalar.
Definition MatrixCSR-Impl.hpp:700
T operator()(size_t i, size_t j) const
Returns (i,j) element.
Definition MatrixCSR-Impl.hpp:915
MatrixCSR & operator/=(const T &s)
Division assignment with input scalar.
Definition MatrixCSR-Impl.hpp:907
bool IsSquare() const
Returns true if this matrix is a square matrix.
Definition MatrixCSR-Impl.hpp:397
MatrixCSR & operator*=(const T &s)
Multiplication assignment with input scalar.
Definition MatrixCSR-Impl.hpp:890
const size_t * RowPointersData() const
Returns constant pointer of the row pointers data.
Definition MatrixCSR-Impl.hpp:463
T * NonZeroData()
Returns pointer of the non-zero elements data.
Definition MatrixCSR-Impl.hpp:451
bool operator==(const MatrixCSR &m) const
Returns true if is equal to m.
Definition MatrixCSR-Impl.hpp:928
NonZeroIterator NonZeroBegin()
Returns the begin iterator of the non-zero elements.
Definition MatrixCSR-Impl.hpp:475
const size_t & ColumnIndex(size_t i) const
Returns i-th column index.
Definition MatrixCSR-Impl.hpp:445
static MatrixCSR< T > MakeIdentity(size_t m)
Definition MatrixCSR-Impl.hpp:940
void AddRow(const NonZeroContainerType &nonZeros, const IndexContainerType &columnIndices)
Definition MatrixCSR-Impl.hpp:273
void Clear()
Clears the matrix and make it zero-dimensional.
Definition MatrixCSR-Impl.hpp:133
void IMul(const T &s)
Multiplies input scalar to this matrix.
Definition MatrixCSR-Impl.hpp:684
MatrixCSR()
Constructs an empty matrix.
Definition MatrixCSR-Impl.hpp:77
T Min() const
Returns minimum among all elements.
Definition MatrixCSR-Impl.hpp:731
bool operator!=(const MatrixCSR &m) const
Returns true if is not equal to m.
Definition MatrixCSR-Impl.hpp:934
bool IsSimilar(const MatrixCSR &other, double tol=std::numeric_limits< double >::epsilon()) const
Definition MatrixCSR-Impl.hpp:360
IndexIterator ColumnIndicesBegin()
Returns the begin iterator of the column indices.
Definition MatrixCSR-Impl.hpp:523
T AbsMin() const
Returns absolute minimum among all elements.
Definition MatrixCSR-Impl.hpp:771
Vector2UZ Size() const
Returns the size of this matrix.
Definition MatrixCSR-Impl.hpp:403
MatrixCSR Sub(const T &s) const
Returns this matrix - input scalar.
Definition MatrixCSR-Impl.hpp:565
T Avg() const
Returns average of all elements.
Definition MatrixCSR-Impl.hpp:725
void SetElement(size_t i, size_t j, const T &value)
Sets non-zero element to (i, j).
Definition MatrixCSR-Impl.hpp:303
MatrixCSR Div(const T &s) const
Returns this matrix / input scalar.
Definition MatrixCSR-Impl.hpp:601
size_t GetCols() const
Returns number of columns of this matrix.
Definition MatrixCSR-Impl.hpp:415
std::vector< size_t > IndexContainerType
Definition MatrixCSR.hpp:91
T Max() const
Returns maximum among all elements.
Definition MatrixCSR-Impl.hpp:751
MatrixCSR RMul(const T &s) const
Returns input scalar * this matrix.
Definition MatrixCSR-Impl.hpp:641
T Trace() const
Definition MatrixCSR-Impl.hpp:807
MatrixCSR RAdd(const T &s) const
Returns input scalar + this matrix.
Definition MatrixCSR-Impl.hpp:612
const size_t * ColumnIndicesData() const
Returns constant pointer of the column indices data.
Definition MatrixCSR-Impl.hpp:469
void ISub(const T &s)
Subtracts input scalar from this matrix.
Definition MatrixCSR-Impl.hpp:671
IndexIterator RowPointersEnd()
Returns the end iterator of the row pointers.
Definition MatrixCSR-Impl.hpp:511
MatrixCSR RDiv(const T &s) const
Returns input matrix / this scalar.
Definition MatrixCSR-Impl.hpp:647
NonZeroIterator NonZeroEnd()
Returns the end iterator of the non-zero elements.
Definition MatrixCSR-Impl.hpp:487
MatrixCSR & operator=(const MatrixCSR &other)
Copies to this matrix.
Definition MatrixCSR-Impl.hpp:113
MatrixCSR & operator-=(const T &s)
Subtraction assignment with input scalar.
Definition MatrixCSR-Impl.hpp:874
void Reserve(size_t rows, size_t cols, size_t numNonZeros)
Reserves memory space of this matrix.
Definition MatrixCSR-Impl.hpp:158
typename NonZeroContainerType::iterator NonZeroIterator
Definition MatrixCSR.hpp:88
MatrixCSR & operator+=(const T &s)
Addition assignment with input scalar.
Definition MatrixCSR-Impl.hpp:858
MatrixCSR Mul(const T &s) const
Returns this matrix * input scalar.
Definition MatrixCSR-Impl.hpp:582
size_t GetCols() const
Number of columns.
Definition MatrixCSR-Impl.hpp:41
T operator()(size_t i, size_t j) const
Returns matrix element at (i, j).
Definition MatrixCSR-Impl.hpp:47
MatrixCSRMatrixMul(const MatrixCSR< T > &m1, const ME &m2)
Definition MatrixCSR-Impl.hpp:23
size_t GetRows() const
Number of rows.
Definition MatrixCSR-Impl.hpp:35
Derived & GetDerived()
Returns actual implementation (the subclass).
Definition MatrixExpression-Impl.hpp:509
Definition Matrix.hpp:30
constexpr size_t GetCols() const
Definition Matrix-Impl.hpp:266
Iterator begin()
Definition Matrix-Impl.hpp:272
constexpr size_t GetRows() const
Definition Matrix-Impl.hpp:260
Iterator end()
Definition Matrix-Impl.hpp:285
Definition pybind11Utils.hpp:21
constexpr size_t ZERO_SIZE
Zero size_t.
Definition Constants.hpp:20
ForwardIter BinaryFind(ForwardIter first, ForwardIter last, const T &value, Compare comp)
Definition CppUtils-Impl.hpp:21
MatrixCSR< T > operator-(const MatrixCSR< T > &a)
Definition MatrixCSR-Impl.hpp:1031
std::enable_if_t< std::is_arithmetic< T >::value, T > AbsMax(T x, T y)
Returns the absolute maximum value among the two inputs.
Definition MathUtils-Impl.hpp:84
void ParallelFor(IndexType beginIndex, IndexType endIndex, const Function &function, ExecutionPolicy policy)
Makes a for-loop from beginIndex to endIndex in parallel.
Definition Parallel-Impl.hpp:212
Matrix< T, Rows, 1 > Vector
Definition Matrix.hpp:738
Vector2< size_t > Vector2UZ
Definition Matrix.hpp:776
MatrixCSR< T > operator+(const MatrixCSR< T > &a, const MatrixCSR< T > &b)
Definition MatrixCSR-Impl.hpp:1037
MatrixCSR< T > operator/(const MatrixCSR< T > &a, T b)
Definition MatrixCSR-Impl.hpp:1092
Value ParallelReduce(IndexType beginIndex, IndexType endIndex, const Value &identity, const Function &function, const Reduce &reduce, ExecutionPolicy policy)
Performs reduce operation in parallel.
Definition Parallel-Impl.hpp:436
Vector< T, 3 > operator*(const Quaternion< T > &q, const Vector< T, 3 > &v)
Returns quaternion q * vector v.
Definition Quaternion-Impl.hpp:543
std::enable_if_t< std::is_arithmetic< T >::value, T > AbsMin(T x, T y)
Returns the absolute minimum value among the two inputs.
Definition MathUtils-Impl.hpp:78
Definition MatrixCSR.hpp:77
Element()
Definition MatrixCSR-Impl.hpp:64