/* * Project: MoleCuilder * Description: creates and alters molecular systems * Copyright (C) 2010 University of Bonn. All rights reserved. * Please see the LICENSE file or "Copyright notice" in builder.cpp for details. */ /* * Eigenspace.cpp * * Created on: Nov 22, 2010 * Author: heber */ // include config.h #ifdef HAVE_CONFIG_H #include #endif #include "CodePatterns/MemDebug.hpp" #include #include #include "CodePatterns/Assert.hpp" #include "CodePatterns/Log.hpp" #include "CodePatterns/Verbose.hpp" #include "Eigenspace.hpp" /** Constructor for Eigenspace. * @param _Indices index set for columns and rows of EigenspaceMatrix. */ Eigenspace::Eigenspace(const indexset &_Indices) : Indices(_Indices), EigenspaceMatrix(_Indices.size(),_Indices.size()), EigenvectorMatrix(_Indices.size(),_Indices.size()) { EigenvectorMatrix.setIdentity(); for (size_t i = 0 ; i< _Indices.size(); ++i) Eigenvalues.push_back(0.); createEigenvectorViews(); } /** Constructor for Eigenspace. * @param _Indices index set for columns and rows of EigenspaceMatrix. * @param _matrix matrix to use */ Eigenspace::Eigenspace(const indexset &_Indices, const MatrixContent &_matrix) : Indices(_Indices), EigenspaceMatrix(_matrix), EigenvectorMatrix(_matrix.getRows(), _matrix.getColumns()) { ASSERT(_Indices.size() == _matrix.getRows(), "Eigenspace::Eigenspace() - number of indices "+toString(_Indices.size()) +" and row dimension of matrix "+toString(_matrix.getRows())+" don't match!"); ASSERT(_Indices.size() == _matrix.getColumns(), "Eigenspace::Eigenspace() - number of indices "+toString(_Indices.size()) +" and column dimension of matrix "+toString(_matrix.getColumns())+" don't match!"); EigenvectorMatrix.setIdentity(); for (size_t i = 0 ; i< _Indices.size(); ++i) Eigenvalues.push_back(0.); createEigenvectorViews(); } /** Destructor for Eigenspace. * */ Eigenspace::~Eigenspace() {} /** Create a number of eigenvectors in Eigenspace::Eigenvectors. * These are views on the resepctive column vectors in * Eigenspace::EigenvectorMatrix. */ void Eigenspace::createEigenvectorViews() { const size_t ColumnCount = EigenvectorMatrix.getColumns(); for (size_t iter = 0; iter < ColumnCount; ++iter) { boost::shared_ptr ev(EigenvectorMatrix.getColumnVector(iter)); Eigenvectors.push_back( ev ); DoLog(1) && (Log() << Verbose(1) << iter << " th Eigenvector is " << *ev << std::endl); } } /** Obtains the eigenvectors to Eigenspace::EigenspaceMatrix. * We diagonalize the matrix and set the Eigenspace::Eigenvectors and * Eigenspace::Eigenvalues. */ void Eigenspace::calculateEigenSubspace() { ASSERT(0, "Eigenspace::calculateEigenSubspace() - we never want to call this function!"); } /** Getter for constant reference to Eigenspace::EigenspaceMatrix. * * @return Eigenspace::EigenspaceMatrix */ const MatrixContent & Eigenspace::getEigenspaceMatrix() const { return EigenspaceMatrix; } /** Setter for Eigenspace::EigenspaceMatrix. * * @param _content matrix to use */ void Eigenspace::setEigenspaceMatrix(const MatrixContent &_content) { EigenspaceMatrix = _content; EigenvectorMatrix.setZero(); } const VectorContent & Eigenspace::getEigenvector(const size_t i) const { return *(Eigenvectors[i]); } /** Checks whether each index of _indexset is contained in this subspace:Indices. * * @param _subspace subspace set to check * @return true - _index is contained, false - at least index is not contained */ bool Eigenspace::contains(const Eigenspace &_subspace) { BOOST_FOREACH(size_t iter, _subspace.getIndices()) { if (Indices.count(iter) == 0) { // index not present, then not contained return false; } } return true; } /** Getter for Eigenspace::Indices. * * @return indexset of this eigenspace */ const Eigenspace::indexset & Eigenspace::getIndices() const { return Indices; } const MatrixContent & Eigenspace::getEigenvectorMatrix() const { return EigenvectorMatrix; } const double Eigenspace::getEigenvalue(const size_t i) const { return Eigenvalues[i]; } const Eigenspace::eigenvalueset & Eigenspace::getEigenvalues() const { return Eigenvalues; } /** Sets the eigenvectors and -values. * * We only implement this for eigenpairs, not eigenvector and eigenvalue * distinctly to avoid mismatches, i.e. old eigenvalues used because only new * eigenvectors have been given. * * @param CurrentEigenvectors eigenvectors to set to * @param CurrentEigenvalues eigenvalues to set to */ void Eigenspace::setEigenpairs(const eigenvectorset &CurrentEigenvectors, const eigenvalueset &CurrentEigenvalues) { ASSERT(CurrentEigenvectors.size() == Eigenvectors.size(), "Eigenspace::setEigenpairs() - " +toString(CurrentEigenvectors.size())+" x CurrentEigenvectors is not the same as " +toString(Eigenvectors.size())+"x Eigenvectors!"); // set eigenvectors std::vector >::const_iterator newev = CurrentEigenvectors.begin(); for(std::vector >::iterator ev = Eigenvectors.begin(); ev != Eigenvectors.end(); ++ev, ++newev) { *ev = *newev; } // eigenvalues can be just copied (integral type) Eigenvalues.clear(); Eigenvalues = CurrentEigenvalues; } /** Output operator for Eigenspace. * * @param ost output stream * @param _s Eigenspace to print: Indices and contained matrix * @return given output stream */ std::ostream & operator<<(std::ostream &ost, const Eigenspace &_s) { BOOST_FOREACH(size_t iter, _s.Indices) { ost << iter << " "; } ost << " with matrix " << _s.EigenspaceMatrix; return ost; }