Быстрое справочное руководство по разреженным матрицам
На этой странице приводится краткий обзор основных операций, доступных для разреженных матриц в классе SparseMatrix. Сначала рекомендуется ознакомиться с вводным руководством по Обработке разреженных матриц. Важно помнить, как хранятся разреженные матрицы: либо по строкам, либо по столбцам. По умолчанию используется порядок по столбцам. Большинство арифметических операций над разреженными матрицами предполагают, что они имеют одинаковый порядок хранения.
Инициализация разреженной матрицы
| Категория | Операции | Примечания |
|---|---|---|
| Конструктор |
SparseMatrix<double> sm1(1000,1000); SparseMatrix<std::complex<double>,RowMajor> sm2; |
По умолчанию ColMajor |
| Изменение размера/резервирование |
sm1.resize(m,n); // Change sm1 to a m x n matrix. sm1.reserve(nnz); // Allocate room for nnz nonzeros elements. |
Обратите внимание, что при вызове reserve() не требуется, чтобы nnz было точным числом ненулевых элементов в конечной матрице. Однако точная оценка позволит избежать многократных перераспределений во время фазы вставки. |
| Присвоение |
SparseMatrix<double,Colmajor> sm1; // Initialize sm2 with sm1. SparseMatrix<double,Rowmajor> sm2(sm1), sm3; // Assignment and evaluations modify the storage order. sm3 = sm1; |
Конструктор копирования может использоваться для преобразования из одного порядка хранения в другой |
| Вставка по элементам |
// Insert a new element; sm1.insert(i, j) = v_ij; // Update the value v_ij sm1.coeffRef(i,j) = v_ij; sm1.coeffRef(i,j) += v_ij; sm1.coeffRef(i,j) -= v_ij; |
insert() предполагает, что элемент еще не существует; в противном случае используйте coeffRef() |
| Партийная вставка |
std::vector< Eigen::Triplet<double> > tripletList;
tripletList.reserve(estimation_of_entries);
// -- Fill tripletList with nonzero elements...
sm1.setFromTriplets(TripletList.begin(), TripletList.end());
|
Полный пример доступен по адресу Вставка по тройкам. |
| Вставка констант или случайных значений |
sm1.setZero(); |
Удаление всех ненулевых коэффициентов |
Свойства матрицы
Помимо основных функций rows() и cols(), существуют полезные функции, позволяющие легко получить информацию о матрице.
sm1.rows(); // Number of rows sm1.cols(); // Number of columns sm1.nonZeros(); // Number of non zero values sm1.outerSize(); // Number of columns (resp. rows) for a column major (resp. row major ) sm1.innerSize(); // Number of rows (resp. columns) for a row major (resp. column major) sm1.norm(); // Euclidian norm of the matrix sm1.squaredNorm(); // Squared norm of the matrix sm1.blueNorm(); sm1.isVector(); // Check if sm1 is a sparse vector or a sparse matrix sm1.isCompressed(); // Check if sm1 is in compressed form ... |
Арифметические операции
Легко выполнять арифметические операции над разреженными матрицами при условии, что размерности согласованы и матрицы имеют одинаковый порядок хранения. Обратите внимание, что вычисления всегда могут выполняться в матрице с другим порядком хранения. В дальнейшем sm обозначает разреженную матрицу, dm — плотную матрицу, а dv — плотный вектор.
| Операции | Код |
Примечания |
|---|---|---|
| Сложение/вычитание |
sm3 = sm1 + sm2; sm3 = sm1 - sm2; sm2 += sm1; sm2 -= sm1; |
sm1 и sm2 должны иметь одинаковый порядок хранения |
| Умножение на скаляр |
sm3 = sm1 * s1; sm3 *= s1; sm3 = s1 * sm1 + s2 * sm2; sm3 /= s1; |
Возможны различные комбинации, если размерности и порядок хранения совпадают. |
| Умножение разреженных матриц |
sm3 = sm1 * sm2; dm2 = sm1 * dm1; dv2 = sm1 * dv1; |
|
| Транспонирование, сопряжение |
sm2 = sm1.transpose(); sm2 = sm1.adjoint(); |
Обратите внимание, что транспонирование изменяет порядок хранения. Поддержка transposeInPlace() отсутствует. |
| Перестановка |
perm.indices(); // Reference to the vector of indices sm1.twistedBy(perm); // Permute rows and columns sm2 = sm1 * perm; // Permute the columns sm2 = perm * sm1; // Permute the columns |
|
| Элементные операции |
sm1.cwiseProduct(sm2); sm1.cwiseQuotient(sm2); sm1.cwiseMin(sm2); sm1.cwiseMax(sm2); sm1.cwiseAbs(); sm1.cwiseSqrt(); |
sm1 и sm2 должны иметь одинаковый порядок хранения |
Другие поддерживаемые операции
| Код | Примечания |
|---|---|
| Подматрицы | |
sm1.block(startRow, startCol, rows, cols); sm1.block(startRow, startCol); sm1.topLeftCorner(rows, cols); sm1.topRightCorner(rows, cols); sm1.bottomLeftCorner( rows, cols); sm1.bottomRightCorner( rows, cols); |
В отличие от плотных матриц, здесь все эти методы являются только для чтения. См. Операции с блоками и ниже для подматриц чтения/записи. |
| Диапазон | |
sm1.innerVector(outer); // RW sm1.innerVectors(start, size); // RW sm1.leftCols(size); // RW sm2.rightCols(size); // RO because sm2 is row-major sm1.middleRows(start, numRows); // RO because sm1 is column-major sm1.middleCols(start, numCols); // RW sm1.col(j); // RW |
Внутренний вектор представляет собой либо строку (для хранения по строкам), либо столбец (для хранения по столбцам). Как отмечалось ранее, для подматрицы чтения/записи (RW) вычисление может выполняться в матрице с другим порядком хранения. |
| Представления треугольных и самосопряженных матриц | |
sm2 = sm1.triangularview<Lower>(); sm2 = sm1.selfadjointview<Lower>(); |
Возможны различные комбинации представлений треугольных матриц и блоков |
| Решение треугольных систем | |
dv2 = sm1.triangularView<Upper>().solve(dv1); dv2 = sm1.topLeftCorner(size, size) .triangularView<Lower>().solve(dv1); |
Для решения общих разреженных систем используйте соответствующий модуль, описанный в Решении разреженных линейных систем |
| API низкого уровня | |
sm1.valuePtr(); // Pointer to the values sm1.innerIndexPtr(); // Pointer to the indices. sm1.outerIndexPtr(); // Pointer to the beginning of each inner vector |
Если матрица не в сжатой форме, перед использованием необходимо вызвать makeCompressed(). Обратите внимание, что эти функции в основном предоставляются для обеспечения совместимости с внешними библиотеками. Более удобный доступ к значениям матрицы осуществляется с помощью класса InnerIterator, как описано в разделе Руководства по разреженным матрицам |
| Картирование внешних буферов | |
int outerIndexPtr[cols+1]; int innerIndices[nnz]; double values[nnz]; Map<SparseMatrix<double> > sm1(rows,cols,nnz,outerIndexPtr, // read-write innerIndices,values); Map<const SparseMatrix<double> > sm2(...); // read-only |
Как и для плотных матриц, класс Map<SparseMatrixType> можно использовать для представления внешних буферов как объекта Eigen's SparseMatrix. |
© Eigen.
Licensed under the MPL2 License.
https://eigen.tuxfamily.org/dox/group__SparseQuickRefPage.html