自Eigen 3.2起,DynamicSparseMatrix
已被弃用,并且存在可以压缩或非压缩的单个结构SparseMatrix
。单独结构的巨大好处是能够控制压缩阶段。现在,每次操作非压缩SparseMatrix
时,它都会自动压缩。
对于我们的应用程序,这是一个问题,因为它会大大减慢我们矩阵的频繁重新初始化。通常,我们解决非线性方程,我们需要经常更新稀疏矩阵A.我们过去使用旧DynamicSparseMatrix
格式执行此操作,并且运行时性能良好:
main {
SparseMatrix<double> A;
Loop {
A=SomeClass.getUpdatedA();
....
}
}
class SomeClass {
public:
DynamicSparseMatrix<double>& getUpdatedA() {
A = Alinear;
// Add nonlinear contributions calling
loop {
A.coeffRef(row,col) += someNonLinearContribution;
}
}
private:
// A and A linear are preallocated with enough space to store all our contributions
DynamicSparseMatrix<double> A, AlinearPart;
}
使用新版本(将DynamicSparseMatrix
替换为SparseMatrix
),当您调用getUpdatedA()时,A会在第一行之后被压缩。一旦压缩,非线性贡献的增加变得缓慢,因为我们每次都需要重新分配所有内容。
我们过去常常提交a bug in Eigen-related forum,我们已收到ggael的以下回答:
您仍然可以使用
<unsupported/Eigen/SparseExtra>
中的DynamicSparseMatrix。但是,它没有得到官方支持。为了更清洁的解决方案,我需要更多细节:
- A的结构是否会发生变化?还是修好了? - 如果它改变了,是否是由于A_linear的结构?或者由于额外的系数?或两者兼而有之? - A_linear的结构是否会发生变化?
以下是答案:
- A和A_linear的结构是固定的。我们需要一个稀疏矩阵的常数模式,因此如果需要保留结构,我们在稀疏矩阵中标记零项。
- A和Alinear有不同的结构。
最新版本的Eigen是否为此问题引入了官方支持的解决方案?
答案 0 :(得分:1)
一个简单的解决方法是将Alinear
存储为额外的显式零,以使其与A
的结构匹配。此解决方案甚至应该比基于DynamicSparseMatrix
的当前解决方案更快,因为在调用coeffRef()
期间不会发生内存复制:其他条目已经存在于正确的位置。