mirror of
https://gitlab.com/libeigen/eigen.git
synced 2025-04-20 00:29:38 +08:00
move sparse solvers from unsupported/ to main Eigen/ and remove the "not stable yet" warning
This commit is contained in:
parent
dcb66d6b40
commit
53fa851724
@ -1,7 +1,7 @@
|
||||
#ifndef EIGEN_CHOLMODSUPPORT_MODULE_H
|
||||
#define EIGEN_CHOLMODSUPPORT_MODULE_H
|
||||
|
||||
#include "SparseExtra"
|
||||
#include "SparseCore"
|
||||
|
||||
#include "../../Eigen/src/Core/util/DisableStupidWarnings.h"
|
||||
|
||||
@ -11,8 +11,8 @@ extern "C" {
|
||||
|
||||
namespace Eigen {
|
||||
|
||||
/** \ingroup Unsupported_modules
|
||||
* \defgroup CholmodSupport_Module Cholmod Support module
|
||||
/** \ingroup Sparse_modules
|
||||
* \defgroup CholmodSupport_Module CholmodSupport module
|
||||
*
|
||||
*
|
||||
* \code
|
||||
@ -20,9 +20,10 @@ namespace Eigen {
|
||||
* \endcode
|
||||
*/
|
||||
|
||||
struct Cholmod {};
|
||||
#include "src/SparseExtra/CholmodSupportLegacy.h"
|
||||
#include "src/SparseExtra/CholmodSupport.h"
|
||||
#include "src/misc/Solve.h"
|
||||
#include "src/misc/SparseSolve.h"
|
||||
|
||||
#include "src/CholmodSupport/CholmodSupport.h"
|
||||
|
||||
|
||||
} // namespace Eigen
|
62
Eigen/Sparse
62
Eigen/Sparse
@ -1,69 +1,27 @@
|
||||
#ifndef EIGEN_SPARSE_MODULE_H
|
||||
#define EIGEN_SPARSE_MODULE_H
|
||||
|
||||
#include "Core"
|
||||
|
||||
#include "src/Core/util/DisableStupidWarnings.h"
|
||||
|
||||
#include <vector>
|
||||
#include <map>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <algorithm>
|
||||
|
||||
#ifdef EIGEN2_SUPPORT
|
||||
#define EIGEN_YES_I_KNOW_SPARSE_MODULE_IS_NOT_STABLE_YET
|
||||
#endif
|
||||
|
||||
#ifndef EIGEN_YES_I_KNOW_SPARSE_MODULE_IS_NOT_STABLE_YET
|
||||
#error The sparse module API is not stable yet. To use it anyway, please define the EIGEN_YES_I_KNOW_SPARSE_MODULE_IS_NOT_STABLE_YET preprocessor token.
|
||||
#endif
|
||||
|
||||
namespace Eigen {
|
||||
|
||||
/** \defgroup Sparse_Module Sparse module
|
||||
/** \defgroup Sparse_modules Sparse modules
|
||||
*
|
||||
*
|
||||
*
|
||||
* See the \ref TutorialSparse "Sparse tutorial"
|
||||
* Meta-module including all related modules:
|
||||
* - SparseCore
|
||||
* - OrderingMethods
|
||||
* - SparseCholesky
|
||||
* - IterativeLinearSolvers
|
||||
*
|
||||
* \code
|
||||
* #include <Eigen/Sparse>
|
||||
* \endcode
|
||||
*/
|
||||
|
||||
/** The type used to identify a general sparse storage. */
|
||||
struct Sparse {};
|
||||
|
||||
#include "src/Sparse/SparseUtil.h"
|
||||
#include "src/Sparse/SparseMatrixBase.h"
|
||||
#include "src/Sparse/CompressedStorage.h"
|
||||
#include "src/Sparse/AmbiVector.h"
|
||||
#include "src/Sparse/SparseMatrix.h"
|
||||
#include "src/Sparse/MappedSparseMatrix.h"
|
||||
#include "src/Sparse/SparseVector.h"
|
||||
#include "src/Sparse/CoreIterators.h"
|
||||
#include "src/Sparse/SparseBlock.h"
|
||||
#include "src/Sparse/SparseTranspose.h"
|
||||
#include "src/Sparse/SparseCwiseUnaryOp.h"
|
||||
#include "src/Sparse/SparseCwiseBinaryOp.h"
|
||||
#include "src/Sparse/SparseDot.h"
|
||||
#include "src/Sparse/SparseAssign.h"
|
||||
#include "src/Sparse/SparseRedux.h"
|
||||
#include "src/Sparse/SparseFuzzy.h"
|
||||
#include "src/Sparse/ConservativeSparseSparseProduct.h"
|
||||
#include "src/Sparse/SparseSparseProductWithPruning.h"
|
||||
#include "src/Sparse/SparseProduct.h"
|
||||
#include "src/Sparse/SparseDenseProduct.h"
|
||||
#include "src/Sparse/SparseDiagonalProduct.h"
|
||||
#include "src/Sparse/SparseTriangularView.h"
|
||||
#include "src/Sparse/SparseSelfAdjointView.h"
|
||||
#include "src/Sparse/TriangularSolver.h"
|
||||
#include "src/Sparse/SparseView.h"
|
||||
|
||||
} // namespace Eigen
|
||||
|
||||
#include "src/Core/util/ReenableStupidWarnings.h"
|
||||
#include "SparseCore"
|
||||
#include "OrderingMethods"
|
||||
#include "SparseCholesky"
|
||||
#include "IterativeLinearSolvers"
|
||||
|
||||
#endif // EIGEN_SPARSE_MODULE_H
|
||||
|
||||
|
64
Eigen/SparseCore
Normal file
64
Eigen/SparseCore
Normal file
@ -0,0 +1,64 @@
|
||||
#ifndef EIGEN_SPARSECORE_MODULE_H
|
||||
#define EIGEN_SPARSECORE_MODULE_H
|
||||
|
||||
#include "Core"
|
||||
|
||||
#include "src/Core/util/DisableStupidWarnings.h"
|
||||
|
||||
#include <vector>
|
||||
#include <map>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <algorithm>
|
||||
|
||||
namespace Eigen {
|
||||
|
||||
/** \defgroup Sparse_Module SparseCore module
|
||||
*
|
||||
* This module provides a sparse matrix representation, and basic associatd matrix manipulations
|
||||
* and operations.
|
||||
*
|
||||
* See the \ref TutorialSparse "Sparse tutorial"
|
||||
*
|
||||
* \code
|
||||
* #include <Eigen/SparseCore>
|
||||
* \endcode
|
||||
*
|
||||
* This module depends on: Core.
|
||||
*/
|
||||
|
||||
/** The type used to identify a general sparse storage. */
|
||||
struct Sparse {};
|
||||
|
||||
#include "src/SparseCore/SparseUtil.h"
|
||||
#include "src/SparseCore/SparseMatrixBase.h"
|
||||
#include "src/SparseCore/CompressedStorage.h"
|
||||
#include "src/SparseCore/AmbiVector.h"
|
||||
#include "src/SparseCore/SparseMatrix.h"
|
||||
#include "src/SparseCore/MappedSparseMatrix.h"
|
||||
#include "src/SparseCore/SparseVector.h"
|
||||
#include "src/SparseCore/CoreIterators.h"
|
||||
#include "src/SparseCore/SparseBlock.h"
|
||||
#include "src/SparseCore/SparseTranspose.h"
|
||||
#include "src/SparseCore/SparseCwiseUnaryOp.h"
|
||||
#include "src/SparseCore/SparseCwiseBinaryOp.h"
|
||||
#include "src/SparseCore/SparseDot.h"
|
||||
#include "src/SparseCore/SparseAssign.h"
|
||||
#include "src/SparseCore/SparseRedux.h"
|
||||
#include "src/SparseCore/SparseFuzzy.h"
|
||||
#include "src/SparseCore/ConservativeSparseSparseProduct.h"
|
||||
#include "src/SparseCore/SparseSparseProductWithPruning.h"
|
||||
#include "src/SparseCore/SparseProduct.h"
|
||||
#include "src/SparseCore/SparseDenseProduct.h"
|
||||
#include "src/SparseCore/SparseDiagonalProduct.h"
|
||||
#include "src/SparseCore/SparseTriangularView.h"
|
||||
#include "src/SparseCore/SparseSelfAdjointView.h"
|
||||
#include "src/SparseCore/TriangularSolver.h"
|
||||
#include "src/SparseCore/SparseView.h"
|
||||
|
||||
} // namespace Eigen
|
||||
|
||||
#include "src/Core/util/ReenableStupidWarnings.h"
|
||||
|
||||
#endif // EIGEN_SPARSECORE_MODULE_H
|
||||
|
@ -1,7 +1,7 @@
|
||||
#ifndef EIGEN_SUPERLUSUPPORT_MODULE_H
|
||||
#define EIGEN_SUPERLUSUPPORT_MODULE_H
|
||||
|
||||
#include "SparseExtra"
|
||||
#include "SparseCore"
|
||||
|
||||
#include "../../Eigen/src/Core/util/DisableStupidWarnings.h"
|
||||
|
||||
@ -30,8 +30,8 @@ namespace Eigen { struct SluMatrix; }
|
||||
|
||||
namespace Eigen {
|
||||
|
||||
/** \ingroup Unsupported_modules
|
||||
* \defgroup SuperLUSupport_Module Super LU support
|
||||
/** \ingroup Sparse_modules
|
||||
* \defgroup SuperLUSupport_Module SuperLUSupport module
|
||||
*
|
||||
* \warning When including this module, you have to use SUPERLU_EMPTY instead of EMPTY which is no longer defined because it is too polluting.
|
||||
*
|
||||
@ -40,10 +40,11 @@ namespace Eigen {
|
||||
* \endcode
|
||||
*/
|
||||
|
||||
#include "src/SparseExtra/SuperLUSupport.h"
|
||||
#include "src/misc/Solve.h"
|
||||
#include "src/misc/SparseSolve.h"
|
||||
|
||||
#include "src/SuperLUSupport/SuperLUSupport.h"
|
||||
|
||||
struct SuperLULegacy {};
|
||||
#include "src/SparseExtra/SuperLUSupportLegacy.h"
|
||||
|
||||
} // namespace Eigen
|
||||
|
@ -1,7 +1,7 @@
|
||||
#ifndef EIGEN_UMFPACKSUPPORT_MODULE_H
|
||||
#define EIGEN_UMFPACKSUPPORT_MODULE_H
|
||||
|
||||
#include "SparseExtra"
|
||||
#include "SparseCore"
|
||||
|
||||
#include "../../Eigen/src/Core/util/DisableStupidWarnings.h"
|
||||
|
||||
@ -11,8 +11,8 @@ extern "C" {
|
||||
|
||||
namespace Eigen {
|
||||
|
||||
/** \ingroup Unsupported_modules
|
||||
* \defgroup UmfPackSupport_Module UmfPack support module
|
||||
/** \ingroup Sparse_modules
|
||||
* \defgroup UmfPackSupport_Module UmfPackSupport module
|
||||
*
|
||||
*
|
||||
*
|
||||
@ -22,10 +22,10 @@ namespace Eigen {
|
||||
* \endcode
|
||||
*/
|
||||
|
||||
struct UmfPack {};
|
||||
#include "src/misc/Solve.h"
|
||||
#include "src/misc/SparseSolve.h"
|
||||
|
||||
#include "src/SparseExtra/UmfPackSupport.h"
|
||||
#include "src/SparseExtra/UmfPackSupportLegacy.h"
|
||||
#include "src/UmfPackSupport/UmfPackSupport.h"
|
||||
|
||||
} // namespace Eigen
|
||||
|
6
Eigen/src/CholmodSupport/CMakeLists.txt
Normal file
6
Eigen/src/CholmodSupport/CMakeLists.txt
Normal file
@ -0,0 +1,6 @@
|
||||
FILE(GLOB Eigen_CholmodSupport_SRCS "*.h")
|
||||
|
||||
INSTALL(FILES
|
||||
${Eigen_CholmodSupport_SRCS}
|
||||
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/CholmodSupport COMPONENT Devel
|
||||
)
|
6
Eigen/src/IterativeLinearSolvers/CMakeLists.txt
Normal file
6
Eigen/src/IterativeLinearSolvers/CMakeLists.txt
Normal file
@ -0,0 +1,6 @@
|
||||
FILE(GLOB Eigen_IterativeLinearSolvers_SRCS "*.h")
|
||||
|
||||
INSTALL(FILES
|
||||
${Eigen_IterativeLinearSolvers_SRCS}
|
||||
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/IterativeLinearSolvers COMPONENT Devel
|
||||
)
|
6
Eigen/src/OrderingMethods/CMakeLists.txt
Normal file
6
Eigen/src/OrderingMethods/CMakeLists.txt
Normal file
@ -0,0 +1,6 @@
|
||||
FILE(GLOB Eigen_OrderingMethods_SRCS "*.h")
|
||||
|
||||
INSTALL(FILES
|
||||
${Eigen_OrderingMethods_SRCS}
|
||||
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/OrderingMethods COMPONENT Devel
|
||||
)
|
@ -1,6 +0,0 @@
|
||||
FILE(GLOB Eigen_Sparse_SRCS "*.h")
|
||||
|
||||
INSTALL(FILES
|
||||
${Eigen_Sparse_SRCS}
|
||||
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/Sparse COMPONENT Devel
|
||||
)
|
6
Eigen/src/SparseCholesky/CMakeLists.txt
Normal file
6
Eigen/src/SparseCholesky/CMakeLists.txt
Normal file
@ -0,0 +1,6 @@
|
||||
FILE(GLOB Eigen_SparseCholesky_SRCS "*.h")
|
||||
|
||||
INSTALL(FILES
|
||||
${Eigen_SparseCholesky_SRCS}
|
||||
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/SparseCholesky COMPONENT Devel
|
||||
)
|
@ -478,7 +478,7 @@ public:
|
||||
};
|
||||
|
||||
/** \class SimplicialCholesky
|
||||
* \deprecated
|
||||
* \deprecated use SimplicialLDLt or class SimplicialLLt
|
||||
* \sa class SimplicialLDLt, class SimplicialLLt
|
||||
*/
|
||||
template<typename _MatrixType, int _UpLo>
|
||||
@ -498,6 +498,7 @@ public:
|
||||
typedef internal::traits<SimplicialLLt<MatrixType,UpLo> > LLtTraits;
|
||||
public:
|
||||
SimplicialCholesky() : Base(), m_LDLt(true) {}
|
||||
|
||||
SimplicialCholesky(const MatrixType& matrix)
|
||||
: Base(), m_LDLt(true)
|
||||
{
|
6
Eigen/src/SparseCore/CMakeLists.txt
Normal file
6
Eigen/src/SparseCore/CMakeLists.txt
Normal file
@ -0,0 +1,6 @@
|
||||
FILE(GLOB Eigen_SparseCore_SRCS "*.h")
|
||||
|
||||
INSTALL(FILES
|
||||
${Eigen_SparseCore_SRCS}
|
||||
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/SparseCore COMPONENT Devel
|
||||
)
|
6
Eigen/src/SuperLUSupport/CMakeLists.txt
Normal file
6
Eigen/src/SuperLUSupport/CMakeLists.txt
Normal file
@ -0,0 +1,6 @@
|
||||
FILE(GLOB Eigen_SuperLUSupport_SRCS "*.h")
|
||||
|
||||
INSTALL(FILES
|
||||
${Eigen_SuperLUSupport_SRCS}
|
||||
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/SuperLUSupport COMPONENT Devel
|
||||
)
|
6
Eigen/src/UmfPackSupport/CMakeLists.txt
Normal file
6
Eigen/src/UmfPackSupport/CMakeLists.txt
Normal file
@ -0,0 +1,6 @@
|
||||
FILE(GLOB Eigen_UmfPackSupport_SRCS "*.h")
|
||||
|
||||
INSTALL(FILES
|
||||
${Eigen_UmfPackSupport_SRCS}
|
||||
DESTINATION ${INCLUDE_INSTALL_DIR}/Eigen/src/UmfPackSupport COMPONENT Devel
|
||||
)
|
@ -12,6 +12,46 @@ foreach(i RANGE 1 999)
|
||||
)
|
||||
endforeach()
|
||||
|
||||
# configure blas/lapack (use Eigen's ones)
|
||||
set(BLAS_FOUND TRUE)
|
||||
set(LAPACK_FOUND TRUE)
|
||||
set(BLAS_LIBRARIES eigen_blas)
|
||||
set(LAPACK_LIBRARIES eigen_lapack)
|
||||
|
||||
set(SPARSE_LIBS " ")
|
||||
|
||||
find_package(Cholmod)
|
||||
if(CHOLMOD_FOUND AND BLAS_FOUND AND LAPACK_FOUND)
|
||||
add_definitions("-DEIGEN_CHOLMOD_SUPPORT")
|
||||
include_directories(${CHOLMOD_INCLUDES})
|
||||
set(SPARSE_LIBS ${SPARSE_LIBS} ${CHOLMOD_LIBRARIES} ${BLAS_LIBRARIES} ${LAPACK_LIBRARIES})
|
||||
ei_add_property(EIGEN_TESTED_BACKENDS "Cholmod, ")
|
||||
else()
|
||||
ei_add_property(EIGEN_MISSING_BACKENDS "Cholmod, ")
|
||||
endif()
|
||||
|
||||
find_package(Umfpack)
|
||||
if(UMFPACK_FOUND AND BLAS_FOUND)
|
||||
add_definitions("-DEIGEN_UMFPACK_SUPPORT")
|
||||
include_directories(${UMFPACK_INCLUDES})
|
||||
set(SPARSE_LIBS ${SPARSE_LIBS} ${UMFPACK_LIBRARIES} ${BLAS_LIBRARIES})
|
||||
set(UMFPACK_ALL_LIBS ${UMFPACK_LIBRARIES} ${BLAS_LIBRARIES})
|
||||
ei_add_property(EIGEN_TESTED_BACKENDS "UmfPack, ")
|
||||
else()
|
||||
ei_add_property(EIGEN_MISSING_BACKENDS "UmfPack, ")
|
||||
endif()
|
||||
|
||||
find_package(SuperLU)
|
||||
if(SUPERLU_FOUND AND BLAS_FOUND)
|
||||
add_definitions("-DEIGEN_SUPERLU_SUPPORT")
|
||||
include_directories(${SUPERLU_INCLUDES})
|
||||
set(SPARSE_LIBS ${SPARSE_LIBS} ${SUPERLU_LIBRARIES} ${BLAS_LIBRARIES})
|
||||
set(SUPERLU_ALL_LIBS ${SUPERLU_LIBRARIES} ${BLAS_LIBRARIES})
|
||||
ei_add_property(EIGEN_TESTED_BACKENDS "SuperLU, ")
|
||||
else()
|
||||
ei_add_property(EIGEN_MISSING_BACKENDS "SuperLU, ")
|
||||
endif()
|
||||
|
||||
find_package(GSL)
|
||||
if(GSL_FOUND AND GSL_VERSION_MINOR LESS 9)
|
||||
set(GSL_FOUND "")
|
||||
@ -123,7 +163,7 @@ endif(QT4_FOUND)
|
||||
ei_add_test(sparse_vector)
|
||||
ei_add_test(sparse_basic)
|
||||
ei_add_test(sparse_product)
|
||||
ei_add_test(sparse_solvers "" "${SPARSE_LIBS}")
|
||||
ei_add_test(sparse_solvers)
|
||||
ei_add_test(umeyama)
|
||||
ei_add_test(householder)
|
||||
ei_add_test(swap)
|
||||
@ -140,6 +180,20 @@ ei_add_test(sizeoverflow)
|
||||
ei_add_test(prec_inverse_4x4)
|
||||
|
||||
|
||||
ei_add_test(simplicial_cholesky)
|
||||
ei_add_test(conjugate_gradient)
|
||||
ei_add_test(bicgstab)
|
||||
|
||||
if(UMFPACK_FOUND)
|
||||
ei_add_test(umfpack_support "" "${UMFPACK_ALL_LIBS}")
|
||||
endif()
|
||||
|
||||
if(SUPERLU_FOUND)
|
||||
ei_add_test(superlu_support "" "${SUPERLU_ALL_LIBS}")
|
||||
endif()
|
||||
|
||||
|
||||
|
||||
string(TOLOWER "${CMAKE_CXX_COMPILER}" cmake_cxx_compiler_tolower)
|
||||
if(cmake_cxx_compiler_tolower MATCHES "qcc")
|
||||
set(CXX_IS_QCC "ON")
|
||||
|
@ -23,17 +23,19 @@
|
||||
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#include "sparse_solver.h"
|
||||
#include <Eigen/IterativeSolvers>
|
||||
#include <Eigen/IterativeLinearSolvers>
|
||||
|
||||
template<typename T> void test_bicgstab_T()
|
||||
{
|
||||
BiCGSTAB<SparseMatrix<T>, DiagonalPreconditioner<T> > bicgstab_colmajor_diag;
|
||||
BiCGSTAB<SparseMatrix<T>, IdentityPreconditioner > bicgstab_colmajor_I;
|
||||
BiCGSTAB<SparseMatrix<T>, IncompleteLU<T> > bicgstab_colmajor_ilu;
|
||||
//BiCGSTAB<SparseMatrix<T>, IncompleteLU<T> > bicgstab_colmajor_ilu;
|
||||
//BiCGSTAB<SparseMatrix<T>, SSORPreconditioner<T> > bicgstab_colmajor_ssor;
|
||||
|
||||
CALL_SUBTEST( check_sparse_square_solving(bicgstab_colmajor_diag) );
|
||||
CALL_SUBTEST( check_sparse_square_solving(bicgstab_colmajor_I) );
|
||||
CALL_SUBTEST( check_sparse_square_solving(bicgstab_colmajor_ilu) );
|
||||
//CALL_SUBTEST( check_sparse_square_solving(bicgstab_colmajor_ilu) );
|
||||
//CALL_SUBTEST( check_sparse_square_solving(bicgstab_colmajor_ssor) );
|
||||
}
|
||||
|
||||
void test_bicgstab()
|
@ -23,7 +23,7 @@
|
||||
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#include "sparse_solver.h"
|
||||
#include <Eigen/IterativeSolvers>
|
||||
#include <Eigen/IterativeLinearSolvers>
|
||||
|
||||
template<typename T> void test_conjugate_gradient_T()
|
||||
{
|
@ -23,7 +23,7 @@
|
||||
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#include "sparse.h"
|
||||
#include <Eigen/SparseExtra>
|
||||
#include <Eigen/SparseCore>
|
||||
|
||||
template<typename Solver, typename Rhs, typename DenseMat, typename DenseRhs>
|
||||
void check_sparse_solving(Solver& solver, const typename Solver::MatrixType& A, const Rhs& b, const DenseMat& dA, const DenseRhs& db)
|
||||
@ -39,7 +39,7 @@ void check_sparse_solving(Solver& solver, const typename Solver::MatrixType& A,
|
||||
solver.compute(A);
|
||||
if (solver.info() != Success)
|
||||
{
|
||||
std::cerr << "sparse SPD: factorization failed (check_sparse_solving)\n";
|
||||
std::cerr << "sparse solver testing: factorization failed (check_sparse_solving)\n";
|
||||
exit(0);
|
||||
return;
|
||||
}
|
||||
@ -64,7 +64,7 @@ void check_sparse_determinant(Solver& solver, const typename Solver::MatrixType&
|
||||
solver.compute(A);
|
||||
if (solver.info() != Success)
|
||||
{
|
||||
std::cerr << "sparse SPD: factorization failed (check_sparse_determinant)\n";
|
||||
std::cerr << "sparse solver testing: factorization failed (check_sparse_determinant)\n";
|
||||
return;
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
set(Eigen_HEADERS AdolcForward BVH IterativeSolvers MatrixFunctions MoreVectorization AutoDiff AlignedVector3 Polynomials
|
||||
CholmodSupport FFT NonLinearOptimization SparseExtra SuperLUSupport UmfPackSupport IterativeSolvers
|
||||
FFT NonLinearOptimization SparseExtra IterativeSolvers
|
||||
NumericalDiff Skyline MPRealSupport OpenGLSupport KroneckerProduct
|
||||
)
|
||||
|
||||
|
@ -42,15 +42,12 @@ namespace Eigen {
|
||||
//@{
|
||||
|
||||
#include "../../Eigen/src/misc/Solve.h"
|
||||
#include "src/SparseExtra/Solve.h"
|
||||
#include "../../Eigen/src/misc/SparseSolve.h"
|
||||
|
||||
#include "src/IterativeSolvers/IterativeSolverBase.h"
|
||||
#include "src/IterativeSolvers/IterationController.h"
|
||||
#include "src/IterativeSolvers/ConstrainedConjGrad.h"
|
||||
#include "src/IterativeSolvers/BasicPreconditioners.h"
|
||||
#include "src/IterativeSolvers/ConjugateGradient.h"
|
||||
#include "src/IterativeSolvers/BiCGSTAB.h"
|
||||
#include "src/IterativeSolvers/IncompleteLU.h"
|
||||
#include "src/IterativeSolvers/SSORPreconditioner.h"
|
||||
|
||||
//@}
|
||||
|
||||
|
@ -54,6 +54,7 @@ enum {
|
||||
};
|
||||
|
||||
#include "../../Eigen/src/misc/Solve.h"
|
||||
#include "../../Eigen/src/misc/SparseSolve.h"
|
||||
|
||||
#include "src/SparseExtra/DynamicSparseMatrix.h"
|
||||
#include "src/SparseExtra/BlockOfDynamicSparseMatrix.h"
|
||||
@ -61,10 +62,6 @@ enum {
|
||||
|
||||
#include "src/SparseExtra/MarketIO.h"
|
||||
|
||||
#include "src/SparseExtra/Solve.h"
|
||||
#include "src/SparseExtra/Amd.h"
|
||||
#include "src/SparseExtra/SimplicialCholesky.h"
|
||||
|
||||
#include "src/SparseExtra/SparseLLT.h"
|
||||
#include "src/SparseExtra/SparseLDLTLegacy.h"
|
||||
#include "src/SparseExtra/SparseLU.h"
|
||||
|
@ -1,520 +0,0 @@
|
||||
// This file is part of Eigen, a lightweight C++ template library
|
||||
// for linear algebra.
|
||||
//
|
||||
// Copyright (C) 2008-2009 Gael Guennebaud <gael.guennebaud@inria.fr>
|
||||
//
|
||||
// Eigen is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU Lesser General Public
|
||||
// License as published by the Free Software Foundation; either
|
||||
// version 3 of the License, or (at your option) any later version.
|
||||
//
|
||||
// Alternatively, you can redistribute it and/or
|
||||
// modify it under the terms of the GNU General Public License as
|
||||
// published by the Free Software Foundation; either version 2 of
|
||||
// the License, or (at your option) any later version.
|
||||
//
|
||||
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Lesser General Public
|
||||
// License and a copy of the GNU General Public License along with
|
||||
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#ifndef EIGEN_CHOLMODSUPPORT_LEGACY_H
|
||||
#define EIGEN_CHOLMODSUPPORT_LEGACY_H
|
||||
|
||||
namespace internal {
|
||||
|
||||
template<typename Scalar, typename CholmodType>
|
||||
void cholmod_configure_matrix_legacy(CholmodType& mat)
|
||||
{
|
||||
if (internal::is_same<Scalar,float>::value)
|
||||
{
|
||||
mat.xtype = CHOLMOD_REAL;
|
||||
mat.dtype = CHOLMOD_SINGLE;
|
||||
}
|
||||
else if (internal::is_same<Scalar,double>::value)
|
||||
{
|
||||
mat.xtype = CHOLMOD_REAL;
|
||||
mat.dtype = CHOLMOD_DOUBLE;
|
||||
}
|
||||
else if (internal::is_same<Scalar,std::complex<float> >::value)
|
||||
{
|
||||
mat.xtype = CHOLMOD_COMPLEX;
|
||||
mat.dtype = CHOLMOD_SINGLE;
|
||||
}
|
||||
else if (internal::is_same<Scalar,std::complex<double> >::value)
|
||||
{
|
||||
mat.xtype = CHOLMOD_COMPLEX;
|
||||
mat.dtype = CHOLMOD_DOUBLE;
|
||||
}
|
||||
else
|
||||
{
|
||||
eigen_assert(false && "Scalar type not supported by CHOLMOD");
|
||||
}
|
||||
}
|
||||
|
||||
template<typename _MatrixType>
|
||||
cholmod_sparse cholmod_map_eigen_to_sparse(_MatrixType& mat)
|
||||
{
|
||||
typedef typename _MatrixType::Scalar Scalar;
|
||||
cholmod_sparse res;
|
||||
res.nzmax = mat.nonZeros();
|
||||
res.nrow = mat.rows();;
|
||||
res.ncol = mat.cols();
|
||||
res.p = mat._outerIndexPtr();
|
||||
res.i = mat._innerIndexPtr();
|
||||
res.x = mat._valuePtr();
|
||||
res.xtype = CHOLMOD_REAL;
|
||||
res.itype = CHOLMOD_INT;
|
||||
res.sorted = 1;
|
||||
res.packed = 1;
|
||||
res.dtype = 0;
|
||||
res.stype = -1;
|
||||
|
||||
internal::cholmod_configure_matrix_legacy<Scalar>(res);
|
||||
|
||||
|
||||
if (_MatrixType::Flags & SelfAdjoint)
|
||||
{
|
||||
if (_MatrixType::Flags & Upper)
|
||||
res.stype = 1;
|
||||
else if (_MatrixType::Flags & Lower)
|
||||
res.stype = -1;
|
||||
else
|
||||
res.stype = 0;
|
||||
}
|
||||
else
|
||||
res.stype = -1; // by default we consider the lower part
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
template<typename Derived>
|
||||
cholmod_dense cholmod_map_eigen_to_dense(MatrixBase<Derived>& mat)
|
||||
{
|
||||
EIGEN_STATIC_ASSERT((internal::traits<Derived>::Flags&RowMajorBit)==0,THIS_METHOD_IS_ONLY_FOR_COLUMN_MAJOR_MATRICES);
|
||||
typedef typename Derived::Scalar Scalar;
|
||||
|
||||
cholmod_dense res;
|
||||
res.nrow = mat.rows();
|
||||
res.ncol = mat.cols();
|
||||
res.nzmax = res.nrow * res.ncol;
|
||||
res.d = Derived::IsVectorAtCompileTime ? mat.derived().size() : mat.derived().outerStride();
|
||||
res.x = mat.derived().data();
|
||||
res.z = 0;
|
||||
|
||||
internal::cholmod_configure_matrix_legacy<Scalar>(res);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
template<typename Scalar, int Flags, typename Index>
|
||||
MappedSparseMatrix<Scalar,Flags,Index> map_cholmod_sparse_to_eigen(cholmod_sparse& cm)
|
||||
{
|
||||
return MappedSparseMatrix<Scalar,Flags,Index>
|
||||
(cm.nrow, cm.ncol, reinterpret_cast<Index*>(cm.p)[cm.ncol],
|
||||
reinterpret_cast<Index*>(cm.p), reinterpret_cast<Index*>(cm.i),reinterpret_cast<Scalar*>(cm.x) );
|
||||
}
|
||||
|
||||
} // namespace internal
|
||||
|
||||
/** \deprecated use class SimplicialLDLT, or class SimplicialLLT, class ConjugateGradient */
|
||||
template<typename _MatrixType>
|
||||
class SparseLLT<_MatrixType, Cholmod> : public SparseLLT<_MatrixType>
|
||||
{
|
||||
protected:
|
||||
typedef SparseLLT<_MatrixType> Base;
|
||||
typedef typename Base::Scalar Scalar;
|
||||
typedef typename Base::RealScalar RealScalar;
|
||||
typedef typename Base::CholMatrixType CholMatrixType;
|
||||
using Base::MatrixLIsDirty;
|
||||
using Base::SupernodalFactorIsDirty;
|
||||
using Base::m_flags;
|
||||
using Base::m_matrix;
|
||||
using Base::m_status;
|
||||
|
||||
public:
|
||||
typedef _MatrixType MatrixType;
|
||||
typedef typename MatrixType::Index Index;
|
||||
|
||||
/** \deprecated the entire class is deprecated */
|
||||
EIGEN_DEPRECATED SparseLLT(int flags = 0)
|
||||
: Base(flags), m_cholmodFactor(0)
|
||||
{
|
||||
cholmod_start(&m_cholmod);
|
||||
}
|
||||
|
||||
/** \deprecated the entire class is deprecated */
|
||||
EIGEN_DEPRECATED SparseLLT(const MatrixType& matrix, int flags = 0)
|
||||
: Base(flags), m_cholmodFactor(0)
|
||||
{
|
||||
cholmod_start(&m_cholmod);
|
||||
compute(matrix);
|
||||
}
|
||||
|
||||
~SparseLLT()
|
||||
{
|
||||
if (m_cholmodFactor)
|
||||
cholmod_free_factor(&m_cholmodFactor, &m_cholmod);
|
||||
cholmod_finish(&m_cholmod);
|
||||
}
|
||||
|
||||
inline const CholMatrixType& matrixL() const;
|
||||
|
||||
template<typename Derived>
|
||||
bool solveInPlace(MatrixBase<Derived> &b) const;
|
||||
|
||||
template<typename Rhs>
|
||||
inline const internal::solve_retval<SparseLLT<MatrixType, Cholmod>, Rhs>
|
||||
solve(const MatrixBase<Rhs>& b) const
|
||||
{
|
||||
eigen_assert(true && "SparseLLT is not initialized.");
|
||||
return internal::solve_retval<SparseLLT<MatrixType, Cholmod>, Rhs>(*this, b.derived());
|
||||
}
|
||||
|
||||
void compute(const MatrixType& matrix);
|
||||
|
||||
inline Index cols() const { return m_matrix.cols(); }
|
||||
inline Index rows() const { return m_matrix.rows(); }
|
||||
|
||||
inline const cholmod_factor* cholmodFactor() const
|
||||
{ return m_cholmodFactor; }
|
||||
|
||||
inline cholmod_common* cholmodCommon() const
|
||||
{ return &m_cholmod; }
|
||||
|
||||
bool succeeded() const;
|
||||
|
||||
protected:
|
||||
mutable cholmod_common m_cholmod;
|
||||
cholmod_factor* m_cholmodFactor;
|
||||
};
|
||||
|
||||
|
||||
namespace internal {
|
||||
|
||||
template<typename _MatrixType, typename Rhs>
|
||||
struct solve_retval<SparseLLT<_MatrixType, Cholmod>, Rhs>
|
||||
: solve_retval_base<SparseLLT<_MatrixType, Cholmod>, Rhs>
|
||||
{
|
||||
typedef SparseLLT<_MatrixType, Cholmod> SpLLTDecType;
|
||||
EIGEN_MAKE_SOLVE_HELPERS(SpLLTDecType,Rhs)
|
||||
|
||||
template<typename Dest> void evalTo(Dest& dst) const
|
||||
{
|
||||
//Index size = dec().cholmodFactor()->n;
|
||||
eigen_assert((Index)dec().cholmodFactor()->n==rhs().rows());
|
||||
|
||||
cholmod_factor* cholmodFactor = const_cast<cholmod_factor*>(dec().cholmodFactor());
|
||||
cholmod_common* cholmodCommon = const_cast<cholmod_common*>(dec().cholmodCommon());
|
||||
// this uses Eigen's triangular sparse solver
|
||||
// if (m_status & MatrixLIsDirty)
|
||||
// matrixL();
|
||||
// Base::solveInPlace(b);
|
||||
// as long as our own triangular sparse solver is not fully optimal,
|
||||
// let's use CHOLMOD's one:
|
||||
cholmod_dense cdb = internal::cholmod_map_eigen_to_dense(rhs().const_cast_derived());
|
||||
cholmod_dense* x = cholmod_solve(CHOLMOD_A, cholmodFactor, &cdb, cholmodCommon);
|
||||
|
||||
dst = Matrix<typename Base::Scalar,Dynamic,1>::Map(reinterpret_cast<typename Base::Scalar*>(x->x), rhs().rows());
|
||||
|
||||
cholmod_free_dense(&x, cholmodCommon);
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
} // namespace internal
|
||||
|
||||
|
||||
|
||||
template<typename _MatrixType>
|
||||
void SparseLLT<_MatrixType,Cholmod>::compute(const _MatrixType& a)
|
||||
{
|
||||
if (m_cholmodFactor)
|
||||
{
|
||||
cholmod_free_factor(&m_cholmodFactor, &m_cholmod);
|
||||
m_cholmodFactor = 0;
|
||||
}
|
||||
|
||||
cholmod_sparse A = internal::cholmod_map_eigen_to_sparse(const_cast<_MatrixType&>(a));
|
||||
// m_cholmod.supernodal = CHOLMOD_AUTO;
|
||||
// TODO
|
||||
// if (m_flags&IncompleteFactorization)
|
||||
// {
|
||||
// m_cholmod.nmethods = 1;
|
||||
// m_cholmod.method[0].ordering = CHOLMOD_NATURAL;
|
||||
// m_cholmod.postorder = 0;
|
||||
// }
|
||||
// else
|
||||
// {
|
||||
// m_cholmod.nmethods = 1;
|
||||
// m_cholmod.method[0].ordering = CHOLMOD_NATURAL;
|
||||
// m_cholmod.postorder = 0;
|
||||
// }
|
||||
// m_cholmod.final_ll = 1;
|
||||
m_cholmodFactor = cholmod_analyze(&A, &m_cholmod);
|
||||
cholmod_factorize(&A, m_cholmodFactor, &m_cholmod);
|
||||
|
||||
this->m_status = (this->m_status & ~Base::SupernodalFactorIsDirty) | Base::MatrixLIsDirty;
|
||||
}
|
||||
|
||||
|
||||
// TODO
|
||||
template<typename _MatrixType>
|
||||
bool SparseLLT<_MatrixType,Cholmod>::succeeded() const
|
||||
{ return true; }
|
||||
|
||||
|
||||
|
||||
template<typename _MatrixType>
|
||||
inline const typename SparseLLT<_MatrixType,Cholmod>::CholMatrixType&
|
||||
SparseLLT<_MatrixType,Cholmod>::matrixL() const
|
||||
{
|
||||
if (this->m_status & Base::MatrixLIsDirty)
|
||||
{
|
||||
eigen_assert(!(this->m_status & Base::SupernodalFactorIsDirty));
|
||||
|
||||
cholmod_sparse* cmRes = cholmod_factor_to_sparse(m_cholmodFactor, &m_cholmod);
|
||||
const_cast<typename Base::CholMatrixType&>(this->m_matrix) =
|
||||
internal::map_cholmod_sparse_to_eigen<Scalar,ColMajor,Index>(*cmRes);
|
||||
free(cmRes);
|
||||
|
||||
this->m_status = (this->m_status & ~Base::MatrixLIsDirty);
|
||||
}
|
||||
return this->m_matrix;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
template<typename _MatrixType>
|
||||
template<typename Derived>
|
||||
bool SparseLLT<_MatrixType,Cholmod>::solveInPlace(MatrixBase<Derived> &b) const
|
||||
{
|
||||
//Index size = m_cholmodFactor->n;
|
||||
eigen_assert((Index)m_cholmodFactor->n==b.rows());
|
||||
|
||||
// this uses Eigen's triangular sparse solver
|
||||
// if (m_status & MatrixLIsDirty)
|
||||
// matrixL();
|
||||
// Base::solveInPlace(b);
|
||||
// as long as our own triangular sparse solver is not fully optimal,
|
||||
// let's use CHOLMOD's one:
|
||||
cholmod_dense cdb = internal::cholmod_map_eigen_to_dense(b);
|
||||
|
||||
cholmod_dense* x = cholmod_solve(CHOLMOD_A, m_cholmodFactor, &cdb, &m_cholmod);
|
||||
eigen_assert(x && "Eigen: cholmod_solve failed.");
|
||||
|
||||
b = Matrix<typename Base::Scalar,Dynamic,1>::Map(reinterpret_cast<typename Base::Scalar*>(x->x),b.rows());
|
||||
cholmod_free_dense(&x, &m_cholmod);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
template<typename _MatrixType>
|
||||
class SparseLDLT<_MatrixType,Cholmod> : public SparseLDLT<_MatrixType>
|
||||
{
|
||||
protected:
|
||||
typedef SparseLDLT<_MatrixType> Base;
|
||||
typedef typename Base::Scalar Scalar;
|
||||
typedef typename Base::RealScalar RealScalar;
|
||||
using Base::MatrixLIsDirty;
|
||||
using Base::SupernodalFactorIsDirty;
|
||||
using Base::m_flags;
|
||||
using Base::m_matrix;
|
||||
using Base::m_status;
|
||||
|
||||
public:
|
||||
typedef _MatrixType MatrixType;
|
||||
typedef typename MatrixType::Index Index;
|
||||
|
||||
SparseLDLT(int flags = 0)
|
||||
: Base(flags), m_cholmodFactor(0)
|
||||
{
|
||||
cholmod_start(&m_cholmod);
|
||||
}
|
||||
|
||||
SparseLDLT(const _MatrixType& matrix, int flags = 0)
|
||||
: Base(flags), m_cholmodFactor(0)
|
||||
{
|
||||
cholmod_start(&m_cholmod);
|
||||
compute(matrix);
|
||||
}
|
||||
|
||||
~SparseLDLT()
|
||||
{
|
||||
if (m_cholmodFactor)
|
||||
cholmod_free_factor(&m_cholmodFactor, &m_cholmod);
|
||||
cholmod_finish(&m_cholmod);
|
||||
}
|
||||
|
||||
inline const typename Base::CholMatrixType& matrixL(void) const;
|
||||
|
||||
template<typename Derived>
|
||||
void solveInPlace(MatrixBase<Derived> &b) const;
|
||||
|
||||
template<typename Rhs>
|
||||
inline const internal::solve_retval<SparseLDLT<MatrixType, Cholmod>, Rhs>
|
||||
solve(const MatrixBase<Rhs>& b) const
|
||||
{
|
||||
eigen_assert(true && "SparseLDLT is not initialized.");
|
||||
return internal::solve_retval<SparseLDLT<MatrixType, Cholmod>, Rhs>(*this, b.derived());
|
||||
}
|
||||
|
||||
void compute(const _MatrixType& matrix);
|
||||
|
||||
inline Index cols() const { return m_matrix.cols(); }
|
||||
inline Index rows() const { return m_matrix.rows(); }
|
||||
|
||||
inline const cholmod_factor* cholmodFactor() const
|
||||
{ return m_cholmodFactor; }
|
||||
|
||||
inline cholmod_common* cholmodCommon() const
|
||||
{ return &m_cholmod; }
|
||||
|
||||
bool succeeded() const;
|
||||
|
||||
protected:
|
||||
mutable cholmod_common m_cholmod;
|
||||
cholmod_factor* m_cholmodFactor;
|
||||
};
|
||||
|
||||
|
||||
|
||||
namespace internal {
|
||||
|
||||
template<typename _MatrixType, typename Rhs>
|
||||
struct solve_retval<SparseLDLT<_MatrixType, Cholmod>, Rhs>
|
||||
: solve_retval_base<SparseLDLT<_MatrixType, Cholmod>, Rhs>
|
||||
{
|
||||
typedef SparseLDLT<_MatrixType, Cholmod> SpLDLTDecType;
|
||||
EIGEN_MAKE_SOLVE_HELPERS(SpLDLTDecType,Rhs)
|
||||
|
||||
template<typename Dest> void evalTo(Dest& dst) const
|
||||
{
|
||||
//Index size = dec().cholmodFactor()->n;
|
||||
eigen_assert((Index)dec().cholmodFactor()->n==rhs().rows());
|
||||
|
||||
cholmod_factor* cholmodFactor = const_cast<cholmod_factor*>(dec().cholmodFactor());
|
||||
cholmod_common* cholmodCommon = const_cast<cholmod_common*>(dec().cholmodCommon());
|
||||
// this uses Eigen's triangular sparse solver
|
||||
// if (m_status & MatrixLIsDirty)
|
||||
// matrixL();
|
||||
// Base::solveInPlace(b);
|
||||
// as long as our own triangular sparse solver is not fully optimal,
|
||||
// let's use CHOLMOD's one:
|
||||
cholmod_dense cdb = internal::cholmod_map_eigen_to_dense(rhs().const_cast_derived());
|
||||
cholmod_dense* x = cholmod_solve(CHOLMOD_LDLt, cholmodFactor, &cdb, cholmodCommon);
|
||||
|
||||
dst = Matrix<typename Base::Scalar,Dynamic,1>::Map(reinterpret_cast<typename Base::Scalar*>(x->x), rhs().rows());
|
||||
cholmod_free_dense(&x, cholmodCommon);
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
|
||||
} // namespace internal
|
||||
|
||||
template<typename _MatrixType>
|
||||
void SparseLDLT<_MatrixType,Cholmod>::compute(const _MatrixType& a)
|
||||
{
|
||||
if (m_cholmodFactor)
|
||||
{
|
||||
cholmod_free_factor(&m_cholmodFactor, &m_cholmod);
|
||||
m_cholmodFactor = 0;
|
||||
}
|
||||
|
||||
cholmod_sparse A = internal::cholmod_map_eigen_to_sparse(const_cast<_MatrixType&>(a));
|
||||
|
||||
//m_cholmod.supernodal = CHOLMOD_AUTO;
|
||||
m_cholmod.supernodal = CHOLMOD_SIMPLICIAL;
|
||||
//m_cholmod.supernodal = CHOLMOD_SUPERNODAL;
|
||||
// TODO
|
||||
if (this->m_flags & IncompleteFactorization)
|
||||
{
|
||||
m_cholmod.nmethods = 1;
|
||||
//m_cholmod.method[0].ordering = CHOLMOD_NATURAL;
|
||||
m_cholmod.method[0].ordering = CHOLMOD_COLAMD;
|
||||
m_cholmod.postorder = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_cholmod.nmethods = 1;
|
||||
m_cholmod.method[0].ordering = CHOLMOD_NATURAL;
|
||||
m_cholmod.postorder = 0;
|
||||
}
|
||||
m_cholmod.final_ll = 0;
|
||||
m_cholmodFactor = cholmod_analyze(&A, &m_cholmod);
|
||||
cholmod_factorize(&A, m_cholmodFactor, &m_cholmod);
|
||||
|
||||
this->m_status = (this->m_status & ~Base::SupernodalFactorIsDirty) | Base::MatrixLIsDirty;
|
||||
}
|
||||
|
||||
|
||||
// TODO
|
||||
template<typename _MatrixType>
|
||||
bool SparseLDLT<_MatrixType,Cholmod>::succeeded() const
|
||||
{ return true; }
|
||||
|
||||
|
||||
template<typename _MatrixType>
|
||||
inline const typename SparseLDLT<_MatrixType>::CholMatrixType&
|
||||
SparseLDLT<_MatrixType,Cholmod>::matrixL() const
|
||||
{
|
||||
if (this->m_status & Base::MatrixLIsDirty)
|
||||
{
|
||||
eigen_assert(!(this->m_status & Base::SupernodalFactorIsDirty));
|
||||
|
||||
cholmod_sparse* cmRes = cholmod_factor_to_sparse(m_cholmodFactor, &m_cholmod);
|
||||
const_cast<typename Base::CholMatrixType&>(this->m_matrix) = MappedSparseMatrix<Scalar>(*cmRes);
|
||||
free(cmRes);
|
||||
|
||||
this->m_status = (this->m_status & ~Base::MatrixLIsDirty);
|
||||
}
|
||||
return this->m_matrix;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
template<typename _MatrixType>
|
||||
template<typename Derived>
|
||||
void SparseLDLT<_MatrixType,Cholmod>::solveInPlace(MatrixBase<Derived> &b) const
|
||||
{
|
||||
//Index size = m_cholmodFactor->n;
|
||||
eigen_assert((Index)m_cholmodFactor->n == b.rows());
|
||||
|
||||
// this uses Eigen's triangular sparse solver
|
||||
// if (m_status & MatrixLIsDirty)
|
||||
// matrixL();
|
||||
// Base::solveInPlace(b);
|
||||
// as long as our own triangular sparse solver is not fully optimal,
|
||||
// let's use CHOLMOD's one:
|
||||
cholmod_dense cdb = internal::cholmod_map_eigen_to_dense(b);
|
||||
cholmod_dense* x = cholmod_solve(CHOLMOD_A, m_cholmodFactor, &cdb, &m_cholmod);
|
||||
b = Matrix<typename Base::Scalar,Dynamic,1>::Map(reinterpret_cast<typename Base::Scalar*>(x->x),b.rows());
|
||||
cholmod_free_dense(&x, &m_cholmod);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#endif // EIGEN_CHOLMODSUPPORT_LEGACY_H
|
@ -1,407 +0,0 @@
|
||||
// This file is part of Eigen, a lightweight C++ template library
|
||||
// for linear algebra.
|
||||
//
|
||||
// Copyright (C) 2008-2009 Gael Guennebaud <gael.guennebaud@inria.fr>
|
||||
//
|
||||
// Eigen is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU Lesser General Public
|
||||
// License as published by the Free Software Foundation; either
|
||||
// version 3 of the License, or (at your option) any later version.
|
||||
//
|
||||
// Alternatively, you can redistribute it and/or
|
||||
// modify it under the terms of the GNU General Public License as
|
||||
// published by the Free Software Foundation; either version 2 of
|
||||
// the License, or (at your option) any later version.
|
||||
//
|
||||
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Lesser General Public
|
||||
// License and a copy of the GNU General Public License along with
|
||||
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#ifndef EIGEN_SUPERLUSUPPORT_LEGACY_H
|
||||
#define EIGEN_SUPERLUSUPPORT_LEGACY_H
|
||||
|
||||
/** \deprecated use class BiCGSTAB, class SuperLU, or class UmfPackLU */
|
||||
template<typename MatrixType>
|
||||
class SparseLU<MatrixType,SuperLULegacy> : public SparseLU<MatrixType>
|
||||
{
|
||||
protected:
|
||||
typedef SparseLU<MatrixType> Base;
|
||||
typedef typename Base::Scalar Scalar;
|
||||
typedef typename Base::RealScalar RealScalar;
|
||||
typedef Matrix<Scalar,Dynamic,1> Vector;
|
||||
typedef Matrix<int, 1, MatrixType::ColsAtCompileTime> IntRowVectorType;
|
||||
typedef Matrix<int, MatrixType::RowsAtCompileTime, 1> IntColVectorType;
|
||||
typedef SparseMatrix<Scalar,Lower|UnitDiag> LMatrixType;
|
||||
typedef SparseMatrix<Scalar,Upper> UMatrixType;
|
||||
using Base::m_flags;
|
||||
using Base::m_status;
|
||||
|
||||
public:
|
||||
|
||||
/** \deprecated the entire class is deprecated */
|
||||
EIGEN_DEPRECATED SparseLU(int flags = NaturalOrdering)
|
||||
: Base(flags)
|
||||
{
|
||||
}
|
||||
|
||||
/** \deprecated the entire class is deprecated */
|
||||
EIGEN_DEPRECATED SparseLU(const MatrixType& matrix, int flags = NaturalOrdering)
|
||||
: Base(flags)
|
||||
{
|
||||
compute(matrix);
|
||||
}
|
||||
|
||||
~SparseLU()
|
||||
{
|
||||
Destroy_SuperNode_Matrix(&m_sluL);
|
||||
Destroy_CompCol_Matrix(&m_sluU);
|
||||
}
|
||||
|
||||
inline const LMatrixType& matrixL() const
|
||||
{
|
||||
if (m_extractedDataAreDirty) extractData();
|
||||
return m_l;
|
||||
}
|
||||
|
||||
inline const UMatrixType& matrixU() const
|
||||
{
|
||||
if (m_extractedDataAreDirty) extractData();
|
||||
return m_u;
|
||||
}
|
||||
|
||||
inline const IntColVectorType& permutationP() const
|
||||
{
|
||||
if (m_extractedDataAreDirty) extractData();
|
||||
return m_p;
|
||||
}
|
||||
|
||||
inline const IntRowVectorType& permutationQ() const
|
||||
{
|
||||
if (m_extractedDataAreDirty) extractData();
|
||||
return m_q;
|
||||
}
|
||||
|
||||
Scalar determinant() const;
|
||||
|
||||
template<typename BDerived, typename XDerived>
|
||||
bool solve(const MatrixBase<BDerived> &b, MatrixBase<XDerived>* x, const int transposed = SvNoTrans) const;
|
||||
|
||||
void compute(const MatrixType& matrix);
|
||||
|
||||
protected:
|
||||
|
||||
void extractData() const;
|
||||
|
||||
protected:
|
||||
// cached data to reduce reallocation, etc.
|
||||
mutable LMatrixType m_l;
|
||||
mutable UMatrixType m_u;
|
||||
mutable IntColVectorType m_p;
|
||||
mutable IntRowVectorType m_q;
|
||||
|
||||
mutable SparseMatrix<Scalar> m_matrix;
|
||||
mutable SluMatrix m_sluA;
|
||||
mutable SuperMatrix m_sluL, m_sluU;
|
||||
mutable SluMatrix m_sluB, m_sluX;
|
||||
mutable SuperLUStat_t m_sluStat;
|
||||
mutable superlu_options_t m_sluOptions;
|
||||
mutable std::vector<int> m_sluEtree;
|
||||
mutable std::vector<RealScalar> m_sluRscale, m_sluCscale;
|
||||
mutable std::vector<RealScalar> m_sluFerr, m_sluBerr;
|
||||
mutable char m_sluEqued;
|
||||
mutable bool m_extractedDataAreDirty;
|
||||
};
|
||||
|
||||
template<typename MatrixType>
|
||||
void SparseLU<MatrixType,SuperLULegacy>::compute(const MatrixType& a)
|
||||
{
|
||||
const int size = a.rows();
|
||||
m_matrix = a;
|
||||
|
||||
set_default_options(&m_sluOptions);
|
||||
m_sluOptions.ColPerm = NATURAL;
|
||||
m_sluOptions.PrintStat = NO;
|
||||
m_sluOptions.ConditionNumber = NO;
|
||||
m_sluOptions.Trans = NOTRANS;
|
||||
// m_sluOptions.Equil = NO;
|
||||
|
||||
switch (Base::orderingMethod())
|
||||
{
|
||||
case NaturalOrdering : m_sluOptions.ColPerm = NATURAL; break;
|
||||
case MinimumDegree_AT_PLUS_A : m_sluOptions.ColPerm = MMD_AT_PLUS_A; break;
|
||||
case MinimumDegree_ATA : m_sluOptions.ColPerm = MMD_ATA; break;
|
||||
case ColApproxMinimumDegree : m_sluOptions.ColPerm = COLAMD; break;
|
||||
default:
|
||||
//std::cerr << "Eigen: ordering method \"" << Base::orderingMethod() << "\" not supported by the SuperLU backend\n";
|
||||
m_sluOptions.ColPerm = NATURAL;
|
||||
};
|
||||
|
||||
m_sluA = internal::asSluMatrix(m_matrix);
|
||||
memset(&m_sluL,0,sizeof m_sluL);
|
||||
memset(&m_sluU,0,sizeof m_sluU);
|
||||
m_sluEqued = 'N';
|
||||
int info = 0;
|
||||
|
||||
m_p.resize(size);
|
||||
m_q.resize(size);
|
||||
m_sluRscale.resize(size);
|
||||
m_sluCscale.resize(size);
|
||||
m_sluEtree.resize(size);
|
||||
|
||||
RealScalar recip_pivot_gross, rcond;
|
||||
RealScalar ferr, berr;
|
||||
|
||||
// set empty B and X
|
||||
m_sluB.setStorageType(SLU_DN);
|
||||
m_sluB.setScalarType<Scalar>();
|
||||
m_sluB.Mtype = SLU_GE;
|
||||
m_sluB.storage.values = 0;
|
||||
m_sluB.nrow = m_sluB.ncol = 0;
|
||||
m_sluB.storage.lda = size;
|
||||
m_sluX = m_sluB;
|
||||
|
||||
StatInit(&m_sluStat);
|
||||
if (m_flags&IncompleteFactorization)
|
||||
{
|
||||
#ifdef EIGEN_SUPERLU_HAS_ILU
|
||||
ilu_set_default_options(&m_sluOptions);
|
||||
|
||||
// no attempt to preserve column sum
|
||||
m_sluOptions.ILU_MILU = SILU;
|
||||
|
||||
// only basic ILU(k) support -- no direct control over memory consumption
|
||||
// better to use ILU_DropRule = DROP_BASIC | DROP_AREA
|
||||
// and set ILU_FillFactor to max memory growth
|
||||
m_sluOptions.ILU_DropRule = DROP_BASIC;
|
||||
m_sluOptions.ILU_DropTol = Base::m_precision;
|
||||
|
||||
SuperLU_gsisx(&m_sluOptions, &m_sluA, m_q.data(), m_p.data(), &m_sluEtree[0],
|
||||
&m_sluEqued, &m_sluRscale[0], &m_sluCscale[0],
|
||||
&m_sluL, &m_sluU,
|
||||
NULL, 0,
|
||||
&m_sluB, &m_sluX,
|
||||
&recip_pivot_gross, &rcond,
|
||||
&m_sluStat, &info, Scalar());
|
||||
#else
|
||||
//std::cerr << "Incomplete factorization is only available in SuperLU v4\n";
|
||||
Base::m_succeeded = false;
|
||||
return;
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
SuperLU_gssvx(&m_sluOptions, &m_sluA, m_q.data(), m_p.data(), &m_sluEtree[0],
|
||||
&m_sluEqued, &m_sluRscale[0], &m_sluCscale[0],
|
||||
&m_sluL, &m_sluU,
|
||||
NULL, 0,
|
||||
&m_sluB, &m_sluX,
|
||||
&recip_pivot_gross, &rcond,
|
||||
&ferr, &berr,
|
||||
&m_sluStat, &info, Scalar());
|
||||
}
|
||||
StatFree(&m_sluStat);
|
||||
|
||||
m_extractedDataAreDirty = true;
|
||||
|
||||
// FIXME how to better check for errors ???
|
||||
Base::m_succeeded = (info == 0);
|
||||
}
|
||||
|
||||
template<typename MatrixType>
|
||||
template<typename BDerived,typename XDerived>
|
||||
bool SparseLU<MatrixType,SuperLULegacy>::solve(const MatrixBase<BDerived> &b,
|
||||
MatrixBase<XDerived> *x, const int transposed) const
|
||||
{
|
||||
const int size = m_matrix.rows();
|
||||
const int rhsCols = b.cols();
|
||||
eigen_assert(size==b.rows());
|
||||
|
||||
switch (transposed) {
|
||||
case SvNoTrans : m_sluOptions.Trans = NOTRANS; break;
|
||||
case SvTranspose : m_sluOptions.Trans = TRANS; break;
|
||||
case SvAdjoint : m_sluOptions.Trans = CONJ; break;
|
||||
default:
|
||||
//std::cerr << "Eigen: transposition option \"" << transposed << "\" not supported by the SuperLU backend\n";
|
||||
m_sluOptions.Trans = NOTRANS;
|
||||
}
|
||||
|
||||
m_sluOptions.Fact = FACTORED;
|
||||
m_sluOptions.IterRefine = NOREFINE;
|
||||
|
||||
m_sluFerr.resize(rhsCols);
|
||||
m_sluBerr.resize(rhsCols);
|
||||
m_sluB = SluMatrix::Map(b.const_cast_derived());
|
||||
m_sluX = SluMatrix::Map(x->derived());
|
||||
|
||||
typename BDerived::PlainObject b_cpy;
|
||||
if(m_sluEqued!='N')
|
||||
{
|
||||
b_cpy = b;
|
||||
m_sluB = SluMatrix::Map(b_cpy.const_cast_derived());
|
||||
}
|
||||
|
||||
StatInit(&m_sluStat);
|
||||
int info = 0;
|
||||
RealScalar recip_pivot_gross, rcond;
|
||||
|
||||
if (m_flags&IncompleteFactorization)
|
||||
{
|
||||
#ifdef EIGEN_SUPERLU_HAS_ILU
|
||||
SuperLU_gsisx(&m_sluOptions, &m_sluA, m_q.data(), m_p.data(), &m_sluEtree[0],
|
||||
&m_sluEqued, &m_sluRscale[0], &m_sluCscale[0],
|
||||
&m_sluL, &m_sluU,
|
||||
NULL, 0,
|
||||
&m_sluB, &m_sluX,
|
||||
&recip_pivot_gross, &rcond,
|
||||
&m_sluStat, &info, Scalar());
|
||||
#else
|
||||
//std::cerr << "Incomplete factorization is only available in SuperLU v4\n";
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
SuperLU_gssvx(
|
||||
&m_sluOptions, &m_sluA,
|
||||
m_q.data(), m_p.data(),
|
||||
&m_sluEtree[0], &m_sluEqued,
|
||||
&m_sluRscale[0], &m_sluCscale[0],
|
||||
&m_sluL, &m_sluU,
|
||||
NULL, 0,
|
||||
&m_sluB, &m_sluX,
|
||||
&recip_pivot_gross, &rcond,
|
||||
&m_sluFerr[0], &m_sluBerr[0],
|
||||
&m_sluStat, &info, Scalar());
|
||||
}
|
||||
StatFree(&m_sluStat);
|
||||
|
||||
// reset to previous state
|
||||
m_sluOptions.Trans = NOTRANS;
|
||||
return info==0;
|
||||
}
|
||||
|
||||
//
|
||||
// the code of this extractData() function has been adapted from the SuperLU's Matlab support code,
|
||||
//
|
||||
// Copyright (c) 1994 by Xerox Corporation. All rights reserved.
|
||||
//
|
||||
// THIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY
|
||||
// EXPRESSED OR IMPLIED. ANY USE IS AT YOUR OWN RISK.
|
||||
//
|
||||
template<typename MatrixType>
|
||||
void SparseLU<MatrixType,SuperLULegacy>::extractData() const
|
||||
{
|
||||
if (m_extractedDataAreDirty)
|
||||
{
|
||||
int upper;
|
||||
int fsupc, istart, nsupr;
|
||||
int lastl = 0, lastu = 0;
|
||||
SCformat *Lstore = static_cast<SCformat*>(m_sluL.Store);
|
||||
NCformat *Ustore = static_cast<NCformat*>(m_sluU.Store);
|
||||
Scalar *SNptr;
|
||||
|
||||
const int size = m_matrix.rows();
|
||||
m_l.resize(size,size);
|
||||
m_l.resizeNonZeros(Lstore->nnz);
|
||||
m_u.resize(size,size);
|
||||
m_u.resizeNonZeros(Ustore->nnz);
|
||||
|
||||
int* Lcol = m_l._outerIndexPtr();
|
||||
int* Lrow = m_l._innerIndexPtr();
|
||||
Scalar* Lval = m_l._valuePtr();
|
||||
|
||||
int* Ucol = m_u._outerIndexPtr();
|
||||
int* Urow = m_u._innerIndexPtr();
|
||||
Scalar* Uval = m_u._valuePtr();
|
||||
|
||||
Ucol[0] = 0;
|
||||
Ucol[0] = 0;
|
||||
|
||||
/* for each supernode */
|
||||
for (int k = 0; k <= Lstore->nsuper; ++k)
|
||||
{
|
||||
fsupc = L_FST_SUPC(k);
|
||||
istart = L_SUB_START(fsupc);
|
||||
nsupr = L_SUB_START(fsupc+1) - istart;
|
||||
upper = 1;
|
||||
|
||||
/* for each column in the supernode */
|
||||
for (int j = fsupc; j < L_FST_SUPC(k+1); ++j)
|
||||
{
|
||||
SNptr = &((Scalar*)Lstore->nzval)[L_NZ_START(j)];
|
||||
|
||||
/* Extract U */
|
||||
for (int i = U_NZ_START(j); i < U_NZ_START(j+1); ++i)
|
||||
{
|
||||
Uval[lastu] = ((Scalar*)Ustore->nzval)[i];
|
||||
/* Matlab doesn't like explicit zero. */
|
||||
if (Uval[lastu] != 0.0)
|
||||
Urow[lastu++] = U_SUB(i);
|
||||
}
|
||||
for (int i = 0; i < upper; ++i)
|
||||
{
|
||||
/* upper triangle in the supernode */
|
||||
Uval[lastu] = SNptr[i];
|
||||
/* Matlab doesn't like explicit zero. */
|
||||
if (Uval[lastu] != 0.0)
|
||||
Urow[lastu++] = L_SUB(istart+i);
|
||||
}
|
||||
Ucol[j+1] = lastu;
|
||||
|
||||
/* Extract L */
|
||||
Lval[lastl] = 1.0; /* unit diagonal */
|
||||
Lrow[lastl++] = L_SUB(istart + upper - 1);
|
||||
for (int i = upper; i < nsupr; ++i)
|
||||
{
|
||||
Lval[lastl] = SNptr[i];
|
||||
/* Matlab doesn't like explicit zero. */
|
||||
if (Lval[lastl] != 0.0)
|
||||
Lrow[lastl++] = L_SUB(istart+i);
|
||||
}
|
||||
Lcol[j+1] = lastl;
|
||||
|
||||
++upper;
|
||||
} /* for j ... */
|
||||
|
||||
} /* for k ... */
|
||||
|
||||
// squeeze the matrices :
|
||||
m_l.resizeNonZeros(lastl);
|
||||
m_u.resizeNonZeros(lastu);
|
||||
|
||||
m_extractedDataAreDirty = false;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename MatrixType>
|
||||
typename SparseLU<MatrixType,SuperLULegacy>::Scalar SparseLU<MatrixType,SuperLULegacy>::determinant() const
|
||||
{
|
||||
assert((!NumTraits<Scalar>::IsComplex) && "This function is not implemented for complex yet");
|
||||
if (m_extractedDataAreDirty)
|
||||
extractData();
|
||||
|
||||
// TODO this code could be moved to the default/base backend
|
||||
// FIXME perhaps we have to take into account the scale factors m_sluRscale and m_sluCscale ???
|
||||
Scalar det = Scalar(1);
|
||||
for (int j=0; j<m_u.cols(); ++j)
|
||||
{
|
||||
if (m_u._outerIndexPtr()[j+1]-m_u._outerIndexPtr()[j] > 0)
|
||||
{
|
||||
int lastId = m_u._outerIndexPtr()[j+1]-1;
|
||||
eigen_assert(m_u._innerIndexPtr()[lastId]<=j);
|
||||
if (m_u._innerIndexPtr()[lastId]==j)
|
||||
{
|
||||
det *= m_u._valuePtr()[lastId];
|
||||
}
|
||||
}
|
||||
// std::cout << m_sluRscale[j] << " " << m_sluCscale[j] << " \n";
|
||||
}
|
||||
return det;
|
||||
}
|
||||
|
||||
#endif // EIGEN_SUPERLUSUPPORT_LEGACY_H
|
@ -1,257 +0,0 @@
|
||||
// This file is part of Eigen, a lightweight C++ template library
|
||||
// for linear algebra.
|
||||
//
|
||||
// Copyright (C) 2008-2009 Gael Guennebaud <gael.guennebaud@inria.fr>
|
||||
//
|
||||
// Eigen is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU Lesser General Public
|
||||
// License as published by the Free Software Foundation; either
|
||||
// version 3 of the License, or (at your option) any later version.
|
||||
//
|
||||
// Alternatively, you can redistribute it and/or
|
||||
// modify it under the terms of the GNU General Public License as
|
||||
// published by the Free Software Foundation; either version 2 of
|
||||
// the License, or (at your option) any later version.
|
||||
//
|
||||
// Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||
// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
|
||||
// FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Lesser General Public
|
||||
// License and a copy of the GNU General Public License along with
|
||||
// Eigen. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#ifndef EIGEN_UMFPACKSUPPORT_LEGACY_H
|
||||
#define EIGEN_UMFPACKSUPPORT_LEGACY_H
|
||||
|
||||
/** \deprecated use class BiCGSTAB, class SuperLU, or class UmfPackLU */
|
||||
template<typename _MatrixType>
|
||||
class SparseLU<_MatrixType,UmfPack> : public SparseLU<_MatrixType>
|
||||
{
|
||||
protected:
|
||||
typedef SparseLU<_MatrixType> Base;
|
||||
typedef typename Base::Scalar Scalar;
|
||||
typedef typename Base::RealScalar RealScalar;
|
||||
typedef Matrix<Scalar,Dynamic,1> Vector;
|
||||
typedef Matrix<int, 1, _MatrixType::ColsAtCompileTime> IntRowVectorType;
|
||||
typedef Matrix<int, _MatrixType::RowsAtCompileTime, 1> IntColVectorType;
|
||||
typedef SparseMatrix<Scalar,Lower|UnitDiag> LMatrixType;
|
||||
typedef SparseMatrix<Scalar,Upper> UMatrixType;
|
||||
using Base::m_flags;
|
||||
using Base::m_status;
|
||||
|
||||
public:
|
||||
typedef _MatrixType MatrixType;
|
||||
typedef typename MatrixType::Index Index;
|
||||
|
||||
/** \deprecated the entire class is deprecated */
|
||||
EIGEN_DEPRECATED SparseLU(int flags = NaturalOrdering)
|
||||
: Base(flags), m_numeric(0)
|
||||
{
|
||||
}
|
||||
|
||||
/** \deprecated the entire class is deprecated */
|
||||
EIGEN_DEPRECATED SparseLU(const MatrixType& matrix, int flags = NaturalOrdering)
|
||||
: Base(flags), m_numeric(0)
|
||||
{
|
||||
compute(matrix);
|
||||
}
|
||||
|
||||
~SparseLU()
|
||||
{
|
||||
if (m_numeric)
|
||||
umfpack_free_numeric(&m_numeric,Scalar());
|
||||
}
|
||||
|
||||
inline const LMatrixType& matrixL() const
|
||||
{
|
||||
if (m_extractedDataAreDirty) extractData();
|
||||
return m_l;
|
||||
}
|
||||
|
||||
inline const UMatrixType& matrixU() const
|
||||
{
|
||||
if (m_extractedDataAreDirty) extractData();
|
||||
return m_u;
|
||||
}
|
||||
|
||||
inline const IntColVectorType& permutationP() const
|
||||
{
|
||||
if (m_extractedDataAreDirty) extractData();
|
||||
return m_p;
|
||||
}
|
||||
|
||||
inline const IntRowVectorType& permutationQ() const
|
||||
{
|
||||
if (m_extractedDataAreDirty) extractData();
|
||||
return m_q;
|
||||
}
|
||||
|
||||
Scalar determinant() const;
|
||||
|
||||
template<typename BDerived, typename XDerived>
|
||||
bool solve(const MatrixBase<BDerived> &b, MatrixBase<XDerived>* x) const;
|
||||
|
||||
template<typename Rhs>
|
||||
inline const internal::solve_retval<SparseLU<MatrixType, UmfPack>, Rhs>
|
||||
solve(const MatrixBase<Rhs>& b) const
|
||||
{
|
||||
eigen_assert(true && "SparseLU is not initialized.");
|
||||
return internal::solve_retval<SparseLU<MatrixType, UmfPack>, Rhs>(*this, b.derived());
|
||||
}
|
||||
|
||||
void compute(const MatrixType& matrix);
|
||||
|
||||
inline Index cols() const { return m_matrixRef->cols(); }
|
||||
inline Index rows() const { return m_matrixRef->rows(); }
|
||||
|
||||
inline const MatrixType& matrixLU() const
|
||||
{
|
||||
//eigen_assert(m_isInitialized && "LU is not initialized.");
|
||||
return *m_matrixRef;
|
||||
}
|
||||
|
||||
const void* numeric() const
|
||||
{
|
||||
return m_numeric;
|
||||
}
|
||||
|
||||
protected:
|
||||
|
||||
void extractData() const;
|
||||
|
||||
protected:
|
||||
// cached data:
|
||||
void* m_numeric;
|
||||
const MatrixType* m_matrixRef;
|
||||
mutable LMatrixType m_l;
|
||||
mutable UMatrixType m_u;
|
||||
mutable IntColVectorType m_p;
|
||||
mutable IntRowVectorType m_q;
|
||||
mutable bool m_extractedDataAreDirty;
|
||||
};
|
||||
|
||||
namespace internal {
|
||||
|
||||
template<typename _MatrixType, typename Rhs>
|
||||
struct solve_retval<SparseLU<_MatrixType, UmfPack>, Rhs>
|
||||
: solve_retval_base<SparseLU<_MatrixType, UmfPack>, Rhs>
|
||||
{
|
||||
typedef SparseLU<_MatrixType, UmfPack> SpLUDecType;
|
||||
EIGEN_MAKE_SOLVE_HELPERS(SpLUDecType,Rhs)
|
||||
|
||||
template<typename Dest> void evalTo(Dest& dst) const
|
||||
{
|
||||
const int rhsCols = rhs().cols();
|
||||
|
||||
eigen_assert((Rhs::Flags&RowMajorBit)==0 && "UmfPack backend does not support non col-major rhs yet");
|
||||
eigen_assert((Dest::Flags&RowMajorBit)==0 && "UmfPack backend does not support non col-major result yet");
|
||||
|
||||
void* numeric = const_cast<void*>(dec().numeric());
|
||||
|
||||
EIGEN_UNUSED int errorCode = 0;
|
||||
for (int j=0; j<rhsCols; ++j)
|
||||
{
|
||||
errorCode = umfpack_solve(UMFPACK_A,
|
||||
dec().matrixLU()._outerIndexPtr(), dec().matrixLU()._innerIndexPtr(), dec().matrixLU()._valuePtr(),
|
||||
&dst.col(j).coeffRef(0), &rhs().const_cast_derived().col(j).coeffRef(0), numeric, 0, 0);
|
||||
eigen_assert(!errorCode && "UmfPack could not solve the system.");
|
||||
}
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
} // end namespace internal
|
||||
|
||||
template<typename MatrixType>
|
||||
void SparseLU<MatrixType,UmfPack>::compute(const MatrixType& a)
|
||||
{
|
||||
typedef typename MatrixType::Index Index;
|
||||
const Index rows = a.rows();
|
||||
const Index cols = a.cols();
|
||||
eigen_assert((MatrixType::Flags&RowMajorBit)==0 && "Row major matrices are not supported yet");
|
||||
|
||||
m_matrixRef = &a;
|
||||
|
||||
if (m_numeric)
|
||||
umfpack_free_numeric(&m_numeric,Scalar());
|
||||
|
||||
void* symbolic;
|
||||
int errorCode = 0;
|
||||
errorCode = umfpack_symbolic(rows, cols, a._outerIndexPtr(), a._innerIndexPtr(), a._valuePtr(),
|
||||
&symbolic, 0, 0);
|
||||
if (errorCode==0)
|
||||
errorCode = umfpack_numeric(a._outerIndexPtr(), a._innerIndexPtr(), a._valuePtr(),
|
||||
symbolic, &m_numeric, 0, 0);
|
||||
|
||||
umfpack_free_symbolic(&symbolic,Scalar());
|
||||
|
||||
m_extractedDataAreDirty = true;
|
||||
|
||||
Base::m_succeeded = (errorCode==0);
|
||||
}
|
||||
|
||||
template<typename MatrixType>
|
||||
void SparseLU<MatrixType,UmfPack>::extractData() const
|
||||
{
|
||||
if (m_extractedDataAreDirty)
|
||||
{
|
||||
// get size of the data
|
||||
int lnz, unz, rows, cols, nz_udiag;
|
||||
umfpack_get_lunz(&lnz, &unz, &rows, &cols, &nz_udiag, m_numeric, Scalar());
|
||||
|
||||
// allocate data
|
||||
m_l.resize(rows,(std::min)(rows,cols));
|
||||
m_l.resizeNonZeros(lnz);
|
||||
|
||||
m_u.resize((std::min)(rows,cols),cols);
|
||||
m_u.resizeNonZeros(unz);
|
||||
|
||||
m_p.resize(rows);
|
||||
m_q.resize(cols);
|
||||
|
||||
// extract
|
||||
umfpack_get_numeric(m_l._outerIndexPtr(), m_l._innerIndexPtr(), m_l._valuePtr(),
|
||||
m_u._outerIndexPtr(), m_u._innerIndexPtr(), m_u._valuePtr(),
|
||||
m_p.data(), m_q.data(), 0, 0, 0, m_numeric);
|
||||
|
||||
m_extractedDataAreDirty = false;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename MatrixType>
|
||||
typename SparseLU<MatrixType,UmfPack>::Scalar SparseLU<MatrixType,UmfPack>::determinant() const
|
||||
{
|
||||
Scalar det;
|
||||
umfpack_get_determinant(&det, 0, m_numeric, 0);
|
||||
return det;
|
||||
}
|
||||
|
||||
template<typename MatrixType>
|
||||
template<typename BDerived,typename XDerived>
|
||||
bool SparseLU<MatrixType,UmfPack>::solve(const MatrixBase<BDerived> &b, MatrixBase<XDerived> *x) const
|
||||
{
|
||||
//const int size = m_matrix.rows();
|
||||
const int rhsCols = b.cols();
|
||||
// eigen_assert(size==b.rows());
|
||||
eigen_assert((BDerived::Flags&RowMajorBit)==0 && "UmfPack backend does not support non col-major rhs yet");
|
||||
eigen_assert((XDerived::Flags&RowMajorBit)==0 && "UmfPack backend does not support non col-major result yet");
|
||||
|
||||
int errorCode;
|
||||
for (int j=0; j<rhsCols; ++j)
|
||||
{
|
||||
errorCode = umfpack_solve(UMFPACK_A,
|
||||
m_matrixRef->_outerIndexPtr(), m_matrixRef->_innerIndexPtr(), m_matrixRef->_valuePtr(),
|
||||
&x->col(j).coeffRef(0), &b.const_cast_derived().col(j).coeffRef(0), m_numeric, 0, 0);
|
||||
if (errorCode!=0)
|
||||
return false;
|
||||
}
|
||||
// errorCode = umfpack_di_solve(UMFPACK_A,
|
||||
// m_matrixRef._outerIndexPtr(), m_matrixRef._innerIndexPtr(), m_matrixRef._valuePtr(),
|
||||
// x->derived().data(), b.derived().data(), m_numeric, 0, 0);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
#endif // EIGEN_UMFPACKSUPPORT_H
|
@ -2,46 +2,6 @@
|
||||
include_directories(../../test ../../unsupported ../../Eigen
|
||||
${CMAKE_CURRENT_BINARY_DIR}/../../test)
|
||||
|
||||
set(SPARSE_LIBS "")
|
||||
|
||||
# configure blas/lapack (use Eigen's by default)
|
||||
set(BLAS_FOUND TRUE)
|
||||
set(LAPACK_FOUND TRUE)
|
||||
set(BLAS_LIBRARIES eigen_blas)
|
||||
set(LAPACK_LIBRARIES eigen_lapack)
|
||||
|
||||
find_package(Cholmod)
|
||||
if(CHOLMOD_FOUND AND BLAS_FOUND AND LAPACK_FOUND)
|
||||
add_definitions("-DEIGEN_CHOLMOD_SUPPORT")
|
||||
include_directories(${CHOLMOD_INCLUDES})
|
||||
set(SPARSE_LIBS ${SPARSE_LIBS} ${CHOLMOD_LIBRARIES} ${BLAS_LIBRARIES} ${LAPACK_LIBRARIES})
|
||||
ei_add_property(EIGEN_TESTED_BACKENDS "Cholmod, ")
|
||||
else()
|
||||
ei_add_property(EIGEN_MISSING_BACKENDS "Cholmod, ")
|
||||
endif()
|
||||
|
||||
find_package(Umfpack)
|
||||
if(UMFPACK_FOUND AND BLAS_FOUND)
|
||||
add_definitions("-DEIGEN_UMFPACK_SUPPORT")
|
||||
include_directories(${UMFPACK_INCLUDES})
|
||||
set(SPARSE_LIBS ${SPARSE_LIBS} ${UMFPACK_LIBRARIES} ${BLAS_LIBRARIES})
|
||||
set(UMFPACK_ALL_LIBS ${UMFPACK_LIBRARIES} ${BLAS_LIBRARIES})
|
||||
ei_add_property(EIGEN_TESTED_BACKENDS "UmfPack, ")
|
||||
else()
|
||||
ei_add_property(EIGEN_MISSING_BACKENDS "UmfPack, ")
|
||||
endif()
|
||||
|
||||
find_package(SuperLU)
|
||||
if(SUPERLU_FOUND AND BLAS_FOUND)
|
||||
add_definitions("-DEIGEN_SUPERLU_SUPPORT")
|
||||
include_directories(${SUPERLU_INCLUDES})
|
||||
set(SPARSE_LIBS ${SPARSE_LIBS} ${SUPERLU_LIBRARIES} ${BLAS_LIBRARIES})
|
||||
set(SUPERLU_ALL_LIBS ${SUPERLU_LIBRARIES} ${BLAS_LIBRARIES})
|
||||
ei_add_property(EIGEN_TESTED_BACKENDS "SuperLU, ")
|
||||
else()
|
||||
ei_add_property(EIGEN_MISSING_BACKENDS "SuperLU, ")
|
||||
endif()
|
||||
|
||||
find_package(GoogleHash)
|
||||
if(GOOGLEHASH_FOUND)
|
||||
add_definitions("-DEIGEN_GOOGLEHASH_SUPPORT")
|
||||
@ -88,22 +48,6 @@ else()
|
||||
ei_add_property(EIGEN_MISSING_BACKENDS "MPFR C++, ")
|
||||
endif()
|
||||
|
||||
ei_add_test(sparse_llt "" "${SPARSE_LIBS}")
|
||||
ei_add_test(sparse_ldlt "" "${SPARSE_LIBS}")
|
||||
ei_add_test(sparse_lu_legacy "" "${SPARSE_LIBS}")
|
||||
|
||||
ei_add_test(simplicial_cholesky)
|
||||
ei_add_test(conjugate_gradient)
|
||||
ei_add_test(bicgstab)
|
||||
|
||||
if(UMFPACK_FOUND)
|
||||
ei_add_test(umfpack_support "" "${UMFPACK_ALL_LIBS}")
|
||||
endif()
|
||||
|
||||
if(SUPERLU_FOUND)
|
||||
ei_add_test(superlu_support "" "${SUPERLU_ALL_LIBS}")
|
||||
endif()
|
||||
|
||||
ei_add_test(sparse_extra "" "")
|
||||
|
||||
find_package(FFTW)
|
||||
@ -150,4 +94,3 @@ endif(GSL_FOUND)
|
||||
ei_add_test(polynomialsolver " " "${GSL_LIBRARIES}" )
|
||||
ei_add_test(polynomialutils)
|
||||
ei_add_test(kronecker_product)
|
||||
ei_add_test(cg)
|
||||
|
Loading…
x
Reference in New Issue
Block a user