bool probing_test(Epetra_CrsMatrix & in_mat, bool build_list){ const Epetra_CrsGraph & graph=in_mat.Graph(); Teuchos::ParameterList main, zoltan; if(build_list){ // zoltan.set("DISTANCE","2"); main.set("ZOLTAN",zoltan); } Isorropia::Epetra::Prober prober(Teuchos::rcp<const Epetra_CrsGraph>(&graph,false),main); Epetra_CrsMatrix out_mat(Copy,graph); int rv=prober.probe(in_mat,out_mat); if(rv!=0) {printf("ERROR: probing failed\n");return false;} #ifdef HAVE_EPETRAEXT EpetraExt::MatrixMatrix::Add(in_mat,false,1,out_mat,-1); double nrm=out_mat.NormInf()/in_mat.NormInf(); if(!in_mat.Comm().MyPID()) printf("diff norm = %22.16e\n",nrm); if(nrm < 1e-12) return true; else return false; #endif return true; }
/*! * \brief Solve. */ void JacobiSolver::iterate( const int max_iters, const double tolerance ) { // Extract the linear problem. Epetra_CrsMatrix *A = dynamic_cast<Epetra_CrsMatrix*>( d_linear_problem->GetMatrix() ); Epetra_Vector *x = dynamic_cast<Epetra_Vector*>( d_linear_problem->GetLHS() ); const Epetra_Vector *b = dynamic_cast<Epetra_Vector*>( d_linear_problem->GetRHS() ); // Setup the residual. Epetra_Map row_map = A->RowMap(); Epetra_Vector residual( row_map ); // Iterate. Epetra_CrsMatrix H = buildH( A ); Epetra_Vector temp_vec( row_map ); d_num_iters = 0; double residual_norm = 1.0; double b_norm; b->NormInf( &b_norm ); double conv_crit = b_norm*tolerance; while ( residual_norm > conv_crit && d_num_iters < max_iters ) { H.Apply( *x, temp_vec ); x->Update( 1.0, temp_vec, 1.0, *b, 0.0 ); A->Apply( *x, temp_vec ); residual.Update( 1.0, *b, -1.0, temp_vec, 0.0 ); residual.NormInf( &residual_norm ); ++d_num_iters; } }
//========================================================================== int Ifpack_CrsRiluk::InitValues(const Epetra_CrsMatrix & A) { UserMatrixIsCrs_ = true; if (!Allocated()) AllocateCrs(); Teuchos::RefCountPtr<Epetra_CrsMatrix> OverlapA = Teuchos::rcp( (Epetra_CrsMatrix *) &A, false ); if (IsOverlapped_) { OverlapA = Teuchos::rcp( new Epetra_CrsMatrix(Copy, *Graph_.OverlapGraph()) ); EPETRA_CHK_ERR(OverlapA->Import(A, *Graph_.OverlapImporter(), Insert)); EPETRA_CHK_ERR(OverlapA->FillComplete()); } // Get Maximun Row length int MaxNumEntries = OverlapA->MaxNumEntries(); // Set L range map and U domain map U_DomainMap_ = Teuchos::rcp( &(A.DomainMap()), false ); L_RangeMap_ = Teuchos::rcp( &(A.RangeMap()), false ); // Do the rest using generic Epetra_RowMatrix interface EPETRA_CHK_ERR(InitAllValues(*OverlapA, MaxNumEntries)); return(0); }
// Simple Power method algorithm double power_method(const Epetra_CrsMatrix& A) { // variable needed for iteration double lambda = 0.0; int niters = A.RowMap().NumGlobalElements()*10; double tolerance = 1.0e-10; // Create vectors Epetra_Vector q(A.RowMap()); Epetra_Vector z(A.RowMap()); Epetra_Vector resid(A.RowMap()); // Fill z with random Numbers z.Random(); // variable needed for iteration double normz; double residual = 0; int iter = 0; while (iter==0 || (iter < niters && residual > tolerance)) { z.Norm2(&normz); // Compute 2-norm of z q.Scale(1.0/normz, z); A.Multiply(false, q, z); // Compute z = A*q q.Dot(z, &lambda); // Approximate maximum eigenvalue if (iter%10==0 || iter+1==niters) { // Compute A*q - lambda*q every 10 iterations resid.Update(1.0, z, -lambda, q, 0.0); resid.Norm2(&residual); if (q.Map().Comm().MyPID()==0) std::cout << "Iter = " << iter << " Lambda = " << lambda << " Two-norm of A*q - lambda*q = " << residual << std::endl; } iter++; } return(lambda); }
int test_azoo_conv_anorm(Epetra_CrsMatrix& A, Epetra_Vector& x, Epetra_Vector& b, bool verbose) { if (verbose) { cout << "testing AztecOO with AZ_conv = AZ_Anorm" << endl; } Epetra_Vector soln_Anorm(x), soln_none(x), vec1(x), rhs(x); //We'll put large numbers in a vector and use that to generate an rhs //which has norm much larger than the infinity-norm of the matrix. vec1.PutScalar(1000.0); soln_Anorm.PutScalar(0.0); soln_none.PutScalar(0.0); A.Multiply(false, vec1, rhs); AztecOO azoo(&A, &soln_Anorm, &rhs); azoo.SetAztecOption(AZ_conv, AZ_Anorm); azoo.SetAztecOption(AZ_solver, AZ_cg); //azoo.SetAztecOption(AZ_scaling, AZ_sym_diag); azoo.Iterate(30, 1.e-5); AztecOO azoo1(&A, &soln_none, &rhs); azoo1.SetAztecOption(AZ_conv, AZ_rhs); azoo1.SetAztecOption(AZ_solver, AZ_cg); azoo1.Iterate(30, 1.e-5); double rhsnorm = 0.0; rhs.Norm2(&rhsnorm); double anorm = A.NormInf(); double rnrm_anorm = resid2norm(A, soln_Anorm, rhs); double rnrm_rhs = resid2norm(A, soln_none, rhs); //we expect the ratio rnrm_anorm/rnrm_rhs to roughly equal //the ratio anorm/rhsnorm, since rnrm_anorm is the residual norm //obtained for the solve that used Anorm scaling to determine //convergence, and rnrm_rhs is the residual norm obtained for //the solve that used rhs scaling. double ratio1 = rnrm_anorm/rnrm_rhs; double ratio2 = anorm/rhsnorm; cout << "ratio1: " << ratio1 << ", ratio2: " << ratio2 << endl; if (std::abs(ratio1 - ratio2) > 1.e-1) { if (verbose) { cout << "anorm: " << anorm << ", rhsnorm: " << rhsnorm << "rnrm_anorm: " << rnrm_anorm << ", rnrm_rhs: " << rnrm_rhs<<endl; } return(-1); } return(0); }
int InitMatValues( const Epetra_CrsMatrix& newA, Epetra_CrsMatrix* A ) { int numMyRows = newA.NumMyRows(); int maxNum = newA.MaxNumEntries(); int numIn; int *idx = 0; double *vals = 0; idx = new int[maxNum]; vals = new double[maxNum]; // For each row get the values and indices, and replace the values in A. for (int i=0; i<numMyRows; ++i) { // Get the values and indices from newA. EPETRA_CHK_ERR( newA.ExtractMyRowCopy(i, maxNum, numIn, vals, idx) ); // Replace the values in A EPETRA_CHK_ERR( A->ReplaceMyValues(i, numIn, vals, idx) ); } // Clean up. delete [] idx; delete [] vals; return 0; }
Epetra_CrsMatrix* create_and_fill_crs_matrix(const Epetra_Map& emap) { int localproc = emap.Comm().MyPID(); int local_n = emap.NumMyElements(); int global_n = emap.NumGlobalElements(); int myFirstGlobalRow = localproc*local_n; int globalCols[3]; double values[3]; Epetra_CrsMatrix* A = new Epetra_CrsMatrix(Copy, emap, 3); for(int i=0; i<local_n; ++i) { int globalRow = myFirstGlobalRow +i; int numcols = 0; if (globalRow > 0) { globalCols[numcols] = globalRow-1; values[numcols++] = -1.0; } globalCols[numcols] = globalRow; values[numcols++] = 4.0; if (globalRow < global_n-1) { globalCols[numcols] = globalRow+1; values[numcols++] = -1.0; } A->InsertGlobalValues(globalRow, numcols, values, globalCols); } A->FillComplete(); return A; }
/*----------------------------------------------------------------------* | m.gee 11/05| *----------------------------------------------------------------------*/ Epetra_CrsMatrix* ML_NOX::StripZeros(Epetra_CrsMatrix& in, double eps) { Epetra_CrsMatrix* out = new Epetra_CrsMatrix(Copy,in.RowMap(),200); for (int lrow=0; lrow<in.NumMyRows(); ++lrow) { int grow = in.GRID(lrow); if (grow<0) { cout << "ERROR: grow<0 \n"; exit(0); } int numentries; int* lindices; double* values; int err = in.ExtractMyRowView(lrow,numentries,values,lindices); if (err) { cout << "ExtractMyRowView returned " << err << endl; exit(0);} for (int j=0; j<numentries; ++j) { int lcol = lindices[j]; int gcol = in.GCID(lcol); if (gcol<0) { cout << "ERROR: gcol<0 \n"; exit(0); } if (abs(values[j])<eps && gcol != grow) continue; int err = out->InsertGlobalValues(grow,1,&values[j],&gcol); if (err) { cout << "InsertGlobalValues returned " << err << endl; exit(0);} } } out->FillComplete(); out->OptimizeStorage(); return out; }
/* ml_epetra_data_pack::setup - This function does the setup phase for ML_Epetra, pulling key parameters from the Teuchos list, and calling the aggregation routines Parameters: N - Number of unknowns [I] rowind - Row indices of matrix (CSC format) [I] colptr - Column indices of matrix (CSC format) [I] vals - Nonzero values of matrix (CSC format) [I] Returns: IS_TRUE if setup was succesful, IS_FALSE otherwise */ int ml_epetra_data_pack::setup(int N,int* rowind,int* colptr, double* vals){ int i,j; int *rnz; /* Nonzero counts for Epetra */ rnz=new int[N]; for(i=0;i<N;i++) rnz[i]=rowind[i+1]-rowind[i]; /* Epetra Setup */ Comm= new Epetra_SerialComm; Map=new Epetra_Map(N,0,*Comm); A=new Epetra_CrsMatrix(Copy,*Map,rnz); /* Do the matrix assembly */ for(i=0;i<N;i++) for(j=colptr[i];j<colptr[i+1];j++) A->InsertGlobalValues(rowind[j],1,&vals[j],&i); //NTS: Redo with block assembly, remembering to transpose A->FillComplete(); /* Allocate Memory */ Prec=new MultiLevelPreconditioner(*A, *List,false); /* Build the Heirarchy */ Prec->ComputePreconditioner(); /* Pull Operator Complexity */ operator_complexity = Prec->GetML_Aggregate()->operator_complexity / Prec->GetML_Aggregate()->fine_complexity; /* Cleanup */ delete rnz; return IS_TRUE; }/*end setup*/
// B here is the "reduced" matrix. Square matrices w/ Row=Domain=Range only. double test_with_matvec_reduced_maps(const Epetra_CrsMatrix &A, const Epetra_CrsMatrix &B, const Epetra_Map & Bfullmap){ const Epetra_Map & Amap = A.DomainMap(); Epetra_Vector Xa(Amap), Ya(Amap), Diff(Amap); const Epetra_Map *Bmap = Bfullmap.NumMyElements() > 0 ? &B.DomainMap() : 0; Epetra_Vector *Xb = Bmap ? new Epetra_Vector(*Bmap) : 0; Epetra_Vector *Yb = Bmap ? new Epetra_Vector(*Bmap) : 0; Epetra_Vector Xb_alias(View,Bfullmap, Bmap ? Xb->Values(): 0); Epetra_Vector Yb_alias(View,Bfullmap, Bmap ? Yb->Values(): 0); Epetra_Import Ximport(Bfullmap,Amap); // Set the input vector Xa.SetSeed(24601); Xa.Random(); Xb_alias.Import(Xa,Ximport,Insert); // Do the multiplies A.Apply(Xa,Ya); if(Bmap) B.Apply(*Xb,*Yb); // Check solution Epetra_Import Yimport(Amap,Bfullmap); Diff.Import(Yb_alias,Yimport,Insert); Diff.Update(-1.0,Ya,1.0); double norm; Diff.Norm2(&norm); delete Xb; delete Yb; return norm; }
//EpetraCrsMatrix_To_TpetraCrsMatrix: copies Epetra_CrsMatrix to its analogous Tpetra_CrsMatrix Teuchos::RCP<Tpetra_CrsMatrix> Petra::EpetraCrsMatrix_To_TpetraCrsMatrix(const Epetra_CrsMatrix& epetraCrsMatrix_, const Teuchos::RCP<const Teuchos::Comm<int> >& commT_) { //get row map of Epetra::CrsMatrix & convert to Tpetra::Map auto tpetraRowMap_ = EpetraMap_To_TpetraMap(epetraCrsMatrix_.RowMap(), commT_); //get col map of Epetra::CrsMatrix & convert to Tpetra::Map auto tpetraColMap_ = EpetraMap_To_TpetraMap(epetraCrsMatrix_.ColMap(), commT_); //get CrsGraph of Epetra::CrsMatrix & convert to Tpetra::CrsGraph const Epetra_CrsGraph epetraCrsGraph_ = epetraCrsMatrix_.Graph(); std::size_t maxEntries = epetraCrsGraph_.GlobalMaxNumIndices(); Teuchos::RCP<Tpetra_CrsGraph> tpetraCrsGraph_ = Teuchos::rcp(new Tpetra_CrsGraph(tpetraRowMap_, tpetraColMap_, maxEntries)); for (LO i=0; i<epetraCrsGraph_.NumMyRows(); i++) { LO NumEntries; LO *Indices; epetraCrsGraph_.ExtractMyRowView(i, NumEntries, Indices); tpetraCrsGraph_->insertLocalIndices(i, NumEntries, Indices); } tpetraCrsGraph_->fillComplete(); //convert Epetra::CrsMatrix to Tpetra::CrsMatrix, after creating Tpetra::CrsMatrix based on above Tpetra::CrsGraph Teuchos::RCP<Tpetra_CrsMatrix> tpetraCrsMatrix_ = Teuchos::rcp(new Tpetra_CrsMatrix(tpetraCrsGraph_)); tpetraCrsMatrix_->setAllToScalar(0.0); for (LO i=0; i<epetraCrsMatrix_.NumMyRows(); i++) { LO NumEntries; LO *Indices; ST *Values; epetraCrsMatrix_.ExtractMyRowView(i, NumEntries, Values, Indices); tpetraCrsMatrix_->replaceLocalValues(i, NumEntries, Values, Indices); } tpetraCrsMatrix_->fillComplete(); return tpetraCrsMatrix_; }
int build_matrix_unfused(const Epetra_CrsMatrix & SourceMatrix, Epetra_Export & RowExporter, Epetra_CrsMatrix *&A){ int rv=0; rv=A->Export(SourceMatrix, RowExporter, Insert); if(rv) {cerr<<"build_matrix_unfused: Export failed"<<endl; return rv;} rv=A->FillComplete(SourceMatrix.DomainMap(), SourceMatrix.RangeMap()); return rv; }
/* ml_epetra_data_pack_status - This function does a status query on the ML_EPETRA_DATA_PACK passed in. Returns: IS_TRUE */ int ml_epetra_data_pack::status(){ mexPrintf("**** Problem ID %d [ML_Epetra] ****\n",id); if(A) mexPrintf("Matrix: %dx%d w/ %d nnz\n",A->NumGlobalRows(),A->NumGlobalCols(),A->NumMyNonzeros()); mexPrintf(" Operator complexity = %e\n",operator_complexity); if(List){mexPrintf("Parameter List:\n");List->print(cout,1);} mexPrintf("\n"); return IS_TRUE; }/*end status*/
int runHypreTest(Epetra_CrsMatrix &A){ Epetra_Vector X(A.RowMap()); EPETRA_CHK_ERR(X.Random()); Epetra_Vector Y(A.RowMap()); EPETRA_CHK_ERR(A.Multiply(false, X, Y)); return 0; }
//! Update matrix static void update(Epetra_CrsMatrix& mat, double a, const Epetra_CrsMatrix& x) { int num_col; for (int i=0; i<mat.NumMyRows(); i++) { mat.NumMyRowEntries(i, num_col); for (int j=0; j<num_col; j++) mat[i][j] += a*x[i][j]; } }
shared_ptr<Epetra_CrsMatrix> sparseCholesky(const Epetra_CrsMatrix &mat) { // Note: we assume the matrix mat is symmetric and positive-definite size_t size = mat.NumGlobalCols(); if (mat.NumGlobalRows() != size) throw std::invalid_argument("sparseCholesky(): matrix must be square"); int *rowOffsets = 0; int *colIndices = 0; double *values = 0; mat.ExtractCrsDataPointers(rowOffsets, colIndices, values); Epetra_SerialComm comm; Epetra_LocalMap rowMap(static_cast<int>(size), 0 /* index_base */, comm); Epetra_LocalMap columnMap(static_cast<int>(size), 0 /* index_base */, comm); shared_ptr<Epetra_CrsMatrix> result = boost::make_shared<Epetra_CrsMatrix>( Copy, rowMap, columnMap, mat.GlobalMaxNumEntries()); arma::Mat<double> localMat; arma::Mat<double> localCholesky; std::vector<bool> processed(size, false); for (size_t r = 0; r < size; ++r) { if (processed[r]) continue; int localSize = rowOffsets[r + 1] - rowOffsets[r]; localMat.set_size(localSize, localSize); localMat.fill(0.); localCholesky.set_size(localSize, localSize); for (int s = 0; s < localSize; ++s) { int row = colIndices[rowOffsets[r] + s]; for (int c = 0; c < localSize; ++c) { int col = colIndices[rowOffsets[row] + c]; if (col != colIndices[rowOffsets[r] + c]) throw std::invalid_argument("sparseCholesky(): matrix is not " "block-diagonal"); localMat(s, c) = values[rowOffsets[row] + c]; } } assert(arma::norm(localMat - localMat.t(), "fro") < 1e-12 * arma::norm(localMat, "fro")); localCholesky = arma::chol(localMat); // localCholesky: U for (int s = 0; s < localSize; ++s) { int row = colIndices[rowOffsets[r] + s]; processed[row] = true; #ifndef NDEBUG int errorCode = #endif result->InsertGlobalValues(row, s + 1 /* number of values */, localCholesky.colptr(s), colIndices + rowOffsets[r]); assert(errorCode == 0); } } result->FillComplete(columnMap, rowMap); return result; }
//============================================================================== Epetra_FastCrsMatrix::Epetra_FastCrsMatrix(const Epetra_CrsMatrix & Matrix, bool UseFloats) : CrsMatrix_(Matrix), Values_(0), NumMyRows_(Matrix.NumMyRows()), NumMyNonzeros(Matrix.NumMyNonzeros()), ImportVector_(0), ExportVector_(0), CV_(Copy) { if (!CrsMatrix_.Filled()) throw CrsMatrix_.ReportError("Input matrix must have called FillComplete()", -1); Allocate(UseFloats); }
//========================================================================= bool EpetraExt::RowMatrix_Transpose::fwd() { int i, j, NumIndices, err; Epetra_CrsMatrix * OrigCrsMatrix = dynamic_cast<Epetra_CrsMatrix*>(origObj_); // Now copy values and global indices into newly create transpose storage for (i=0;i<NumMyCols_; i++) TransNumNz_[i] = 0; // Reset transpose NumNz counter for (i=0; i<NumMyRows_; i++) { if(OrigMatrixIsCrsMatrix_) err = OrigCrsMatrix->ExtractMyRowView(i, NumIndices, Values_, Indices_); else err = origObj_->ExtractMyRowCopy(i, MaxNumEntries_, NumIndices, Values_, Indices_); if (err != 0) { std::cerr << "ExtractMyRowCopy/View failed."<<std::endl; throw err; } int ii = origObj_->RowMatrixRowMap().GID(i); for (j=0; j<NumIndices; j++) { int TransRow = Indices_[j]; int loc = TransNumNz_[TransRow]; TransIndices_[TransRow][loc] = ii; TransValues_[TransRow][loc] = Values_[j]; ++TransNumNz_[TransRow]; // increment counter into current transpose row } } // Build Transpose matrix with some rows being shared across processors. // We will use a view here since the matrix will not be used for anything else const Epetra_Map & TransMap = origObj_->RowMatrixColMap(); Epetra_CrsMatrix TempTransA1(View, TransMap, TransNumNz_); TransMap.MyGlobalElements(TransMyGlobalEquations_); for (i=0; i<NumMyCols_; i++) EPETRA_CHK_ERR(TempTransA1.InsertGlobalValues(TransMyGlobalEquations_[i], TransNumNz_[i], TransValues_[i], TransIndices_[i])); // Note: The following call to FillComplete is currently necessary because // some global constants that are needed by the Export () are computed in this routine EPETRA_CHK_ERR(TempTransA1.FillComplete(false)); // Now that transpose matrix with shared rows is entered, update values of target transpose matrix TransposeMatrix_->PutScalar(0.0); // Zero out all values of the matrix EPETRA_CHK_ERR(TransposeMatrix_->Export(TempTransA1, *TransposeExporter_, Add)); return(0); }
Epetra_CrsMatrix* TridiagMatrix(const Epetra_Map* Map, const double a, const double b, const double c) { Epetra_CrsMatrix* Matrix = new Epetra_CrsMatrix(Copy, *Map, 3); int NumGlobalElements = Map->NumGlobalElements(); int NumMyElements = Map->NumMyElements(); int* MyGlobalElements = Map->MyGlobalElements(); std::vector<double> Values(2); std::vector<int> Indices(2); int NumEntries; for (int i = 0; i < NumMyElements; ++i) { if (MyGlobalElements[i] == 0) { // off-diagonal for first row Indices[0] = 1; NumEntries = 1; Values[0] = c; } else if (MyGlobalElements[i] == NumGlobalElements - 1) { // off-diagonal for last row Indices[0] = NumGlobalElements - 2; NumEntries = 1; Values[0] = b; } else { // off-diagonal for internal row Indices[0] = MyGlobalElements[i] - 1; Values[1] = b; Indices[1] = MyGlobalElements[i] + 1; Values[0] = c; NumEntries = 2; } Matrix->InsertGlobalValues(MyGlobalElements[i], NumEntries, &Values[0], &Indices[0]); // Put in the diagonal entry Values[0] = a; Matrix->InsertGlobalValues(MyGlobalElements[i], 1, &Values[0], MyGlobalElements + i); } // Finish up, trasforming the matrix entries into local numbering, // to optimize data transfert during matrix-vector products Matrix->FillComplete(); Matrix->OptimizeStorage(); return(Matrix); }
int main(int argc, char *argv[]) { MPI_Init(&argc,&argv); Epetra_MpiComm Comm(MPI_COMM_WORLD); Epetra_MpiComm SerialComm(MPI_COMM_SELF); if (Comm.MyPID() == 0) { ParameterList GaleriList; GaleriList.set("nx", 10); GaleriList.set("ny", 10); GaleriList.set("mx", 1); GaleriList.set("my", 1); Epetra_Map* Map = CreateMap("Cartesian2D", SerialComm, GaleriList); Epetra_CrsMatrix* A = CreateCrsMatrix("Laplace2D", Map, GaleriList); Epetra_Vector LHS(A->OperatorDomainMap()); Epetra_Vector RHS(A->OperatorRangeMap()); LHS.PutScalar(0.0); RHS.Random(); Epetra_LinearProblem problem(A, &LHS, &RHS); AztecOO solver(problem); ParameterList MLList; ML_Epetra::SetDefaults("SA",MLList); MLList.set("ML output", 0); ML_Epetra::MultiLevelPreconditioner* MLPrec = new ML_Epetra::MultiLevelPreconditioner(*A, MLList); solver.SetPrecOperator(MLPrec); solver.SetAztecOption(AZ_solver, AZ_cg_condnum); solver.SetAztecOption(AZ_output, 32); solver.Iterate(500, 1e-12); // destroy the preconditioner delete MLPrec; delete A; delete Map; } MPI_Finalize(); return(0); } // main driver
int powerMethod (double & lambda, Epetra_CrsMatrix& A, const int niters, const double tolerance, const bool verbose) { // In the power iteration, z = A*q. Thus, q must be in the domain // of A, and z must be in the range of A. The residual vector is of // course in the range of A. Epetra_Vector q (A.OperatorDomainMap ()); Epetra_Vector z (A.OperatorRangeMap ()); Epetra_Vector resid (A.OperatorRangeMap ()); Epetra_Flops* counter = A.GetFlopCounter(); if (counter != 0) { q.SetFlopCounter(A); z.SetFlopCounter(A); resid.SetFlopCounter(A); } // Initialize the starting vector z with random data. z.Random(); double normz, residual; int ierr = 1; for (int iter = 0; iter < niters; ++iter) { z.Norm2 (&normz); // normz := ||z||_2 q.Scale (1.0/normz, z); // q := z / normz A.Multiply(false, q, z); // z := A * q q.Dot(z, &lambda); // lambda := dot (q, z) // Compute the residual vector and display status output every // 100 iterations, or if we have reached the maximum number of // iterations. if (iter % 100 == 0 || iter + 1 == niters) { resid.Update (1.0, z, -lambda, q, 0.0); // resid := A*q - lambda*q resid.Norm2 (&residual); // residual := ||resid||_2 if (verbose) cout << "Iter = " << iter << " Lambda = " << lambda << " Residual of A*q - lambda*q = " << residual << endl; } if (residual < tolerance) { // We've converged! ierr = 0; break; } } return ierr; }
void BlockCrsMatrix::TExtractBlock(Epetra_CrsMatrix & BaseMatrix, const int_type Row, const int_type Col) { std::vector<int_type>& RowIndices_ = TRowIndices<int_type>(); std::vector< std::vector<int_type> >& RowStencil_ = TRowStencil<int_type>(); int_type RowOffset = RowIndices_[(std::size_t)Row] * ROffset_; int_type ColOffset = (RowIndices_[(std::size_t)Row] + RowStencil_[(std::size_t)Row][(std::size_t)Col]) * COffset_; // const Epetra_CrsGraph & BaseGraph = BaseMatrix.Graph(); const Epetra_BlockMap & BaseMap = BaseMatrix.RowMatrixRowMap(); //const Epetra_BlockMap & BaseColMap = BaseMatrix.RowMatrixColMap(); // This routine extracts entries of a BaseMatrix from a big BlockCrsMatrix // It performs the following operation on the global IDs row-by-row // BaseMatrix.val[i][j] = this->val[i+rowOffset][j+ColOffset] int MaxIndices = BaseMatrix.MaxNumEntries(); vector<int_type> Indices(MaxIndices); vector<double> Values(MaxIndices); int NumIndices; int_type indx,icol; double* BlkValues; int *BlkIndices; int BlkNumIndices; int ierr=0; (void) ierr; // Forestall compiler warning for unused variable. for (int i=0; i<BaseMap.NumMyElements(); i++) { // Get pointers to values and indices of whole block matrix row int_type BaseRow = (int_type) BaseMap.GID64(i); int myBlkBaseRow = this->RowMatrixRowMap().LID(BaseRow + RowOffset); ierr = this->ExtractMyRowView(myBlkBaseRow, BlkNumIndices, BlkValues, BlkIndices); NumIndices = 0; // Grab columns with global indices in correct range for this block for( int l = 0; l < BlkNumIndices; ++l ) { icol = (int_type) this->RowMatrixColMap().GID64(BlkIndices[l]); indx = icol - ColOffset; if (indx >= 0 && indx < COffset_) { Indices[NumIndices] = indx; Values[NumIndices] = BlkValues[l]; NumIndices++; } } //Load this row into base matrix BaseMatrix.ReplaceGlobalValues(BaseRow, NumIndices, &Values[0], &Indices[0] ); } }
/*----------------------------------------------------------------------* | m.gee 11/05| *----------------------------------------------------------------------*/ bool ML_NOX::Print_Epetra_CrsMatrix(Epetra_CrsMatrix& matrix) { for (int i=0; i<matrix.NumMyRows(); ++i) { printf("Lrow %5d: ",i); fflush(stdout); int numentries; int* indices; double* values; int err = matrix.ExtractMyRowView(i,numentries,values,indices); for (int j=0; j<numentries; ++j) printf("%5d %10.3e ",indices[j],values[j]); printf("\n"); fflush(stdout); } return true; }
// ================================================ ====== ==== ==== == = // Constructor ML_Epetra::ML_RefMaxwell_11_Operator::ML_RefMaxwell_11_Operator(const Epetra_CrsMatrix& SM_Matrix, //S+M const Epetra_CrsMatrix& D0_Matrix, //T or D0 const Epetra_CrsMatrix& M0inv_Matrix, //M0^{-1} const Epetra_CrsMatrix& M1_Matrix): //M1(1) SM_Matrix_(&SM_Matrix),Addon_Matrix_(0),D0T_Matrix_(0) { Label_=new char [80]; strcpy(Label_,"ML_RefMaxwell_11_Operator"); Comm_ = &(SM_Matrix_->Comm()); DomainMap_ = &(SM_Matrix_->OperatorDomainMap()); RangeMap_ = &(SM_Matrix_->OperatorRangeMap()); /* Transpose D0 */ #ifdef MANUALLY_TRANSPOSE_D0 D0_Matrix_Transposer_= new EpetraExt::RowMatrix_Transpose((Epetra_Map*)&M0inv_Matrix.OperatorRangeMap()); D0T_Matrix_= dynamic_cast<Epetra_CrsMatrix*>( & ((*D0_Matrix_Transposer_)((Epetra_CrsMatrix&)D0_Matrix))); D0T_Matrix_= dynamic_cast<Epetra_CrsMatrix*>(ModifyEpetraMatrixColMap(*D0T_Matrix_,D0T_Matrix_Trans_,"D0T",false)); #endif /* Build the Epetra_Multi_CrsMatrix */ Addon_Matrix_=new Epetra_CrsMatrix*[5]; Addon_Matrix_[0]=Addon_Matrix_[4]=(Epetra_CrsMatrix*)&M1_Matrix; Addon_Matrix_[1]=(Epetra_CrsMatrix*)&D0_Matrix; #ifdef MANUALLY_TRANSPOSE_D0 Addon_Matrix_[3]=D0T_Matrix_; #else Addon_Matrix_[3]=(Epetra_CrsMatrix*)&D0_Matrix;//HAQ #endif Addon_Matrix_[2]=(Epetra_CrsMatrix*)&M0inv_Matrix; Addon_=new Epetra_Multi_CrsMatrix(5,Addon_Matrix_); }/*end Constructor*/
// ================================================ ====== ==== ==== == = // Computes C= <me> * A int ML_Epetra::ML_RefMaxwell_11_Operator::MatrixMatrix_Multiply(const Epetra_CrsMatrix & A, Epetra_CrsMatrix **C) const { ML_Comm* comm; ML_Comm_Create(&comm); #ifdef ML_MPI const Epetra_MpiComm *epcomm = dynamic_cast<const Epetra_MpiComm*>(&(A.Comm())); // Get the MPI communicator, as it may not be MPI_COMM_W0RLD, and update the ML comm object if (epcomm) ML_Comm_Set_UsrComm(comm,epcomm->Comm()); #endif ML_Operator *C_; int rv=MatrixMatrix_Multiply(A,comm,&C_); Epetra_CrsMatrix_Wrap_ML_Operator(C_,*Comm_,*DomainMap_,C,Copy,A.IndexBase()); ML_Operator_Destroy(&C_); ML_Comm_Destroy(&comm); return rv; }/*end MatrixMatrix_Multiply*/
// ========================================================================= // ========================================================================= int UnpackAndCombineIntoCrsArrays(const Epetra_CrsMatrix& SourceMatrix, int NumSameIDs, int NumRemoteIDs, const int * RemoteLIDs, int NumPermuteIDs, const int *PermuteToLIDs, const int *PermuteFromLIDs, int LenImports, char* Imports, int TargetNumRows, int TargetNumNonzeros, int * CSR_rowptr, long long * CSR_colind, double * CSR_values, const std::vector<int> &SourcePids, std::vector<int> &TargetPids) { if(SourceMatrix.RowMap().GlobalIndicesLongLong()) { return TUnpackAndCombineIntoCrsArrays<long long>(SourceMatrix,NumSameIDs,NumRemoteIDs,RemoteLIDs,NumPermuteIDs, PermuteToLIDs,PermuteFromLIDs,LenImports,Imports,TargetNumRows,TargetNumNonzeros, CSR_rowptr,CSR_colind,CSR_values,SourcePids,TargetPids); } else throw std::runtime_error("UnpackAndCombineIntoCrsArrays: int type not matched."); }
/** Setup operator */ void Stokhos::AdaptivityManager:: setupOperator(Epetra_CrsMatrix & A,const Sparse3Tensor<int,double> & Cijk,Stokhos::EpetraOperatorOrthogPoly & poly, bool onlyUseLinear,bool includeMean) const { typedef Stokhos::Sparse3Tensor<int,double> Cijk_type; // build the sparse hash only once Sparse3TensorHash hashLookup(Cijk); // Zero out matrix A.PutScalar(0.0); // Compute loop bounds Cijk_type::k_iterator k_begin = Cijk.k_begin(); Cijk_type::k_iterator k_end = Cijk.k_end(); if (!includeMean && index(k_begin) == 0) ++k_begin; if (onlyUseLinear) { int dim = sg_master_basis_->dimension(); k_end = Cijk.find_k(dim+1); } // Assemble matrix // const Teuchos::Array<double>& norms = sg_basis->norm_squared(); for (Cijk_type::k_iterator k_it=k_begin; k_it!=k_end; ++k_it) { int k = index(k_it); Teuchos::RCP<Epetra_CrsMatrix> block = Teuchos::rcp_dynamic_cast<Epetra_CrsMatrix>(poly.getCoeffPtr(k), true); // add in matrix k sumInOperator(A,hashLookup,k,*block); } }
void BlockCrsMatrix::ExtractBlock(Epetra_CrsMatrix & BaseMatrix, const int Row, const int Col) { if(Epetra_CrsMatrix::RowMatrixRowMap().GlobalIndicesInt() && BaseMatrix.RowMatrixRowMap().GlobalIndicesInt()) return TExtractBlock<int>(BaseMatrix, Row, Col); else throw "EpetraExt::BlockCrsMatrix::ExtractBlock: Global indices not int"; }
void BlockCrsMatrix::ExtractBlock(Epetra_CrsMatrix & BaseMatrix, const long long Row, const long long Col) { if(Epetra_CrsMatrix::RowMatrixRowMap().GlobalIndicesLongLong() && BaseMatrix.RowMatrixRowMap().GlobalIndicesLongLong()) return TExtractBlock<long long>(BaseMatrix, Row, Col); else throw "EpetraExt::BlockCrsMatrix::ExtractBlock: Global indices not long long"; }
int power_method(bool TransA, Epetra_CrsMatrix& A, Epetra_Vector& q, Epetra_Vector& z, Epetra_Vector& resid, double* lambda, int niters, double tolerance, bool verbose) { // Fill z with random Numbers z.Random(); // variable needed for iteration double normz, residual; int ierr = 1; for(int iter = 0; iter < niters; iter++) { z.Norm2(&normz); // Compute 2-norm of z q.Scale(1.0/normz, z); A.Multiply(TransA, q, z); // Compute z = A*q // SEGFAULT HAPPENS HERE q.Dot(z, lambda); // Approximate maximum eigenvaluE if(iter%100==0 || iter+1==niters) { resid.Update(1.0, z, -(*lambda), q, 0.0); // Compute A*q - lambda*q resid.Norm2(&residual); if(verbose) cout << "Iter = " << iter << " Lambda = " << *lambda << " Residual of A*q - lambda*q = " << residual << endl; } if(residual < tolerance) { ierr = 0; break; } } return(ierr); }