00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include "sparse.h"
00026
00027 template<typename Scalar> void
00028 initSPD(double density,
00029 Matrix<Scalar,Dynamic,Dynamic>& refMat,
00030 SparseMatrix<Scalar>& sparseMat)
00031 {
00032 Matrix<Scalar,Dynamic,Dynamic> aux(refMat.rows(),refMat.cols());
00033 initSparse(density,refMat,sparseMat);
00034 refMat = refMat * refMat.adjoint();
00035 for (int k=0; k<2; ++k)
00036 {
00037 initSparse(density,aux,sparseMat,ForceNonZeroDiag);
00038 refMat += aux * aux.adjoint();
00039 }
00040 sparseMat.setZero();
00041 for (int j=0 ; j<sparseMat.cols(); ++j)
00042 for (int i=j ; i<sparseMat.rows(); ++i)
00043 if (refMat(i,j)!=Scalar(0))
00044 sparseMat.insert(i,j) = refMat(i,j);
00045 sparseMat.finalize();
00046 }
00047
00048 template<typename Scalar> void sparse_solvers(int rows, int cols)
00049 {
00050 double density = std::max(8./(rows*cols), 0.01);
00051 typedef Matrix<Scalar,Dynamic,Dynamic> DenseMatrix;
00052 typedef Matrix<Scalar,Dynamic,1> DenseVector;
00053
00054
00055 DenseVector vec1 = DenseVector::Random(rows);
00056
00057 std::vector<Vector2i> zeroCoords;
00058 std::vector<Vector2i> nonzeroCoords;
00059
00060
00061 {
00062 DenseVector vec2 = vec1, vec3 = vec1;
00063 SparseMatrix<Scalar> m2(rows, cols);
00064 DenseMatrix refMat2 = DenseMatrix::Zero(rows, cols);
00065
00066
00067 initSparse<Scalar>(density, refMat2, m2, ForceNonZeroDiag|MakeLowerTriangular, &zeroCoords, &nonzeroCoords);
00068 VERIFY_IS_APPROX(refMat2.template triangularView<Lower>().solve(vec2),
00069 m2.template triangularView<Lower>().solve(vec3));
00070
00071
00072 initSparse<Scalar>(density, refMat2, m2, ForceNonZeroDiag|MakeUpperTriangular, &zeroCoords, &nonzeroCoords);
00073 VERIFY_IS_APPROX(refMat2.template triangularView<Upper>().solve(vec2),
00074 m2.template triangularView<Upper>().solve(vec3));
00075
00076
00077 initSparse<Scalar>(density, refMat2, m2, ForceNonZeroDiag|MakeLowerTriangular, &zeroCoords, &nonzeroCoords);
00078 VERIFY_IS_APPROX(refMat2.transpose().template triangularView<Upper>().solve(vec2),
00079 m2.transpose().template triangularView<Upper>().solve(vec3));
00080
00081
00082 initSparse<Scalar>(density, refMat2, m2, ForceNonZeroDiag|MakeUpperTriangular, &zeroCoords, &nonzeroCoords);
00083 VERIFY_IS_APPROX(refMat2.transpose().template triangularView<Lower>().solve(vec2),
00084 m2.transpose().template triangularView<Lower>().solve(vec3));
00085
00086 SparseMatrix<Scalar> matB(rows, rows);
00087 DenseMatrix refMatB = DenseMatrix::Zero(rows, rows);
00088
00089
00090 initSparse<Scalar>(density, refMat2, m2, ForceNonZeroDiag|MakeLowerTriangular);
00091 initSparse<Scalar>(density, refMatB, matB);
00092 refMat2.template triangularView<Lower>().solveInPlace(refMatB);
00093 m2.template triangularView<Lower>().solveInPlace(matB);
00094 VERIFY_IS_APPROX(matB.toDense(), refMatB);
00095
00096
00097 initSparse<Scalar>(density, refMat2, m2, ForceNonZeroDiag|MakeUpperTriangular);
00098 initSparse<Scalar>(density, refMatB, matB);
00099 refMat2.template triangularView<Upper>().solveInPlace(refMatB);
00100 m2.template triangularView<Upper>().solveInPlace(matB);
00101 VERIFY_IS_APPROX(matB, refMatB);
00102
00103
00104 initSparse<Scalar>(density, refMat2, m2, ForceNonZeroDiag|MakeLowerTriangular, &zeroCoords, &nonzeroCoords);
00105 VERIFY_IS_APPROX(refMat2.template triangularView<Lower>().solve(vec2),
00106 m2.template triangularView<Lower>().solve(vec3));
00107 }
00108 }
00109
00110 void test_sparse_solvers()
00111 {
00112 for(int i = 0; i < g_repeat; i++) {
00113 CALL_SUBTEST_1(sparse_solvers<double>(8, 8) );
00114 int s = internal::random<int>(1,300);
00115 CALL_SUBTEST_2(sparse_solvers<std::complex<double> >(s,s) );
00116 CALL_SUBTEST_1(sparse_solvers<double>(s,s) );
00117 }
00118 }