43 #ifndef IFPACK2_BANDEDCONTAINER_DEF_HPP
44 #define IFPACK2_BANDEDCONTAINER_DEF_HPP
47 #include "Tpetra_CrsMatrix.hpp"
55 # include "Teuchos_DefaultSerialComm.hpp"
60 template<
class MatrixType,
class LocalScalarType>
61 BandedContainer<MatrixType, LocalScalarType, true>::
66 scalar_type DampingFactor) :
67 Container<MatrixType>(matrix, partitions, importer, OverlapLevel, DampingFactor),
68 ipiv_(this->partitions_.size()),
69 kl_(this->numBlocks_, -1),
70 ku_(this->numBlocks_, -1),
72 scalarOffsets_(this->numBlocks_)
75 ! matrix->hasColMap (), std::invalid_argument,
"Ifpack2::BandedContainer: "
76 "The constructor's input matrix must have a column Map.");
79 const map_type& rowMap = * (matrix->getRowMap ());
80 for(
int i = 0; i < this->numBlocks_; i++)
83 for(local_ordinal_type j = 0; j < this->blockRows_[i]; j++)
86 !rowMap.isNodeLocalElement(localRows[j]),
87 std::invalid_argument,
"Ifpack2::BandedContainer: "
88 "On process " << rowMap.getComm ()->getRank () <<
" of "
89 << rowMap.getComm ()->getSize () <<
", in the given set of local row "
91 "entry is not valid local row indices on the calling process: "
92 << localRows[j] <<
".");
95 IsInitialized_ =
false;
99 template<
class MatrixType,
class LocalScalarType>
100 BandedContainer<MatrixType, LocalScalarType, true>::
103 Container<MatrixType>(matrix, localRows),
104 ipiv_(this->blockRows_[0]),
111 "The constructor's input matrix must have a column Map.");
114 const map_type& rowMap = *(matrix->getRowMap());
115 for(local_ordinal_type j = 0; j < this->blockRows_[0]; j++)
118 !rowMap.isNodeLocalElement(localRows[j]),
119 std::invalid_argument,
"Ifpack2::BandedContainer: "
120 "On process " << rowMap.getComm()->getRank() <<
" of "
121 << rowMap.getComm()->getSize() <<
", in the given set of local row "
123 "entry is not valid local row indices on the calling process: "
124 << localRows[j] <<
".");
126 IsInitialized_ =
false;
130 template<
class MatrixType,
class LocalScalarType>
131 BandedContainer<MatrixType, LocalScalarType, true>::
138 template<
class MatrixType,
class LocalScalarType>
139 void BandedContainer<MatrixType, LocalScalarType, true>::
143 if(List.
isParameter(
"relaxation: banded container superdiagonals"))
144 kl_[0] = List.
get<
int>(
"relaxation: banded container superdiagonals");
145 if(List.
isParameter(
"relaxation: banded container subdiagonals"))
146 ku_[0] = List.
get<
int>(
"relaxation: banded container subdiagonals");
148 for(local_ordinal_type b = 1; b < this->numBlocks_; b++)
156 for(local_ordinal_type b = 0; b < this->numBlocks_; b++)
158 if (ku_[b] == -1 || kl_[b] == -1)
161 const size_type numRows = localRows.
size();
164 for(size_type i = 0; i < numRows; ++i)
168 this->inputMatrix_->getLocalRowView(localRows[i], indices, values);
170 size_type min_col_it = numRows > 0 ? numRows - 1 : 0;
171 size_type max_col_it = 0;
173 size_type cntCols = 0;
176 for(size_type c = 0; c < indices.
size(); c++)
178 const local_ordinal_type lColIdx = indices[c];
180 for(size_type j = 0; j < numRows; j++)
182 if (localRows[j] == lColIdx)
184 if(localRows[min_col_it] > lColIdx)
186 if(localRows[max_col_it] < lColIdx)
191 if(cntCols == numRows)
194 ku_[b] = std::max(ku_[b], Teuchos::as<local_ordinal_type>(max_col_it - i));
195 kl_[b] = std::max(kl_[b], Teuchos::as<local_ordinal_type>(i - min_col_it));
199 (kl_[b] == -1 || ku_[b] == -1, std::invalid_argument,
200 "Ifpack2::BandedContainer::setParameters: the user must provide the number"
201 " of sub- and superdiagonals in the 'kl' and 'ku' parameters.");
205 template<
class MatrixType,
class LocalScalarType>
207 BandedContainer<MatrixType, LocalScalarType, true>::
212 for(local_ordinal_type b = 0; b < this->numBlocks_; b++)
215 (kl_[b] == -1 || ku_[b] == -1, std::invalid_argument,
216 "Ifpack2::BandedContainer::initialize: the user must provide the number of"
217 " sub- and superdiagonals in the 'kl' and 'ku' parameters. Make sure that "
218 "you call BandedContainer<T>::setParameters!");
220 global_ordinal_type totalScalars = 0;
221 for(local_ordinal_type b = 0; b < this->numBlocks_; b++)
223 local_ordinal_type stride = 2 * kl_[b] + ku_[b] + 1;
224 scalarOffsets_[b] = totalScalars;
225 totalScalars += stride * this->blockRows_[b];
227 scalars_ =
new local_scalar_type[totalScalars];
228 for(
int b = 0; b < this->numBlocks_; b++)
230 local_ordinal_type nrows = this->blockRows_[b];
231 diagBlocks_.emplace_back(
Teuchos::View, scalars_ + scalarOffsets_[b], 2 * kl_[b] + ku_[b] + 1, nrows, nrows, kl_[b], kl_[b] + ku_[b]);
236 IsInitialized_ =
false;
238 std::fill (ipiv_.begin (), ipiv_.end (), 0);
239 IsInitialized_ =
true;
242 template<
class MatrixType,
class LocalScalarType>
244 BandedContainer<MatrixType, LocalScalarType, true>::
248 ipiv_.size () != this->partitions_.size(), std::logic_error,
249 "Ifpack2::BandedContainer::compute: ipiv_ array has the wrong size. "
250 "Please report this bug to the Ifpack2 developers.");
253 if (! this->isInitialized ()) {
264 template<
class MatrixType,
class LocalScalarType>
266 BandedContainer<MatrixType, LocalScalarType, true>::
269 std::vector<HostViewLocal> empty1;
270 std::swap(empty1, X_local);
271 std::vector<HostViewLocal> empty2;
272 std::swap(empty2, Y_local);
273 Container<MatrixType>::clearBlocks ();
276 template<
class MatrixType,
class LocalScalarType>
278 BandedContainer<MatrixType, LocalScalarType, true>::
284 for(
int i = 0; i < this->numBlocks_; i++)
288 "BandedContainer<T>::factor: Diagonal block is an empty SerialBandDenseMatrix<T>!");
290 "BandedContainer<T>::factor: Diagonal block needs kl additional superdiagonals for factorization! However, the number of superdiagonals is smaller than the number of subdiagonals!");
291 int* blockIpiv = &ipiv_[this->partitionIndices_[i]];
292 lapack.
GBTRF (diagBlocks_[i].numRows(),
293 diagBlocks_[i].numCols(),
294 diagBlocks_[i].lowerBandwidth(),
295 diagBlocks_[i].upperBandwidth() - diagBlocks_[i].lowerBandwidth(),
296 diagBlocks_[i].values(),
297 diagBlocks_[i].stride(),
303 INFO < 0, std::logic_error,
"Ifpack2::BandedContainer::factor: "
304 "LAPACK's _GBTRF (LU factorization with partial pivoting) was called "
305 "incorrectly. INFO = " << INFO <<
" < 0. "
306 "Please report this bug to the Ifpack2 developers.");
311 INFO > 0, std::runtime_error,
"Ifpack2::BandedContainer::factor: "
312 "LAPACK's _GBTRF (LU factorization with partial pivoting) reports that the "
313 "computed U factor is exactly singular. U(" << INFO <<
"," << INFO <<
") "
314 "(one-based index i) is exactly zero. This probably means that the input "
315 "matrix has a singular diagonal block.");
319 template<
class MatrixType,
class LocalScalarType>
321 BandedContainer<MatrixType, LocalScalarType, true>::
322 applyImpl (HostViewLocal& X,
327 const local_scalar_type alpha,
328 const local_scalar_type beta)
const
335 using Teuchos::rcpFromRef;
338 X.extent (0) != Y.extent (0),
339 std::logic_error,
"Ifpack2::BandedContainer::applyImpl: X and Y have "
340 "incompatible dimensions (" << X.extent (0) <<
" resp. "
341 << Y.extent (0) <<
"). Please report this bug to "
342 "the Ifpack2 developers.");
344 X.extent (0) !=
static_cast<size_t> (mode ==
Teuchos::NO_TRANS ? diagBlocks_[blockIndex].numCols() : diagBlocks_[blockIndex].numRows()),
345 std::logic_error,
"Ifpack2::BandedContainer::applyImpl: The input "
346 "multivector X has incompatible dimensions from those of the "
347 "inverse operator (" << X.extent (0) <<
" vs. "
348 << (mode ==
Teuchos::NO_TRANS ? diagBlocks_[blockIndex].numCols() : diagBlocks_[blockIndex].numRows())
349 <<
"). Please report this bug to the Ifpack2 developers.");
351 Y.extent (0) !=
static_cast<size_t> (mode ==
Teuchos::NO_TRANS ? diagBlocks_[blockIndex].numRows() : diagBlocks_[blockIndex].numCols()),
352 std::logic_error,
"Ifpack2::BandedContainer::applyImpl: The output "
353 "multivector Y has incompatible dimensions from those of the "
354 "inverse operator (" << Y.extent (0) <<
" vs. "
355 << (mode ==
Teuchos::NO_TRANS ? diagBlocks_[blockIndex].numRows() : diagBlocks_[blockIndex].numCols())
356 <<
"). Please report this bug to the Ifpack2 developers.");
358 size_t numVecs = (int) X.extent (1);
366 for(
size_t j = 0; j < Y.extent(0); j++)
367 for(
size_t i = 0; i < Y.extent(1); i++)
371 for(
size_t j = 0; j < Y.extent(0); j++)
372 for(
size_t i = 0; i < Y.extent(1); i++)
373 Y(i, j) = beta * (local_impl_scalar_type) Y(i, j);
381 Ptr<HostViewLocal> Y_tmp;
382 bool deleteYT =
false;
388 Y_tmp = ptr (
new HostViewLocal (
"", X.extent (0), X.extent (1)));
390 Kokkos::deep_copy(*Y_tmp, X);
393 local_scalar_type*
const Y_ptr = (local_scalar_type*) Y_tmp->data();
398 const int* blockIpiv = &ipiv_[this->partitionIndices_[blockIndex]];
400 diagBlocks_[blockIndex].numCols(),
401 diagBlocks_[blockIndex].lowerBandwidth(),
403 diagBlocks_[blockIndex].upperBandwidth() - diagBlocks_[blockIndex].lowerBandwidth(),
405 diagBlocks_[blockIndex].values(),
406 diagBlocks_[blockIndex].stride(),
408 Y_ptr, stride, &INFO);
411 INFO != 0, std::runtime_error,
"Ifpack2::BandedContainer::applyImpl: "
412 "LAPACK's _GBTRS (solve using LU factorization with partial pivoting) "
413 "failed with INFO = " << INFO <<
" != 0.");
416 for(
size_t j = 0; j < Y.extent(1); j++)
417 for(
size_t i = 0; i < Y.extent(0); i++)
418 Y(i, j) = beta * Y(i, j) + alpha * (*Y_tmp)(i, j);
425 template<
class MatrixType,
class LocalScalarType>
427 BandedContainer<MatrixType, LocalScalarType, true>::
434 scalar_type beta)
const
448 Details::MultiVectorLocalGatherScatter<mv_type, local_mv_type> mvgs;
449 const size_t numVecs = X.extent(1);
452 ! IsComputed_, std::runtime_error,
"Ifpack2::BandedContainer::apply: "
453 "You must have called the compute() method before you may call apply(). "
454 "You may call the apply() method as many times as you want after calling "
455 "compute() once, but you must have called compute() at least once.");
457 X.extent(1) != Y.extent(1), std::runtime_error,
458 "Ifpack2::BandedContainer::apply: X and Y have different numbers of "
459 "vectors. X has " << X.extent(1)
460 <<
", but Y has " << Y.extent(1) <<
".");
481 if(X_local.size() == 0)
485 for(
int i = 0; i < this->numBlocks_; i++)
487 X_local.emplace_back(
"", this->blockRows_[i], numVecs);
489 for(
int i = 0; i < this->numBlocks_; i++)
491 Y_local.emplace_back(
"", this->blockRows_[i], numVecs);
495 ArrayView<const local_ordinal_type> localRows = this->getLocalRows(blockIndex);
497 mvgs.gatherViewToView(X_local[blockIndex], X, localRows);
504 mvgs.gatherViewToView (Y_local[blockIndex], Y, localRows);
508 this->applyImpl (X_local[blockIndex], Y_local[blockIndex], blockIndex, stride, mode, as<local_scalar_type>(alpha),
509 as<local_scalar_type>(beta));
513 mvgs.scatterViewToView(Y, Y_local[blockIndex], localRows);
516 template<
class MatrixType,
class LocalScalarType>
518 BandedContainer<MatrixType, LocalScalarType, true>::
519 weightedApply (HostView& ,
535 using Teuchos::rcp_const_cast;
540 true, std::runtime_error,
"Ifpack2::BandedContainer::"
541 "weightedApply: This code is not tested and not used. Expect bugs.");
557 Details::MultiVectorLocalGatherScatter<mv_type, local_mv_type> mvgs;
558 const size_t numVecs = X.extent(1);
561 ! IsComputed_, std::runtime_error,
"Ifpack2::BandedContainer::"
562 "weightedApply: You must have called the compute() method before you may "
563 "call apply(). You may call the apply() method as many times as you want "
564 "after calling compute() once, but you must have called compute() at least "
567 numVecs != Y.extent(1), std::runtime_error,
568 "Ifpack2::BandedContainer::weightedApply: X and Y have different numbers "
569 "of vectors. X has " << X.extent(1) <<
", but Y has "
570 << Y.extent(1) <<
".");
600 const size_t numRows = this->blockRows_[blockIndex];
602 if(X_local.size() == 0)
606 for(
int i = 0; i < this->numBlocks_; i++)
608 X_local.emplace_back(
"", this->blockRows_[i], numVecs);
610 for(
int i = 0; i < this->numBlocks_; i++)
612 Y_local.emplace_back(
"", this->blockRows_[i], numVecs);
616 HostViewLocal D_local(
"", numRows, 1);
617 HostViewLocal X_scaled(
"", numRows, numVecs);
619 ArrayView<const local_ordinal_type> localRows = this->getLocalRows(blockIndex);
620 mvgs.gatherViewToView (X_local[blockIndex], X, localRows);
627 mvgs.gatherViewToView (Y_local[blockIndex], Y, localRows);
639 mvgs.gatherViewToView (D_local, D, localRows);
641 for(
size_t j = 0; j < numVecs; j++)
642 for(
size_t i = 0; i < numRows; i++)
643 X_scaled(i, j) = X_local[blockIndex](i, j) * D_local(i, 0);
650 Ptr<HostViewLocal> Y_temp;
651 bool deleteYT =
false;
653 Y_temp = ptr(&Y_local[blockIndex]);
656 Y_temp = ptr(
new HostViewLocal(
"", numRows, numVecs));
661 applyImpl(X_scaled, *Y_temp, blockIndex, stride, mode, one, one);
668 for(
size_t j = 0; j < numVecs; j++)
669 for(
size_t i = 0; i < numRows; i++)
670 Y_local[blockIndex](i, j) = Y_local[blockIndex](i, j) * (local_impl_scalar_type) beta + (local_impl_scalar_type) alpha * (*Y_temp)(i, j) * D_local(i, 0);
677 mvgs.scatterViewToView (Y, Y_local[blockIndex], localRows);
682 template<
class MatrixType,
class LocalScalarType>
684 BandedContainer<MatrixType, LocalScalarType, true>::
685 print (std::ostream& os)
const
688 fos.setOutputToRootOnly (0);
693 template<
class MatrixType,
class LocalScalarType>
695 BandedContainer<MatrixType, LocalScalarType, true>::
698 std::ostringstream oss;
700 if (isInitialized()) {
702 oss <<
"{status = initialized, computed";
705 oss <<
"{status = initialized, not computed";
709 oss <<
"{status = not initialized, not computed";
715 template<
class MatrixType,
class LocalScalarType>
717 BandedContainer<MatrixType, LocalScalarType, true>::
722 os <<
"================================================================================" << std::endl;
723 os <<
"Ifpack2::BandedContainer" << std::endl;
724 for(
int i = 0; i < this->numBlocks_; i++)
726 os <<
"Block " << i <<
": Number of rows = " << this->blockRows_[i] << std::endl;
727 os <<
"Block " << i <<
": Number of subdiagonals = " << diagBlocks_[i].lowerBandwidth() << std::endl;
728 os <<
"Block " << i <<
": Number of superdiagonals = " << diagBlocks_[i].upperBandwidth() << std::endl;
730 os <<
"isInitialized() = " << IsInitialized_ << std::endl;
731 os <<
"isComputed() = " << IsComputed_ << std::endl;
732 os <<
"================================================================================" << std::endl;
736 template<
class MatrixType,
class LocalScalarType>
738 BandedContainer<MatrixType, LocalScalarType, true>::
744 auto& A = *this->inputMatrix_;
745 const size_t inputMatrixNumRows = A.getNodeNumRows ();
749 const int myRank = A.getRowMap()->getComm()->getRank();
750 const int numProcs = A.getRowMap()->getComm()->getSize();
752 for(
int blockIndex = 0; blockIndex < this->numBlocks_; blockIndex++)
754 const local_ordinal_type numRows_ = this->blockRows_[blockIndex];
757 ArrayView<const local_ordinal_type> localRows = this->getLocalRows(blockIndex);
758 for(local_ordinal_type j = 0; j < numRows_; j++)
762 static_cast<size_t> (localRows[j]) >= inputMatrixNumRows,
763 std::runtime_error,
"Ifpack2::BandedContainer::extract: On process " <<
764 myRank <<
" of " << numProcs <<
", localRows[j=" << j <<
"] = " <<
765 localRows[j] <<
", which is out of the valid range of local row indices "
766 "indices [0, " << (inputMatrixNumRows - 1) <<
"] for the input matrix.");
779 const map_type& globalRowMap = *(A.getRowMap ());
780 const map_type& globalColMap = *(A.getColMap ());
781 const map_type& globalDomMap = *(A.getDomainMap ());
783 bool rowIndsValid =
true;
784 bool colIndsValid =
true;
785 Array<local_ordinal_type> localCols (numRows_);
788 Array<local_ordinal_type> invalidLocalRowInds;
789 Array<global_ordinal_type> invalidGlobalColInds;
790 for(local_ordinal_type i = 0; i < numRows_; i++)
793 const local_ordinal_type ii_local = localRows[i];
798 const global_ordinal_type jj_global = globalRowMap.getGlobalElement(ii_local);
806 rowIndsValid =
false;
807 invalidLocalRowInds.push_back(ii_local);
812 if(globalDomMap.isNodeGlobalElement(jj_global))
822 const local_ordinal_type jj_local = globalColMap.getLocalElement(jj_global);
825 colIndsValid =
false;
826 invalidGlobalColInds.push_back(jj_global);
829 localCols[i] = jj_local;
833 ! rowIndsValid, std::logic_error,
"Ifpack2::BandedContainer::extract: "
834 "On process " << myRank <<
", at least one row index in the set of local "
835 "row indices given to the constructor is not a valid local row index in "
836 "the input matrix's row Map on this process. This should be impossible "
837 "because the constructor checks for this case. Here is the complete set "
838 "of invalid local row indices: " <<
toString(invalidLocalRowInds) <<
". "
839 "Please report this bug to the Ifpack2 developers.");
841 ! colIndsValid, std::runtime_error,
"Ifpack2::BandedContainer::extract: "
842 "On process " << myRank <<
", "
843 "At least one row index in the set of row indices given to the constructor "
844 "does not have a corresponding column index in the input matrix's column "
845 "Map. This probably means that the column(s) in question is/are empty on "
846 "this process, which would make the submatrix to extract structurally "
847 "singular. Here is the compete set of invalid global column indices: "
848 <<
toString(invalidGlobalColInds) <<
".");
850 const size_t maxNumEntriesInRow = A.getNodeMaxNumRowEntries();
851 Array<scalar_type> val(maxNumEntriesInRow);
852 Array<local_ordinal_type> ind(maxNumEntriesInRow);
855 for (local_ordinal_type i = 0; i < numRows_; i++)
857 const local_ordinal_type localRow = this->partitions_[this->partitionIndices_[blockIndex] + i];
859 A.getLocalRowCopy(localRow, ind(), val(), numEntries);
860 for (
size_t k = 0; k < numEntries; ++k)
862 const local_ordinal_type localCol = ind[k];
872 if(localCol >= 0 && static_cast<size_t>(localCol) < inputMatrixNumRows)
876 local_ordinal_type jj = INVALID;
877 for (
size_t kk = 0; kk < (size_t) numRows_; kk++)
879 if(localRows[kk] == localCol)
883 diagBlocks_[blockIndex](i, jj) += val[k];
890 template<
class MatrixType,
class LocalScalarType>
891 std::string BandedContainer<MatrixType, LocalScalarType, true>::getName()
896 template<
class MatrixType,
class LocalScalarType>
897 BandedContainer<MatrixType, LocalScalarType, false>::
902 scalar_type DampingFactor) :
903 Container<MatrixType>(matrix, partitions, importer, OverlapLevel, DampingFactor)
906 (
true, std::logic_error,
"Ifpack2::BandedContainer: Not implemented for "
911 template<
class MatrixType,
class LocalScalarType>
912 BandedContainer<MatrixType, LocalScalarType, false>::
915 Container<MatrixType>(matrix, localRows)
918 (
true, std::logic_error,
"Ifpack2::BandedContainer: Not implemented for "
923 template<
class MatrixType,
class LocalScalarType>
924 BandedContainer<MatrixType, LocalScalarType, false>::
925 ~BandedContainer () {}
927 template<
class MatrixType,
class LocalScalarType>
928 void BandedContainer<MatrixType, LocalScalarType, false>::
931 template<
class MatrixType,
class LocalScalarType>
933 BandedContainer<MatrixType, LocalScalarType, false>::
936 template<
class MatrixType,
class LocalScalarType>
938 BandedContainer<MatrixType, LocalScalarType, false>::
941 template<
class MatrixType,
class LocalScalarType>
943 BandedContainer<MatrixType, LocalScalarType, false>::
946 template<
class MatrixType,
class LocalScalarType>
948 BandedContainer<MatrixType, LocalScalarType, false>::
951 template<
class MatrixType,
class LocalScalarType>
953 BandedContainer<MatrixType, LocalScalarType, false>::
954 applyImpl (HostViewLocal& X,
959 const local_scalar_type alpha,
960 const local_scalar_type beta)
const {}
962 template<
class MatrixType,
class LocalScalarType>
964 BandedContainer<MatrixType, LocalScalarType, false>::
971 scalar_type beta)
const {}
973 template<
class MatrixType,
class LocalScalarType>
975 BandedContainer<MatrixType, LocalScalarType, false>::
976 weightedApply (HostView& X,
983 scalar_type beta)
const {}
985 template<
class MatrixType,
class LocalScalarType>
987 BandedContainer<MatrixType, LocalScalarType, false>::
988 print (std::ostream& os)
const
993 template<
class MatrixType,
class LocalScalarType>
995 BandedContainer<MatrixType, LocalScalarType, false>::
1001 template<
class MatrixType,
class LocalScalarType>
1003 BandedContainer<MatrixType, LocalScalarType, false>::
1007 template<
class MatrixType,
class LocalScalarType>
1009 BandedContainer<MatrixType, LocalScalarType, false>::
1012 template<
class MatrixType,
class LocalScalarType>
1013 std::string BandedContainer<MatrixType, LocalScalarType, false>::getName()
1020 #define IFPACK2_BANDEDCONTAINER_INSTANT(S,LO,GO,N) \
1021 template class Ifpack2::BandedContainer< Tpetra::RowMatrix<S, LO, GO, N>, S >;
1023 #endif // IFPACK2_BANDEDCONTAINER_HPP
T & get(const std::string &name, T def_value)
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
void GBTRF(const OrdinalType &m, const OrdinalType &n, const OrdinalType &kl, const OrdinalType &ku, ScalarType *A, const OrdinalType &lda, OrdinalType *IPIV, OrdinalType *info) const
bool isParameter(const std::string &name) const
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
virtual std::string description() const
TEUCHOSCORE_LIB_DLL_EXPORT std::string toString(const EVerbosityLevel verbLevel)
void GBTRS(const char &TRANS, const OrdinalType &n, const OrdinalType &kl, const OrdinalType &ku, const OrdinalType &nrhs, const ScalarType *A, const OrdinalType &lda, const OrdinalType *IPIV, ScalarType *B, const OrdinalType &ldb, OrdinalType *info) const
TypeTo as(const TypeFrom &t)
std::string toString(const T &t)