CDenseMatrixOperator<T>::CDenseMatrixOperator(
	const CDenseMatrixOperator<T>& orig)
	: CMatrixOperator<T>(orig.get_dimension())
	{
		init();

		m_operator=SGMatrix<T>(orig.m_operator.num_rows, orig.m_operator.num_cols);
		for (index_t i=0; i<m_operator.num_cols; ++i)
		{
			for (index_t j=0; j<m_operator.num_rows; ++j)
				m_operator(j,i)=orig.m_operator(j,i);
		}

		SG_SGCDEBUG("%s deep copy created (%p)\n", this->get_name(), this);
	}
Пример #2
0
void CDirectEigenSolver::compute()
{
	if (m_is_computed_min && m_is_computed_max)
	{
		SG_DEBUG("Minimum/maximum eigenvalues are already computed, exiting\n");
		return;
	}

	CDenseMatrixOperator<float64_t>* op
		=dynamic_cast<CDenseMatrixOperator<float64_t>*>(m_linear_operator);
	REQUIRE(op, "Linear operator is not of CDenseMatrixOperator type!\n");

	SGMatrix<float64_t> m=op->get_matrix_operator();
	Map<MatrixXd> map_m(m.matrix, m.num_rows, m.num_cols);

	// compute the eigenvalues with Eigen3
	SelfAdjointEigenSolver<MatrixXd> eig_solver(map_m);
	m_min_eigenvalue=eig_solver.eigenvalues()[0];
	m_max_eigenvalue=eig_solver.eigenvalues()[op->get_dimension()-1];

	m_is_computed_min=true;
	m_is_computed_max=false;
}
Пример #3
0
void CDenseMatrixExactLog::precompute()
{
	SG_DEBUG("Entering...\n");

	// check for proper downcast
	CDenseMatrixOperator<float64_t>* op
		=dynamic_cast<CDenseMatrixOperator<float64_t>*>(m_linear_operator);
	REQUIRE(op, "Operator not an instance of DenseMatrixOperator!\n");
	SGMatrix<float64_t> m=op->get_matrix_operator();

	// compute log(C) using Eigen3
	Map<MatrixXd> mat(m.matrix, m.num_rows, m.num_cols);
	SGMatrix<float64_t> log_m(m.num_rows, m.num_cols);
	Map<MatrixXd> log_mat(log_m.matrix, log_m.num_rows, log_m.num_cols);
	log_mat=mat.log();

	// the log(C) is also a linear operator here
	// reset the operator of this function with log(C)
	SG_UNREF(m_linear_operator);
	m_linear_operator=new CDenseMatrixOperator<float64_t>(log_m);
	SG_REF(m_linear_operator);

	SG_DEBUG("Leaving...\n");
}
CJobResultAggregator* CLogRationalApproximationIndividual::submit_jobs(
	SGVector<float64_t> sample)
{
	SG_DEBUG("OperatorFunction::submit_jobs(): Entering..\n");
	REQUIRE(sample.vector, "Sample is not initialized!\n");
	REQUIRE(m_linear_operator, "Operator is not initialized!\n");
	REQUIRE(m_computation_engine, "Computation engine is NULL\n");

	// create the aggregator with sample, and the multiplier
	CIndividualJobResultAggregator* agg=new CIndividualJobResultAggregator(
		m_linear_operator, sample, m_constant_multiplier);
	// we don't want the aggregator to be destroyed when the job is unref-ed
	SG_REF(agg);

	// this enum will save from repeated typechecking for all jobs
	enum typeID {DENSE=1, SPARSE, UNKNOWN} operator_type=UNKNOWN;

	// create a complex copy of the matrix linear operator
	CMatrixOperator<complex128_t>* complex_op=NULL;
	if (typeid(*m_linear_operator)==typeid(CDenseMatrixOperator<float64_t>))
	{
		operator_type=DENSE;

		CDenseMatrixOperator<float64_t>* op
			=dynamic_cast<CDenseMatrixOperator<float64_t>*>(m_linear_operator);

		REQUIRE(op->get_matrix_operator().matrix, "Matrix is not initialized!\n");

		// create complex dense matrix operator
		complex_op=static_cast<CDenseMatrixOperator<complex128_t>*>(*op);
	}
	else if (typeid(*m_linear_operator)==typeid(CSparseMatrixOperator<float64_t>))
	{
		operator_type=SPARSE;

		CSparseMatrixOperator<float64_t>* op
			=dynamic_cast<CSparseMatrixOperator<float64_t>*>(m_linear_operator);

		REQUIRE(op->get_matrix_operator().sparse_matrix, "Matrix is not initialized!\n");

		// create complex sparse matrix operator
		complex_op=static_cast<CSparseMatrixOperator<complex128_t>*>(*op);
	}
	else
	{
		// something weird happened
		SG_ERROR("OperatorFunction::submit_jobs(): Unknown MatrixOperator given!\n");
	}

	// create num_shifts number of jobs for current sample vector
	for (index_t i=0; i<m_num_shifts; ++i)
	{
		// create a deep copy of the operator
		CMatrixOperator<complex128_t>* shifted_op=NULL;

		switch(operator_type)
		{
		case DENSE:
			shifted_op=new CDenseMatrixOperator<complex128_t>
				(*dynamic_cast<CDenseMatrixOperator<complex128_t>*>(complex_op));
			break;
		case SPARSE:
			shifted_op=new CSparseMatrixOperator<complex128_t>
				(*dynamic_cast<CSparseMatrixOperator<complex128_t>*>(complex_op));
			break;
		default:
			break;
		}

		REQUIRE(shifted_op, "OperatorFunction::submit_jobs():"
			"MatrixOperator typeinfo was not detected!\n");

		// move the shift inside the operator
		// (see CRationalApproximation)
		SGVector<complex128_t> diag=shifted_op->get_diagonal();
		for (index_t j=0; j<diag.vlen; ++j)
			diag[j]-=m_shifts[i];
		shifted_op->set_diagonal(diag);

		// create a job and submit to the engine
		CRationalApproximationIndividualJob* job
			=new CRationalApproximationIndividualJob(agg, m_linear_solver,
				shifted_op, sample, m_weights[i]);
		SG_REF(job);

		m_computation_engine->submit_job(job);

		// we can safely unref the job here, computation engine takes it from here
		SG_UNREF(job);
	}

	SG_UNREF(complex_op);

	SG_DEBUG("OperatorFunction::submit_jobs(): Leaving..\n");
	return agg;
}