Esempio n. 1
0
Measurement::Measurement(MatrixXcd observable)
{
    ComplexEigenSolver<MatrixXcd> solver(observable);
    MatrixXcd vectors = solver.eigenvectors();
    for (int i = 0; i < vectors.cols(); ++i)
	addOperator(vectors.col(i) * vectors.col(i).transpose(), i_to_string(i));    
    _checkOperatorsAreValid();
}
Esempio n. 2
0
Rcpp::List EigsGen::extract()
{
    int nconv = iparam[5 - 1];
    int niter = iparam[9 - 1];

    // Sometimes there are nconv = nev + 1 converged eigenvalues,
    // mainly due to pairs of complex eigenvalues.
    // We will truncate at nev.
    int truenconv = nconv > nev ? nev : nconv;

    // Converged eigenvalues from aupd()
    VectorXcd evalsConverged(nconv);
    evalsConverged.real() = MapVec(workl + ncv * ncv, nconv);
    evalsConverged.imag() = MapVec(workl + ncv * ncv + ncv, nconv);
    
    // If only eigenvalues are requested
    if(!retvec)
    {
        if(nconv < nev)
            ::Rf_warning("only %d eigenvalues converged, less than k", nconv);

        sortDesc(evalsConverged);
        
        if(evalsConverged.size() > truenconv)
            evalsConverged.conservativeResize(truenconv);
        
        return returnResult(returnRealIfPossible(evalsConverged),
                            R_NilValue, wrap(truenconv), wrap(niter));
    }
    
    // Recompute the Hessenburg matrix, since occasionally
    // aupd() will give us the incorrect one
    recomputeH();

    MapMat Hm(workl, ncv, ncv);
    MapMat Vm(V, n, ncv);
    RealSchur<MatrixXd> schur(Hm);
    MatrixXd Qm = schur.matrixU();
    MatrixXd Rm = schur.matrixT();
    VectorXcd evalsRm(ncv);
    VectorXi selectInd(nconv);
    
    eigenvalueSchur(Rm, evalsRm);
    findMatchedIndex(evalsConverged.head(nconv), evalsRm, selectInd);
    
    //Rcpp::Rcout << evalsRm << "\n\n";
    //Rcpp::Rcout << evalsConverged << "\n\n";
    
    truenconv = selectInd.size();
    if(truenconv < 1)
    {
        ::Rf_warning("no converged eigenvalues found");
        
        return returnResult(R_NilValue, R_NilValue, wrap(0L),
                            wrap(niter));
    }
    
    // Shrink Qm and Rm to the dimension given by the largest value
    // in selectInd. Since selectInd is strictly increasing,
    // we can just use its last value.
    int lastInd = selectInd[selectInd.size() - 1];
    Qm.conservativeResize(Eigen::NoChange, lastInd + 1);
    Rm.conservativeResize(lastInd + 1, lastInd + 1);
    
    // Eigen decomposition of Rm
    EigenSolver<MatrixXd> es(Rm);
    evalsRm = es.eigenvalues();
    MatrixXcd evecsA = Vm * (Qm * es.eigenvectors());
    
    // Order and select eigenvalues/eigenvectors
    for(int i = 0; i < truenconv; i++)
    {
        // Since selectInd[i] >= i for all i, it is safe to
        // overwrite the elements and columns.
        evalsRm[i] = evalsRm[selectInd[i]];
    }
    if(evalsRm.size() > truenconv)
        evalsRm.conservativeResize(truenconv);
    transformEigenvalues(evalsRm);
    // Now (evalsRm, selectInd) gives the pair of (value, location)
    sortDescPair(evalsRm, selectInd);
    
    if(truenconv > nev)
    {
        truenconv = nev;
        evalsRm.conservativeResize(truenconv);
    }
    MatrixXcd evecsConverged(n, truenconv);
    for(int i = 0; i < truenconv; i++)
    {
        evecsConverged.col(i) = evecsA.col(selectInd[i]);
    }
    
    if(truenconv < nev)
        ::Rf_warning("only %d eigenvalues converged, less than k", truenconv);

    return returnResult(returnRealIfPossible(evalsRm),
                        returnRealIfPossible(evecsConverged),
                        wrap(truenconv),
                        wrap(niter));
}
Esempio n. 3
0
bool Ellipsoid::overlapsWith(Ellipsoid ellipsoid, bool &ellipsoidMatrixDecompositionIsSuccessful)
{
    // Construct translation matrix

    MatrixXd T1 = MatrixXd::Identity(Ndimensions+1,Ndimensions+1);
    MatrixXd T2 = MatrixXd::Identity(Ndimensions+1,Ndimensions+1);
    
    T1.bottomLeftCorner(1,Ndimensions) = (-1.0) * centerCoordinates.transpose();
    T2.bottomLeftCorner(1,Ndimensions) = (-1.0) * ellipsoid.getCenterCoordinates().transpose();


    // Construct ellipsoid matrix in homogeneous coordinates

    MatrixXd A = MatrixXd::Zero(Ndimensions+1,Ndimensions+1);
    MatrixXd B = A;

    A(Ndimensions,Ndimensions) = -1;
    B(Ndimensions,Ndimensions) = -1;

    A.topLeftCorner(Ndimensions,Ndimensions) = covarianceMatrix.matrix().inverse();
    B.topLeftCorner(Ndimensions,Ndimensions) = ellipsoid.getCovarianceMatrix().matrix().inverse();

    MatrixXd AT = T1*A*T1.transpose();        // Translating to ellipsoid center
    MatrixXd BT = T2*B*T2.transpose();        // Translating to ellipsoid center


    // Compute Hyper Quadric Matrix generating from the two ellipsoids 
    // and derive its eigenvalues decomposition

    MatrixXd C = AT.inverse() * BT;
    MatrixXcd CC(Ndimensions+1,Ndimensions+1);

    CC.imag() = MatrixXd::Zero(Ndimensions+1,Ndimensions+1); 
    CC.real() = C;
    
    ComplexEigenSolver<MatrixXcd> eigenSolver(CC);


    // If eigenvalue decomposition fails, set control flag to false 
    // to stop the nested sampling and print the results 

    if (eigenSolver.info() != Success)
    {
        ellipsoidMatrixDecompositionIsSuccessful = false;
    }
    
    MatrixXcd E = eigenSolver.eigenvalues();
    MatrixXcd V = eigenSolver.eigenvectors();

    bool ellipsoidsDoOverlap = false;       // Assume no overlap in the beginning
    double pointA;                          // Point laying in this ellipsoid
    double pointB;                          // Point laying in the other ellipsoid


    // Loop over all eigenvectors

    for (int i = 0; i < Ndimensions+1; i++) 
    {
        // Skip inadmissible eigenvectors

        if (V(Ndimensions,i).real() == 0)
        {
            continue;                   
        }
        else if (E(i).imag() != 0)
            {
                V.col(i) = V.col(i).array() * (V.conjugate())(Ndimensions,i);      // Multiply eigenvector by complex conjugate of last element
                V.col(i) = V.col(i).array() / V(Ndimensions,i).real();             // Normalize eigenvector to last component value
                pointA = V.col(i).transpose().real() * AT * V.col(i).real();       // Evaluate point from this ellipsoid
                pointB = V.col(i).transpose().real() * BT * V.col(i).real();       // Evaluate point from the other ellipsoid


                // Accept only if point belongs to both ellipsoids

                if ((pointA <= 0) && (pointB <= 0))  
                {
                    ellipsoidsDoOverlap = true;            // Exit if ellipsoidsDoOverlap is found
                    break;
                }
            }
    }

    return ellipsoidsDoOverlap;
}
Esempio n. 4
0
        /*!
         \brief Partial pivoted LU to construct low-rank.


         */
	void partial_Piv_LU(const int start_Row, const int start_Col, const int n_Rows, const int n_Cols, const double tolerance, int& computed_Rank, MatrixXcd& U, MatrixXcd& V) {

	/********************************/
	/*	PURPOSE OF EXISTENCE	*/
	/********************************/

	/*!
         Obtains the low-rank decomposition of the matrix to a desired tolerance using the partial pivoting LU algorithm, i.e., given a sub-matrix 'A' and tolerance 'epsilon', computes matrices 'U' and 'V' such that ||A-UV||_F < epsilon. The norm is Frobenius norm.
         */

	/************************/
	/*	INPUTS          */
	/************************/

	///	start_Row	-	Starting row of the sub-matrix.
	///	start_Col	-	Starting column of the sub-matrix.
	///	n_Rows		-	Number of rows of the sub-matrix.
	///	n_Cols		-	Number of columns of the sub-matrix.
	///	tolerance	-	Tolerance of low-rank approximation.

	/************************/
	/*	OUTPUTS		*/
	/************************/

	///	computed_Rank	-	Rank obtained for the given tolerance.
	///	U		-	Matrix forming the column basis.
	///	V		-	Matrix forming the row basis.

		/// If the matrix is small enough, do not do anything
		int tolerable_Rank =   5;
		if (n_Cols <= tolerable_Rank){
			kernel->get_Matrix(start_Row, start_Col, n_Rows, n_Cols, U);
			V               =   MatrixXcd::Identity(n_Cols, n_Cols);
			computed_Rank   =   n_Cols;
			return;
		}
		else if (n_Rows <= tolerable_Rank){
			U               =   MatrixXcd::Identity(n_Rows, n_Rows);
			kernel->get_Matrix(start_Row, start_Col, n_Rows, n_Cols, V);
			computed_Rank   =   n_Rows;
			return;
		}

		vector<int> rowIndex;	///	This stores the row indices, which have already been used.
		vector<int> colIndex;	///	This stores the column indices, which have already been used.
		vector<VectorXcd> u;	///	Stores the column basis.
		vector<VectorXcd> v;	///	Stores the row basis.

		srand (time(NULL));
                complex<double> max, unused_max, Gamma;

		/*  INITIALIZATION  */

		/// Initialize the matrix norm and the the first row index
		double matrix_Norm  =   0;
		rowIndex.push_back(0);

		int pivot;

		computed_Rank   =   0;

		VectorXcd a, row, col;

		double row_Squared_Norm, row_Norm, col_Squared_Norm, col_Norm;

		/// Repeat till the desired tolerance is obtained
		do {
			/// Generation of the row
			kernel->get_Matrix_Row(start_Col, n_Cols, start_Row+rowIndex.back(), a);
			/// Row of the residuum and the pivot column
			row =   a;
			for (int l=0; l<computed_Rank; ++l) {
				row =   row-u[l](rowIndex.back())*v[l];
			}

			pivot   =   kernel->max_Abs_Vector(row, colIndex, max);

			int max_tries  =   100;
			int count      =   0;
			int count1     =   0;

			/// This randomization is needed if in the middle of the algorithm the row happens to be exactly the linear combination of the previous rows.
			while (abs(max)<tolerance && count < max_tries) {
				int new_rowIndex;
				rowIndex.pop_back();
				do {
					new_rowIndex   =   rand()%n_Rows;
					++count1;
				} while (find(rowIndex.begin(),rowIndex.end(),new_rowIndex)!=rowIndex.end() && count1 < max_tries);
				count1  =   0;
				rowIndex.push_back(new_rowIndex);

				/// Generation of the row
				kernel->get_Matrix_Row(start_Col, n_Cols, start_Row+rowIndex.back(), a);

				/// Row of the residuum and the pivot column
				row =   a;
				for (int l=0; l<computed_Rank; ++l) {
					row =   row-u[l](rowIndex.back())*v[l];
				}
				pivot   =   kernel->max_Abs_Vector(row, colIndex, max);
				++count;
			}

			if (count == max_tries) break;

			count = 0;

			colIndex.push_back(pivot);

			/// Normalizing constant
			Gamma   =   1.0/(max);

			/// Generation of the column
			kernel->get_Matrix_Col(start_Row, n_Rows, start_Col+colIndex.back(), a);

			/// Column of the residuum and the pivot row
			col =   a;
			for (int l=0; l<computed_Rank; ++l) {
				col =   col-v[l](colIndex.back())*u[l];
			}
			pivot   =   kernel->max_Abs_Vector(col, rowIndex, unused_max);

			/// This randomization is needed if in the middle of the algorithm the columns happens to be exactly the linear combination of the previous columns.
			while (abs(max)<tolerance && count < max_tries) {
				colIndex.pop_back();
				int new_colIndex;
				do {
					new_colIndex   =   rand()%n_Cols;
				} while (find(colIndex.begin(),colIndex.end(),new_colIndex)!=colIndex.end() && count1 < max_tries);
				count1  =   0;
				colIndex.push_back(new_colIndex);

				/// Generation of the column
				kernel->get_Matrix_Col(start_Row, n_Rows, start_Col+colIndex.back(), a);

				/// Column of the residuum and the pivot row
				col =   a;
				for (int l=0; l<computed_Rank; ++l) {
					col =   col-u[l](colIndex.back())*v[l];
				}
				pivot   =   kernel->max_Abs_Vector(col, rowIndex, unused_max);
				++count;
			}

			if (count == max_tries) break;

			count = 0;

			rowIndex.push_back(pivot);

			/// New vectors
			u.push_back(Gamma*col);
			v.push_back(row);

			/// New approximation of matrix norm
			row_Squared_Norm    =   row.squaredNorm();
			row_Norm            =   sqrt(row_Squared_Norm);

			col_Squared_Norm    =   col.squaredNorm();
			col_Norm            =   sqrt(col_Squared_Norm);

			matrix_Norm         =   matrix_Norm +   abs(Gamma*Gamma*row_Squared_Norm*col_Squared_Norm);

			for (int j=0; j<computed_Rank; ++j) {
				matrix_Norm     =   matrix_Norm +   2.0*abs(u[j].dot(u.back()))*abs(v[j].dot(v.back()));
			}
			++computed_Rank;
		} while (row_Norm*col_Norm > abs(max)*tolerance*matrix_Norm && computed_Rank <= fmin(n_Rows, n_Cols));

		/// If the computed_Rank is close to full-rank then return the trivial full-rank decomposition
		if (computed_Rank>=fmin(n_Rows, n_Cols)) {
			if (n_Rows < n_Cols) {
				U   =   MatrixXcd::Identity(n_Rows,n_Rows);
				kernel->get_Matrix(start_Row, start_Col, n_Rows, n_Cols, V);
				computed_Rank   =   n_Rows;
				return;
			}
			else {
				kernel->get_Matrix(start_Row, start_Col, n_Rows, n_Cols, U);
				V   =   MatrixXcd::Identity(n_Cols,n_Cols);
				computed_Rank   =   n_Cols;
				return;
			}
		}

		U   =   MatrixXcd(n_Rows,computed_Rank);
		V   =   MatrixXcd(computed_Rank,n_Cols);
		for (int j=0; j<computed_Rank; ++j) {
			U.col(j)    =   u[j];
			V.row(j)    =   v[j];
		}
	};
Esempio n. 5
0
int main() {

    // The eigen approach
    ArrayXd n                = ArrayXd::LinSpaced(N+1,0,N);
    double multiplier        = M_PI/N;
    Array<double, 1, N+1> nT = n.transpose();
    ArrayXd x                = - cos(multiplier*n);
    ArrayXd xsub             = x.middleRows(1, N-1);
    ArrayXd ysub             = (x1-x0)/2*xsub + (x1+x0)/2;

    ArrayXXd T               = cos((acos(x).matrix()*nT.matrix()).array());
    ArrayXXd Tsub            = cos((acos(xsub).matrix()*nT.matrix()).array());
    ArrayXd sqinx            = 1/sqrt(1-xsub*xsub);

    MatrixXd inv1x2          = (sqinx).matrix().asDiagonal();

    // Can't use the following to test elements of inv1x2
    // std::cout << inv1x2(0,0) << "\n";

    MatrixXd Usub            = inv1x2 * sin(((acos(xsub).matrix())*nT.matrix()).array()).matrix();
    MatrixXd dTsub           = Usub*(n.matrix().asDiagonal());
    MatrixXd d2Tsub          = ((sqinx*sqinx).matrix().asDiagonal())*((xsub.matrix().asDiagonal()) * (dTsub.matrix()) - (Tsub.matrix()) * ((n*n).matrix().asDiagonal()));

    MatrixXd d2T(N+1, N+1);
    RowVectorXd a            = (pow((-1),nT))*(nT*nT+1)*(nT*nT)/3;
    RowVectorXd b            = (nT*nT+1)*(nT*nT)/3;
    d2T.middleRows(1,N-1)    = d2Tsub; 
    d2T.row(0)               = a;
    d2T.row(N)               = b;

    MatrixXd D2              = d2T.matrix() * ((T.matrix()).inverse());
    MatrixXd E2              = D2.middleRows(1,N-1).middleCols(1,N-1);
    MatrixXd Y               = ysub.matrix().asDiagonal();
    MatrixXd H               = - (4 / ((x1-x0)*(x1-x0))) * E2 + k*Y;

    Eigen::EigenSolver<Eigen::MatrixXd> HE(H);
    VectorXcd D              = HE.eigenvalues();
    MatrixXcd V              = HE.eigenvectors();
    std::cout << HE.info() << std::endl;

    // Open ofstream
    ofstream Dfile;
    Dfile.open("D-output.txt");

    ofstream Vfile;
    Vfile.open("V-output.txt");

    ofstream V544file;
    V544file.open("V544-output.txt");

    Dfile.precision(15);
    Dfile << D.real() << "\n";

    Vfile.precision(15);
    Vfile << V.real() << "\n";

    V544file.precision(15);

	for(int i = 1; i<N-1; i++)
    {
		V544file << ysub[i-1];
        V544file << " "        << V.col(544).row(i-1).real() << "\n";
	}
    Dfile.close();
    Vfile.close();
	V544file.close();
	system("gnuplot -p plot.gp");
	system("rsvg-convert -w 2000 -o V544-plot.png V544-plot.svg");

}