int main(int argc,char **args) { Mat A,B; PetscErrorCode ierr; char file[PETSC_MAX_PATH_LEN]; PetscBool flg; PetscViewer fd; MatType type = MATMPIBAIJ; PetscInitialize(&argc,&args,(char*)0,help); ierr = PetscOptionsHasName(NULL,"-aij",&flg);CHKERRQ(ierr); if (flg) type = MATMPIAIJ; ierr = PetscOptionsGetString(NULL,"-f",file,PETSC_MAX_PATH_LEN,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_WORLD,1,"Must indicate binary file with the -f option"); /* Open binary file. Note that we use FILE_MODE_READ to indicate reading from this file. */ ierr = PetscViewerBinaryOpen(PETSC_COMM_WORLD,file,FILE_MODE_READ,&fd);CHKERRQ(ierr); /* Load the matrix; then destroy the viewer. */ ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetType(A,type);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatLoad(A,fd);CHKERRQ(ierr); ierr = PetscViewerDestroy(&fd);CHKERRQ(ierr); /* Open another binary file. Note that we use FILE_MODE_WRITE to indicate reading from this file. */ ierr = PetscViewerBinaryOpen(PETSC_COMM_WORLD,"fileoutput",FILE_MODE_WRITE,&fd);CHKERRQ(ierr); ierr = PetscViewerBinarySetFlowControl(fd,3);CHKERRQ(ierr); /* Save the matrix and vector; then destroy the viewer. */ ierr = MatView(A,fd);CHKERRQ(ierr); ierr = PetscViewerDestroy(&fd);CHKERRQ(ierr); /* load the new matrix */ ierr = PetscViewerBinaryOpen(PETSC_COMM_WORLD,"fileoutput",FILE_MODE_READ,&fd);CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&B);CHKERRQ(ierr); ierr = MatSetType(B,type);CHKERRQ(ierr); ierr = MatSetFromOptions(B);CHKERRQ(ierr); ierr = MatLoad(B,fd);CHKERRQ(ierr); ierr = PetscViewerDestroy(&fd);CHKERRQ(ierr); ierr = MatEqual(A,B,&flg);CHKERRQ(ierr); if (flg) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Matrices are equal\n");CHKERRQ(ierr); } else { ierr = PetscPrintf(PETSC_COMM_WORLD,"Matrices are not equal\n");CHKERRQ(ierr); } ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
int main(int argc,char **args) { Mat C,Caij; PetscInt i,j,m = 5,n,nrows,ncols; const PetscInt *rows,*cols; IS isrows,iscols; PetscErrorCode ierr; PetscBool flg,Test_MatMatMult=PETSC_FALSE,mats_view=PETSC_FALSE; PetscScalar *v; PetscMPIInt rank,size; PetscInitialize(&argc,&args,(char *)0,help); ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); ierr = PetscOptionsHasName(PETSC_NULL,"-mats_view",&mats_view);CHKERRQ(ierr); // Get local block or element size ierr = PetscOptionsGetInt(PETSC_NULL,"-m",&m,PETSC_NULL);CHKERRQ(ierr); n = m; ierr = PetscOptionsGetInt(PETSC_NULL,"-n",&n,PETSC_NULL);CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&C);CHKERRQ(ierr); ierr = MatSetSizes(C,m,n,PETSC_DECIDE,PETSC_DECIDE);CHKERRQ(ierr); ierr = MatSetType(C,MATELEMENTAL);CHKERRQ(ierr); ierr = MatSetFromOptions(C);CHKERRQ(ierr); ierr = MatSetUp(C);CHKERRQ(ierr); ierr = PetscOptionsHasName(PETSC_NULL,"-row_oriented",&flg);CHKERRQ(ierr); if (flg) {ierr = MatSetOption(C,MAT_ROW_ORIENTED,PETSC_TRUE);CHKERRQ(ierr);} ierr = MatGetOwnershipIS(C,&isrows,&iscols);CHKERRQ(ierr); ierr = PetscOptionsHasName(PETSC_NULL,"-Cexp_view_ownership",&flg);CHKERRQ(ierr); if (flg) { // View ownership of explicit C IS tmp; ierr = PetscPrintf(PETSC_COMM_WORLD,"Ownership of explicit C:\n");CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row index set:\n");CHKERRQ(ierr); ierr = ISOnComm(isrows,PETSC_COMM_WORLD,PETSC_USE_POINTER,&tmp);CHKERRQ(ierr); ierr = ISView(tmp,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = ISDestroy(&tmp);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Column index set:\n");CHKERRQ(ierr); ierr = ISOnComm(iscols,PETSC_COMM_WORLD,PETSC_USE_POINTER,&tmp);CHKERRQ(ierr); ierr = ISView(tmp,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = ISDestroy(&tmp);CHKERRQ(ierr); } // Set local matrix entries ierr = ISGetLocalSize(isrows,&nrows);CHKERRQ(ierr); ierr = ISGetIndices(isrows,&rows);CHKERRQ(ierr); ierr = ISGetLocalSize(iscols,&ncols);CHKERRQ(ierr); ierr = ISGetIndices(iscols,&cols);CHKERRQ(ierr); ierr = PetscMalloc(nrows*ncols*sizeof(*v),&v);CHKERRQ(ierr); for (i=0; i<nrows; i++) { for (j=0; j<ncols; j++) { //v[i*ncols+j] = (PetscReal)(rank); v[i*ncols+j] = (PetscReal)(rank*10000+100*rows[i]+cols[j]); } } ierr = MatSetValues(C,nrows,rows,ncols,cols,v,INSERT_VALUES);CHKERRQ(ierr); ierr = ISRestoreIndices(isrows,&rows);CHKERRQ(ierr); ierr = ISRestoreIndices(iscols,&cols);CHKERRQ(ierr); ierr = MatAssemblyBegin(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); // Test MatView() if (mats_view){ ierr = MatView(C,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } // Set unowned matrix entries - add subdiagonals and diagonals from proc[0] if (rank == 0) { PetscInt M,N,cols[2]; ierr = MatGetSize(C,&M,&N);CHKERRQ(ierr); for (i=0; i<M; i++){ cols[0] = i; v[0] = i + 0.5; cols[1] = i-1; v[1] = 0.5; if (i) { ierr = MatSetValues(C,1,&i,2,cols,v,ADD_VALUES);CHKERRQ(ierr); } else { ierr = MatSetValues(C,1,&i,1,&i,v,ADD_VALUES);CHKERRQ(ierr); } } } ierr = MatAssemblyBegin(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); // Test MatMult() ierr = MatComputeExplicitOperator(C,&Caij);CHKERRQ(ierr); ierr = MatMultEqual(C,Caij,5,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_NOTSAMETYPE,"C != Caij. MatMultEqual() fails"); ierr = MatMultTransposeEqual(C,Caij,5,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_NOTSAMETYPE,"C != Caij. MatMultTransposeEqual() fails"); // Test MatMultAdd() and MatMultTransposeAddEqual() ierr = MatMultAddEqual(C,Caij,5,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_NOTSAMETYPE,"C != Caij. MatMultAddEqual() fails"); ierr = MatMultTransposeAddEqual(C,Caij,5,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_NOTSAMETYPE,"C != Caij. MatMultTransposeAddEqual() fails"); // Test MatMatMult() ierr = PetscOptionsHasName(PETSC_NULL,"-test_matmatmult",&Test_MatMatMult);CHKERRQ(ierr); if (Test_MatMatMult){ Mat CCelem,CCaij; ierr = MatMatMult(C,C,MAT_INITIAL_MATRIX,PETSC_DEFAULT,&CCelem);CHKERRQ(ierr); ierr = MatMatMult(Caij,Caij,MAT_INITIAL_MATRIX,PETSC_DEFAULT,&CCaij);CHKERRQ(ierr); ierr = MatMultEqual(CCelem,CCaij,5,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_NOTSAMETYPE,"CCelem != CCaij. MatMatMult() fails"); ierr = MatDestroy(&CCaij);CHKERRQ(ierr); ierr = MatDestroy(&CCelem);CHKERRQ(ierr); } ierr = PetscFree(v);CHKERRQ(ierr); ierr = ISDestroy(&isrows);CHKERRQ(ierr); ierr = ISDestroy(&iscols);CHKERRQ(ierr); ierr = MatDestroy(&C);CHKERRQ(ierr); ierr = MatDestroy(&Caij);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
PetscErrorCode test1_DAInjection3d(PetscInt mx, PetscInt my, PetscInt mz) { PetscErrorCode ierr; DM dac,daf; PetscViewer vv; Vec ac,af; PetscInt periodicity; DMBoundaryType bx,by,bz; PetscFunctionBeginUser; bx = DM_BOUNDARY_NONE; by = DM_BOUNDARY_NONE; bz = DM_BOUNDARY_NONE; periodicity = 0; ierr = PetscOptionsGetInt(NULL,"-periodic", &periodicity, NULL);CHKERRQ(ierr); if (periodicity==1) { bx = DM_BOUNDARY_PERIODIC; } else if (periodicity==2) { by = DM_BOUNDARY_PERIODIC; } else if (periodicity==3) { bz = DM_BOUNDARY_PERIODIC; } ierr = DMDACreate3d(PETSC_COMM_WORLD, bx,by,bz, DMDA_STENCIL_BOX, mx+1, my+1,mz+1, PETSC_DECIDE, PETSC_DECIDE,PETSC_DECIDE, 1, /* 1 dof */ 1, /* stencil = 1 */ NULL,NULL,NULL, &daf);CHKERRQ(ierr); ierr = DMSetFromOptions(daf);CHKERRQ(ierr); ierr = DMCoarsen(daf,MPI_COMM_NULL,&dac);CHKERRQ(ierr); ierr = DMDASetUniformCoordinates(dac, -1.0,1.0, -1.0,1.0, -1.0,1.0);CHKERRQ(ierr); ierr = DMDASetUniformCoordinates(daf, -1.0,1.0, -1.0,1.0, -1.0,1.0);CHKERRQ(ierr); { DM cdaf,cdac; Vec coordsc,coordsf,coordsf2; VecScatter inject; Mat interp; PetscReal norm; ierr = DMGetCoordinateDM(dac,&cdac);CHKERRQ(ierr); ierr = DMGetCoordinateDM(daf,&cdaf);CHKERRQ(ierr); ierr = DMGetCoordinates(dac,&coordsc);CHKERRQ(ierr); ierr = DMGetCoordinates(daf,&coordsf);CHKERRQ(ierr); ierr = DMCreateInjection(cdac,cdaf,&inject);CHKERRQ(ierr); ierr = VecScatterBegin(inject,coordsf,coordsc,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); ierr = VecScatterEnd(inject ,coordsf,coordsc,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); ierr = VecScatterDestroy(&inject);CHKERRQ(ierr); ierr = DMCreateInterpolation(cdac,cdaf,&interp,NULL);CHKERRQ(ierr); ierr = VecDuplicate(coordsf,&coordsf2);CHKERRQ(ierr); ierr = MatInterpolate(interp,coordsc,coordsf2);CHKERRQ(ierr); ierr = VecAXPY(coordsf2,-1.0,coordsf);CHKERRQ(ierr); ierr = VecNorm(coordsf2,NORM_MAX,&norm);CHKERRQ(ierr); /* The fine coordinates are only reproduced in certain cases */ if (!bx && !by && !bz && norm > 1.e-10) {ierr = PetscPrintf(PETSC_COMM_WORLD,"Norm %g\n",(double)norm);CHKERRQ(ierr);} ierr = VecDestroy(&coordsf2);CHKERRQ(ierr); ierr = MatDestroy(&interp);CHKERRQ(ierr); } if (0) { ierr = DMCreateGlobalVector(dac,&ac);CHKERRQ(ierr); ierr = VecZeroEntries(ac);CHKERRQ(ierr); ierr = DMCreateGlobalVector(daf,&af);CHKERRQ(ierr); ierr = VecZeroEntries(af);CHKERRQ(ierr); ierr = PetscViewerASCIIOpen(PETSC_COMM_WORLD, "dac_7.vtk", &vv);CHKERRQ(ierr); ierr = PetscViewerSetFormat(vv, PETSC_VIEWER_ASCII_VTK);CHKERRQ(ierr); ierr = DMView(dac, vv);CHKERRQ(ierr); ierr = VecView(ac, vv);CHKERRQ(ierr); ierr = PetscViewerDestroy(&vv);CHKERRQ(ierr); ierr = PetscViewerASCIIOpen(PETSC_COMM_WORLD, "daf_7.vtk", &vv);CHKERRQ(ierr); ierr = PetscViewerSetFormat(vv, PETSC_VIEWER_ASCII_VTK);CHKERRQ(ierr); ierr = DMView(daf, vv);CHKERRQ(ierr); ierr = VecView(af, vv);CHKERRQ(ierr); ierr = PetscViewerDestroy(&vv);CHKERRQ(ierr); ierr = VecDestroy(&ac);CHKERRQ(ierr); ierr = VecDestroy(&af);CHKERRQ(ierr); } ierr = DMDestroy(&dac);CHKERRQ(ierr); ierr = DMDestroy(&daf);CHKERRQ(ierr); PetscFunctionReturn(0); }
PetscErrorCode port_lsd_bfbt(void) { Mat A; Vec x,b; KSP ksp_A; PC pc_A; IS isu,isp; PetscErrorCode ierr; PetscFunctionBeginUser; ierr = LoadTestMatrices(&A,&x,&b,&isu,&isp);CHKERRQ(ierr); ierr = KSPCreate(PETSC_COMM_WORLD,&ksp_A);CHKERRQ(ierr); ierr = KSPSetOptionsPrefix(ksp_A,"fc_");CHKERRQ(ierr); ierr = KSPSetOperators(ksp_A,A,A);CHKERRQ(ierr); ierr = KSPGetPC(ksp_A,&pc_A);CHKERRQ(ierr); ierr = PCSetType(pc_A,PCFIELDSPLIT);CHKERRQ(ierr); ierr = PCFieldSplitSetBlockSize(pc_A,2);CHKERRQ(ierr); ierr = PCFieldSplitSetIS(pc_A,"velocity",isu);CHKERRQ(ierr); ierr = PCFieldSplitSetIS(pc_A,"pressure",isp);CHKERRQ(ierr); ierr = KSPSetFromOptions(ksp_A);CHKERRQ(ierr); ierr = KSPSolve(ksp_A,b,x);CHKERRQ(ierr); /* Pull u,p out of x */ { PetscInt loc; PetscReal max,norm; PetscScalar sum; Vec uvec,pvec; VecScatter uscat,pscat; Mat A11,A22; /* grab matrices and create the compatable u,p vectors */ ierr = MatCreateSubMatrix(A,isu,isu,MAT_INITIAL_MATRIX,&A11);CHKERRQ(ierr); ierr = MatCreateSubMatrix(A,isp,isp,MAT_INITIAL_MATRIX,&A22);CHKERRQ(ierr); ierr = MatCreateVecs(A11,&uvec,NULL);CHKERRQ(ierr); ierr = MatCreateVecs(A22,&pvec,NULL);CHKERRQ(ierr); /* perform the scatter from x -> (u,p) */ ierr = VecScatterCreateWithData(x,isu,uvec,NULL,&uscat);CHKERRQ(ierr); ierr = VecScatterBegin(uscat,x,uvec,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); ierr = VecScatterEnd(uscat,x,uvec,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); ierr = VecScatterCreateWithData(x,isp,pvec,NULL,&pscat);CHKERRQ(ierr); ierr = VecScatterBegin(pscat,x,pvec,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); ierr = VecScatterEnd(pscat,x,pvec,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); PetscPrintf(PETSC_COMM_WORLD,"-- vector vector values --\n"); ierr = VecMin(uvec,&loc,&max);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Min(u) = %1.6f [loc=%D]\n",(double)max,loc);CHKERRQ(ierr); ierr = VecMax(uvec,&loc,&max);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Max(u) = %1.6f [loc=%D]\n",(double)max,loc);CHKERRQ(ierr); ierr = VecNorm(uvec,NORM_2,&norm);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Norm(u) = %1.6f \n",(double)norm);CHKERRQ(ierr); ierr = VecSum(uvec,&sum);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Sum(u) = %1.6f \n",(double)PetscRealPart(sum));CHKERRQ(ierr); PetscPrintf(PETSC_COMM_WORLD,"-- pressure vector values --\n"); ierr = VecMin(pvec,&loc,&max);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Min(p) = %1.6f [loc=%D]\n",(double)max,loc);CHKERRQ(ierr); ierr = VecMax(pvec,&loc,&max);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Max(p) = %1.6f [loc=%D]\n",(double)max,loc);CHKERRQ(ierr); ierr = VecNorm(pvec,NORM_2,&norm);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Norm(p) = %1.6f \n",(double)norm);CHKERRQ(ierr); ierr = VecSum(pvec,&sum);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Sum(p) = %1.6f \n",(double)PetscRealPart(sum));CHKERRQ(ierr); PetscPrintf(PETSC_COMM_WORLD,"-- Full vector values --\n"); ierr = VecMin(x,&loc,&max);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Min(u,p) = %1.6f [loc=%D]\n",(double)max,loc);CHKERRQ(ierr); ierr = VecMax(x,&loc,&max);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Max(u,p) = %1.6f [loc=%D]\n",(double)max,loc);CHKERRQ(ierr); ierr = VecNorm(x,NORM_2,&norm);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Norm(u,p) = %1.6f \n",(double)norm);CHKERRQ(ierr); ierr = VecSum(x,&sum);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD," Sum(u,p) = %1.6f \n",(double)PetscRealPart(sum));CHKERRQ(ierr); ierr = VecScatterDestroy(&uscat);CHKERRQ(ierr); ierr = VecScatterDestroy(&pscat);CHKERRQ(ierr); ierr = VecDestroy(&uvec);CHKERRQ(ierr); ierr = VecDestroy(&pvec);CHKERRQ(ierr); ierr = MatDestroy(&A11);CHKERRQ(ierr); ierr = MatDestroy(&A22);CHKERRQ(ierr); } ierr = KSPDestroy(&ksp_A);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr); ierr = ISDestroy(&isu);CHKERRQ(ierr); ierr = ISDestroy(&isp);CHKERRQ(ierr); PetscFunctionReturn(0); }
int main(int argc,char **args) { Mat A, *S; IS rowis[2], colis[2]; PetscInt n,N,i,j,k,l,nsub,Jlow[2] = {0,1}, *jlow, Jhigh[2] = {3,4}, *jhigh, row, col, *subindices, ncols; const PetscInt *cols; PetscScalar v; PetscMPIInt rank, size, p, inversions, total_inversions; PetscBool sort_rows, sort_cols, show_inversions; PetscErrorCode ierr; ierr = PetscInitialize(&argc,&args,(char*)0,help);if (ierr) return ierr; ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); if (size>2) SETERRQ(PETSC_COMM_WORLD,PETSC_ERR_ARG_WRONG, "A uniprocessor or two-processor example only.\n"); ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); if (size > 1) { n = 8; N = 16; } else { n = 16; N = 16; } ierr = MatSetSizes(A,n,n,N,N);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatSetUp(A);CHKERRQ(ierr); /* Don't care if the entries are set multiple times by different procs. */ for (i=0; i<4; ++i) { for (j = 0; j<4; ++j) { row = j*4+i; v = -1.0; if (i>0) { col = row-1; ierr = MatSetValues(A,1,&row,1,&col,&v,INSERT_VALUES);CHKERRQ(ierr); } if (i<3) { col = row+1; ierr = MatSetValues(A,1,&row,1,&col,&v,INSERT_VALUES);CHKERRQ(ierr); } if (j>0) { col = row-4; ierr = MatSetValues(A,1,&row,1,&col,&v,INSERT_VALUES);CHKERRQ(ierr); } if (j<3) { col = row+4; ierr = MatSetValues(A,1,&row,1,&col,&v,INSERT_VALUES);CHKERRQ(ierr); } v = 4.0; ierr = MatSetValues(A,1,&row,1,&row,&v,INSERT_VALUES);CHKERRQ(ierr); } } ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD, "Original matrix\n");CHKERRQ(ierr); ierr = MatView(A,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); if (size > 1) { nsub = 1; /* one subdomain per rank */ } else { nsub = 2; /* both subdomains on rank 0 */ } if (rank) { jlow = Jlow+1; jhigh = Jhigh+1; } else { jlow = Jlow; jhigh = Jhigh; } sort_rows = PETSC_FALSE; ierr = PetscOptionsGetBool(NULL,NULL, "-sort_rows", &sort_rows, NULL);CHKERRQ(ierr); sort_cols = PETSC_FALSE; ierr = PetscOptionsGetBool(NULL,NULL, "-sort_cols", &sort_cols, NULL);CHKERRQ(ierr); for (l = 0; l < nsub; ++l) { ierr = PetscMalloc1(12, &subindices);CHKERRQ(ierr); k = 0; for (i = 0; i < 4; ++i) { for (j = jlow[l]; j < jhigh[l]; ++j) { subindices[k] = j*4+i; k++; } } ierr = ISCreateGeneral(PETSC_COMM_SELF, 12, subindices, PETSC_OWN_POINTER, rowis+l);CHKERRQ(ierr); if ((sort_rows && !sort_cols) || (!sort_rows && sort_cols)) { ierr = ISDuplicate(rowis[l],colis+l);CHKERRQ(ierr); } else { ierr = PetscObjectReference((PetscObject)rowis[l]);CHKERRQ(ierr); colis[l] = rowis[l]; } if (sort_rows) { ierr = ISSort(rowis[l]);CHKERRQ(ierr); } if (sort_cols) { ierr = ISSort(colis[l]);CHKERRQ(ierr); } } ierr = PetscMalloc1(nsub, &S);CHKERRQ(ierr); ierr = MatGetSubMatrices(A,nsub,rowis,colis,MAT_INITIAL_MATRIX, &S);CHKERRQ(ierr); show_inversions = PETSC_FALSE; ierr = PetscOptionsGetBool(NULL,NULL, "-show_inversions", &show_inversions, NULL);CHKERRQ(ierr); inversions = 0; for (p = 0; p < size; ++p) { if (p == rank) { ierr = PetscPrintf(PETSC_COMM_SELF, "[%D:%D]: Number of subdomains: %D:\n", rank, size, nsub);CHKERRQ(ierr); for (l = 0; l < nsub; ++l) { PetscInt i0, i1; ierr = PetscPrintf(PETSC_COMM_SELF, "[%D:%D]: Subdomain row IS %D:\n", rank, size, l);CHKERRQ(ierr); ierr = ISView(rowis[l],PETSC_VIEWER_STDOUT_SELF);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_SELF, "[%D:%D]: Subdomain col IS %D:\n", rank, size, l);CHKERRQ(ierr); ierr = ISView(colis[l],PETSC_VIEWER_STDOUT_SELF);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_SELF, "[%D:%D]: Submatrix %D:\n", rank, size, l);CHKERRQ(ierr); ierr = MatView(S[l],PETSC_VIEWER_STDOUT_SELF);CHKERRQ(ierr); if (show_inversions) { ierr = MatGetOwnershipRange(S[l], &i0,&i1);CHKERRQ(ierr); for (i = i0; i < i1; ++i) { ierr = MatGetRow(S[l], i, &ncols, &cols, NULL);CHKERRQ(ierr); for (j = 1; j < ncols; ++j) { if (cols[j] < cols[j-1]) { ierr = PetscPrintf(PETSC_COMM_SELF, "***Inversion in row %D: col[%D] = %D < %D = col[%D]\n", i, j, cols[j], cols[j-1], j-1);CHKERRQ(ierr); inversions++; } } ierr = MatRestoreRow(S[l], i, &ncols, &cols, NULL);CHKERRQ(ierr); } } } } ierr = MPI_Barrier(PETSC_COMM_WORLD);CHKERRQ(ierr); } if (show_inversions) { ierr = MPI_Reduce(&inversions,&total_inversions,1,MPIU_INT, MPI_SUM,0,PETSC_COMM_WORLD);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD, "*Total inversions: %D\n", total_inversions);CHKERRQ(ierr); } ierr = MatDestroy(&A);CHKERRQ(ierr); for (l = 0; l < nsub; ++l) { ierr = MatDestroy(&(S[l]));CHKERRQ(ierr); ierr = ISDestroy(&(rowis[l]));CHKERRQ(ierr); ierr = ISDestroy(&(colis[l]));CHKERRQ(ierr); } ierr = PetscFree(S);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
PetscErrorCode DMCoarsen_Plex(DM dm, MPI_Comm comm, DM *dmCoarsened) { DM_Plex *mesh = (DM_Plex*) dm->data; #ifdef PETSC_HAVE_PRAGMATIC DM udm, coordDM; DMLabel bd; Mat A; Vec coordinates, mb, mx; PetscSection coordSection; const PetscScalar *coords; double *coarseCoords; IS bdIS; PetscReal *x, *y, *z, *eqns, *metric; PetscReal coarseRatio = PetscSqr(0.5); const PetscInt *faces; PetscInt *cells, *bdFaces, *bdFaceIds; PetscInt dim, numCorners, cStart, cEnd, numCells, numCoarseCells, c, vStart, vEnd, numVertices, numCoarseVertices, v, numBdFaces, f, maxConeSize, size, bdSize, coff; #endif PetscErrorCode ierr; PetscFunctionBegin; #ifdef PETSC_HAVE_PRAGMATIC if (!mesh->coarseMesh) { ierr = DMGetDimension(dm, &dim);CHKERRQ(ierr); ierr = DMGetCoordinateDM(dm, &coordDM);CHKERRQ(ierr); ierr = DMGetDefaultSection(coordDM, &coordSection);CHKERRQ(ierr); ierr = DMGetCoordinatesLocal(dm, &coordinates);CHKERRQ(ierr); ierr = DMPlexGetHeightStratum(dm, 0, &cStart, &cEnd);CHKERRQ(ierr); ierr = DMPlexGetDepthStratum(dm, 0, &vStart, &vEnd);CHKERRQ(ierr); ierr = DMPlexUninterpolate(dm, &udm);CHKERRQ(ierr); ierr = DMPlexGetMaxSizes(udm, &maxConeSize, NULL);CHKERRQ(ierr); numCells = cEnd - cStart; numVertices = vEnd - vStart; ierr = PetscCalloc5(numVertices, &x, numVertices, &y, numVertices, &z, numVertices*PetscSqr(dim), &metric, numCells*maxConeSize, &cells);CHKERRQ(ierr); ierr = VecGetArrayRead(coordinates, &coords);CHKERRQ(ierr); for (v = vStart; v < vEnd; ++v) { PetscInt off; ierr = PetscSectionGetOffset(coordSection, v, &off);CHKERRQ(ierr); x[v-vStart] = coords[off+0]; y[v-vStart] = coords[off+1]; if (dim > 2) z[v-vStart] = coords[off+2]; } ierr = VecRestoreArrayRead(coordinates, &coords);CHKERRQ(ierr); for (c = 0, coff = 0; c < numCells; ++c) { const PetscInt *cone; PetscInt coneSize, cl; ierr = DMPlexGetConeSize(udm, c, &coneSize);CHKERRQ(ierr); ierr = DMPlexGetCone(udm, c, &cone);CHKERRQ(ierr); for (cl = 0; cl < coneSize; ++cl) cells[coff++] = cone[cl] - vStart; } switch (dim) { case 2: pragmatic_2d_init(&numVertices, &numCells, cells, x, y); break; case 3: pragmatic_3d_init(&numVertices, &numCells, cells, x, y, z); break; default: SETERRQ1(PetscObjectComm((PetscObject) dm), PETSC_ERR_ARG_OUTOFRANGE, "No Pragmatic coarsening defined for dimension %d", dim); } /* Create boundary mesh */ ierr = DMLabelCreate("boundary", &bd);CHKERRQ(ierr); ierr = DMPlexMarkBoundaryFaces(dm, bd);CHKERRQ(ierr); ierr = DMLabelGetStratumIS(bd, 1, &bdIS);CHKERRQ(ierr); ierr = DMLabelGetStratumSize(bd, 1, &numBdFaces);CHKERRQ(ierr); ierr = ISGetIndices(bdIS, &faces);CHKERRQ(ierr); for (f = 0, bdSize = 0; f < numBdFaces; ++f) { PetscInt *closure = NULL; PetscInt closureSize, cl; ierr = DMPlexGetTransitiveClosure(dm, faces[f], PETSC_TRUE, &closureSize, &closure);CHKERRQ(ierr); for (cl = 0; cl < closureSize*2; cl += 2) { if ((closure[cl] >= vStart) && (closure[cl] < vEnd)) ++bdSize; } ierr = DMPlexRestoreTransitiveClosure(dm, f, PETSC_TRUE, &closureSize, &closure);CHKERRQ(ierr); } ierr = PetscMalloc2(bdSize, &bdFaces, numBdFaces, &bdFaceIds);CHKERRQ(ierr); for (f = 0, bdSize = 0; f < numBdFaces; ++f) { PetscInt *closure = NULL; PetscInt closureSize, cl; ierr = DMPlexGetTransitiveClosure(dm, faces[f], PETSC_TRUE, &closureSize, &closure);CHKERRQ(ierr); for (cl = 0; cl < closureSize*2; cl += 2) { if ((closure[cl] >= vStart) && (closure[cl] < vEnd)) bdFaces[bdSize++] = closure[cl] - vStart; } /* TODO Fix */ bdFaceIds[f] = 1; ierr = DMPlexRestoreTransitiveClosure(dm, f, PETSC_TRUE, &closureSize, &closure);CHKERRQ(ierr); } ierr = ISDestroy(&bdIS);CHKERRQ(ierr); ierr = DMLabelDestroy(&bd);CHKERRQ(ierr); pragmatic_set_boundary(&numBdFaces, bdFaces, bdFaceIds); /* Create metric */ size = (dim*(dim+1))/2; ierr = PetscMalloc1(PetscSqr(size), &eqns);CHKERRQ(ierr); ierr = MatCreateSeqDense(PETSC_COMM_SELF, size, size, eqns, &A);CHKERRQ(ierr); ierr = MatCreateVecs(A, &mx, &mb);CHKERRQ(ierr); ierr = VecSet(mb, 1.0);CHKERRQ(ierr); for (c = 0; c < numCells; ++c) { const PetscScalar *sol; PetscScalar *cellCoords = NULL; PetscReal e[3], vol; const PetscInt *cone; PetscInt coneSize, cl, i, j, d, r; ierr = DMPlexVecGetClosure(dm, coordSection, coordinates, c, NULL, &cellCoords);CHKERRQ(ierr); /* Only works for simplices */ for (i = 0, r = 0; i < dim+1; ++i) { for (j = 0; j < i; ++j, ++r) { for (d = 0; d < dim; ++d) e[d] = cellCoords[i*dim+d] - cellCoords[j*dim+d]; /* FORTRAN ORDERING */ if (dim == 2) { eqns[0*size+r] = PetscSqr(e[0]); eqns[1*size+r] = 2.0*e[0]*e[1]; eqns[2*size+r] = PetscSqr(e[1]); } else { eqns[0*size+r] = PetscSqr(e[0]); eqns[1*size+r] = 2.0*e[0]*e[1]; eqns[2*size+r] = 2.0*e[0]*e[2]; eqns[3*size+r] = PetscSqr(e[1]); eqns[4*size+r] = 2.0*e[1]*e[2]; eqns[5*size+r] = PetscSqr(e[2]); } } } ierr = MatSetUnfactored(A);CHKERRQ(ierr); ierr = DMPlexVecRestoreClosure(dm, coordSection, coordinates, c, NULL, &cellCoords);CHKERRQ(ierr); ierr = MatLUFactor(A, NULL, NULL, NULL);CHKERRQ(ierr); ierr = MatSolve(A, mb, mx);CHKERRQ(ierr); ierr = VecGetArrayRead(mx, &sol);CHKERRQ(ierr); ierr = DMPlexComputeCellGeometryFVM(dm, c, &vol, NULL, NULL);CHKERRQ(ierr); ierr = DMPlexGetCone(udm, c, &cone);CHKERRQ(ierr); ierr = DMPlexGetConeSize(udm, c, &coneSize);CHKERRQ(ierr); for (cl = 0; cl < coneSize; ++cl) { const PetscInt v = cone[cl] - vStart; if (dim == 2) { metric[v*4+0] += vol*coarseRatio*sol[0]; metric[v*4+1] += vol*coarseRatio*sol[1]; metric[v*4+2] += vol*coarseRatio*sol[1]; metric[v*4+3] += vol*coarseRatio*sol[2]; } else { metric[v*9+0] += vol*coarseRatio*sol[0]; metric[v*9+1] += vol*coarseRatio*sol[1]; metric[v*9+3] += vol*coarseRatio*sol[1]; metric[v*9+2] += vol*coarseRatio*sol[2]; metric[v*9+6] += vol*coarseRatio*sol[2]; metric[v*9+4] += vol*coarseRatio*sol[3]; metric[v*9+5] += vol*coarseRatio*sol[4]; metric[v*9+7] += vol*coarseRatio*sol[4]; metric[v*9+8] += vol*coarseRatio*sol[5]; } } ierr = VecRestoreArrayRead(mx, &sol);CHKERRQ(ierr); } for (v = 0; v < numVertices; ++v) { const PetscInt *support; PetscInt supportSize, s; PetscReal vol, totVol = 0.0; ierr = DMPlexGetSupport(udm, v+vStart, &support);CHKERRQ(ierr); ierr = DMPlexGetSupportSize(udm, v+vStart, &supportSize);CHKERRQ(ierr); for (s = 0; s < supportSize; ++s) {ierr = DMPlexComputeCellGeometryFVM(dm, support[s], &vol, NULL, NULL);CHKERRQ(ierr); totVol += vol;} for (s = 0; s < PetscSqr(dim); ++s) metric[v*PetscSqr(dim)+s] /= totVol; } ierr = VecDestroy(&mx);CHKERRQ(ierr); ierr = VecDestroy(&mb);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = DMDestroy(&udm);CHKERRQ(ierr); ierr = PetscFree(eqns);CHKERRQ(ierr); pragmatic_set_metric(metric); pragmatic_adapt(); /* Read out mesh */ pragmatic_get_info(&numCoarseVertices, &numCoarseCells); ierr = PetscMalloc1(numCoarseVertices*dim, &coarseCoords);CHKERRQ(ierr); switch (dim) { case 2: pragmatic_get_coords_2d(x, y); numCorners = 3; for (v = 0; v < numCoarseVertices; ++v) {coarseCoords[v*2+0] = x[v]; coarseCoords[v*2+1] = y[v];} break; case 3: pragmatic_get_coords_3d(x, y, z); numCorners = 4; for (v = 0; v < numCoarseVertices; ++v) {coarseCoords[v*3+0] = x[v]; coarseCoords[v*3+1] = y[v]; coarseCoords[v*3+2] = z[v];} break; default: SETERRQ1(PetscObjectComm((PetscObject) dm), PETSC_ERR_ARG_OUTOFRANGE, "No Pragmatic coarsening defined for dimension %d", dim); } pragmatic_get_elements(cells); /* TODO Read out markers for boundary */ ierr = DMPlexCreateFromCellList(PetscObjectComm((PetscObject) dm), dim, numCoarseCells, numCoarseVertices, numCorners, PETSC_TRUE, cells, dim, coarseCoords, &mesh->coarseMesh);CHKERRQ(ierr); pragmatic_finalize(); ierr = PetscFree5(x, y, z, metric, cells);CHKERRQ(ierr); ierr = PetscFree2(bdFaces, bdFaceIds);CHKERRQ(ierr); ierr = PetscFree(coarseCoords);CHKERRQ(ierr); } #endif ierr = PetscObjectReference((PetscObject) mesh->coarseMesh);CHKERRQ(ierr); *dmCoarsened = mesh->coarseMesh; PetscFunctionReturn(0); }
int main(int argc,char **args) { User user; Mat A,S; PetscScalar *data,diag = 1.3; PetscReal tol = PETSC_SMALL; PetscInt i,j,m = PETSC_DECIDE,n = PETSC_DECIDE,M = 17,N = 15,s1,s2; PetscInt test, ntest = 2; PetscMPIInt rank,size; PetscBool nc = PETSC_FALSE, cong; PetscBool ronl = PETSC_TRUE; PetscBool randomize = PETSC_FALSE; PetscBool keep = PETSC_FALSE; PetscBool testzerorows = PETSC_TRUE, testdiagscale = PETSC_TRUE, testgetdiag = PETSC_TRUE; PetscBool testshift = PETSC_TRUE, testscale = PETSC_TRUE, testdup = PETSC_TRUE, testreset = PETSC_TRUE; PetscErrorCode ierr; ierr = PetscInitialize(&argc,&args,(char*)0,help);if (ierr) return ierr; ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,NULL,"-M",&M,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,NULL,"-N",&N,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,NULL,"-ml",&m,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,NULL,"-nl",&n,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-square_nc",&nc,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-rows_only",&ronl,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-randomize",&randomize,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-test_zerorows",&testzerorows,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-test_diagscale",&testdiagscale,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-test_getdiag",&testgetdiag,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-test_shift",&testshift,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-test_scale",&testscale,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-test_dup",&testdup,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-test_reset",&testreset,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,NULL,"-loop",&ntest,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetReal(NULL,NULL,"-tol",&tol,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetScalar(NULL,NULL,"-diag",&diag,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,NULL,"-keep",&keep,NULL);CHKERRQ(ierr); /* This tests square matrices with different row/col layout */ if (nc && size > 1) { M = PetscMax(PetscMax(N,M),1); N = M; m = n = 0; if (rank == 0) { m = M-1; n = 1; } else if (rank == 1) { m = 1; n = N-1; } } ierr = MatCreateDense(PETSC_COMM_WORLD,m,n,M,N,NULL,&A);CHKERRQ(ierr); ierr = MatGetLocalSize(A,&m,&n);CHKERRQ(ierr); ierr = MatGetSize(A,&M,&N);CHKERRQ(ierr); ierr = MatHasCongruentLayouts(A,&cong);CHKERRQ(ierr); ierr = MatGetOwnershipRange(A,&s1,NULL);CHKERRQ(ierr); s2 = 1; while (s2 < M) s2 *= 10; ierr = MatDenseGetArray(A,&data);CHKERRQ(ierr); for (j = 0; j < N; j++) { for (i = 0; i < m; i++) { data[j*m + i] = s2*j + i + s1 + 1; } } ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatConvert(A,MATAIJ,MAT_INPLACE_MATRIX,&A);CHKERRQ(ierr); ierr = MatSetOption(A,MAT_KEEP_NONZERO_PATTERN,keep);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)A,"initial");CHKERRQ(ierr); ierr = MatViewFromOptions(A,NULL,"-view_mat");CHKERRQ(ierr); ierr = PetscNew(&user);CHKERRQ(ierr); ierr = MatCreateShell(PETSC_COMM_WORLD,m,n,M,N,user,&S);CHKERRQ(ierr); ierr = MatShellSetOperation(S,MATOP_MULT,(void (*)(void))MatMult_User);CHKERRQ(ierr); ierr = MatShellSetOperation(S,MATOP_MULT_TRANSPOSE,(void (*)(void))MatMultTranspose_User);CHKERRQ(ierr); if (cong) { ierr = MatShellSetOperation(S,MATOP_GET_DIAGONAL,(void (*)(void))MatGetDiagonal_User);CHKERRQ(ierr); } ierr = MatDuplicate(A,MAT_COPY_VALUES,&user->B);CHKERRQ(ierr); /* Square and rows only scaling */ ronl = cong ? ronl : PETSC_TRUE; for (test = 0; test < ntest; test++) { PetscReal err; if (testzerorows) { Mat ST,B,C,BT,BTT; IS zr; Vec x = NULL, b1 = NULL, b2 = NULL; PetscInt *idxs = NULL, nr = 0; if (rank == (test%size)) { nr = 1; ierr = PetscMalloc1(nr,&idxs);CHKERRQ(ierr); if (test%2) { idxs[0] = (2*M - 1 - test/2)%M; } else { idxs[0] = (test/2)%M; } idxs[0] = PetscMax(idxs[0],0); } ierr = ISCreateGeneral(PETSC_COMM_WORLD,nr,idxs,PETSC_OWN_POINTER,&zr);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)zr,"ZR");CHKERRQ(ierr); ierr = ISViewFromOptions(zr,NULL,"-view_is");CHKERRQ(ierr); ierr = MatCreateVecs(A,&x,&b1);CHKERRQ(ierr); if (randomize) { ierr = VecSetRandom(x,NULL);CHKERRQ(ierr); ierr = VecSetRandom(b1,NULL);CHKERRQ(ierr); } else { ierr = VecSet(x,11.4);CHKERRQ(ierr); ierr = VecSet(b1,-14.2);CHKERRQ(ierr); } ierr = VecDuplicate(b1,&b2);CHKERRQ(ierr); ierr = VecCopy(b1,b2);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)b1,"A_B1");CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)b2,"A_B2");CHKERRQ(ierr); if (size > 1 && !cong) { /* MATMPIAIJ ZeroRows and ZeroRowsColumns are buggy in this case */ ierr = VecDestroy(&b1);CHKERRQ(ierr); } if (ronl) { ierr = MatZeroRowsIS(A,zr,diag,x,b1);CHKERRQ(ierr); ierr = MatZeroRowsIS(S,zr,diag,x,b2);CHKERRQ(ierr); } else { ierr = MatZeroRowsColumnsIS(A,zr,diag,x,b1);CHKERRQ(ierr); ierr = MatZeroRowsColumnsIS(S,zr,diag,x,b2);CHKERRQ(ierr); ierr = ISDestroy(&zr);CHKERRQ(ierr); /* Mix zerorows and zerorowscols */ nr = 0; idxs = NULL; if (!rank) { nr = 1; ierr = PetscMalloc1(nr,&idxs);CHKERRQ(ierr); if (test%2) { idxs[0] = (3*M - 2 - test/2)%M; } else { idxs[0] = (test/2+1)%M; } idxs[0] = PetscMax(idxs[0],0); } ierr = ISCreateGeneral(PETSC_COMM_WORLD,nr,idxs,PETSC_OWN_POINTER,&zr);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)zr,"ZR2");CHKERRQ(ierr); ierr = ISViewFromOptions(zr,NULL,"-view_is");CHKERRQ(ierr); ierr = MatZeroRowsIS(A,zr,diag*2.0+PETSC_SMALL,NULL,NULL);CHKERRQ(ierr); ierr = MatZeroRowsIS(S,zr,diag*2.0+PETSC_SMALL,NULL,NULL);CHKERRQ(ierr); } ierr = ISDestroy(&zr);CHKERRQ(ierr); if (b1) { Vec b; ierr = VecViewFromOptions(b1,NULL,"-view_b");CHKERRQ(ierr); ierr = VecViewFromOptions(b2,NULL,"-view_b");CHKERRQ(ierr); ierr = VecDuplicate(b1,&b);CHKERRQ(ierr); ierr = VecCopy(b1,b);CHKERRQ(ierr); ierr = VecAXPY(b,-1.0,b2);CHKERRQ(ierr); ierr = VecNorm(b,NORM_INFINITY,&err);CHKERRQ(ierr); if (err >= tol) { ierr = PetscPrintf(PETSC_COMM_WORLD,"[test %D] Error b %g\n",test,(double)err);CHKERRQ(ierr); } ierr = VecDestroy(&b);CHKERRQ(ierr); } ierr = VecDestroy(&b1);CHKERRQ(ierr); ierr = VecDestroy(&b2);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = MatConvert(S,MATDENSE,MAT_INITIAL_MATRIX,&B);CHKERRQ(ierr); ierr = MatCreateTranspose(S,&ST);CHKERRQ(ierr); ierr = MatComputeOperator(ST,MATDENSE,&BT);CHKERRQ(ierr); ierr = MatTranspose(BT,MAT_INITIAL_MATRIX,&BTT);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)B,"S");CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)BTT,"STT");CHKERRQ(ierr); ierr = MatConvert(A,MATDENSE,MAT_INITIAL_MATRIX,&C);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)C,"A");CHKERRQ(ierr); ierr = MatViewFromOptions(C,NULL,"-view_mat");CHKERRQ(ierr); ierr = MatViewFromOptions(B,NULL,"-view_mat");CHKERRQ(ierr); ierr = MatViewFromOptions(BTT,NULL,"-view_mat");CHKERRQ(ierr); ierr = MatAXPY(C,-1.0,B,SAME_NONZERO_PATTERN);CHKERRQ(ierr); ierr = MatNorm(C,NORM_FROBENIUS,&err);CHKERRQ(ierr); if (err >= tol) { ierr = PetscPrintf(PETSC_COMM_WORLD,"[test %D] Error mat mult %g\n",test,(double)err);CHKERRQ(ierr); } ierr = MatConvert(A,MATDENSE,MAT_REUSE_MATRIX,&C);CHKERRQ(ierr); ierr = MatAXPY(C,-1.0,BTT,SAME_NONZERO_PATTERN);CHKERRQ(ierr); ierr = MatNorm(C,NORM_FROBENIUS,&err);CHKERRQ(ierr); if (err >= tol) { ierr = PetscPrintf(PETSC_COMM_WORLD,"[test %D] Error mat mult transpose %g\n",test,(double)err);CHKERRQ(ierr); } ierr = MatDestroy(&ST);CHKERRQ(ierr); ierr = MatDestroy(&BTT);CHKERRQ(ierr); ierr = MatDestroy(&BT);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = MatDestroy(&C);CHKERRQ(ierr); } if (testdiagscale) { /* MatDiagonalScale() */ Vec vr,vl; ierr = MatCreateVecs(A,&vr,&vl);CHKERRQ(ierr); if (randomize) { ierr = VecSetRandom(vr,NULL);CHKERRQ(ierr); ierr = VecSetRandom(vl,NULL);CHKERRQ(ierr); } else { ierr = VecSet(vr,test%2 ? 0.15 : 1.0/0.15);CHKERRQ(ierr); ierr = VecSet(vl,test%2 ? -1.2 : 1.0/-1.2);CHKERRQ(ierr); } ierr = MatDiagonalScale(A,vl,vr);CHKERRQ(ierr); ierr = MatDiagonalScale(S,vl,vr);CHKERRQ(ierr); ierr = VecDestroy(&vr);CHKERRQ(ierr); ierr = VecDestroy(&vl);CHKERRQ(ierr); } if (testscale) { /* MatScale() */ ierr = MatScale(A,test%2 ? 1.4 : 1.0/1.4);CHKERRQ(ierr); ierr = MatScale(S,test%2 ? 1.4 : 1.0/1.4);CHKERRQ(ierr); } if (testshift && cong) { /* MatShift() : MATSHELL shift is broken when row/cols layout are not congruent and left/right scaling have been applied */ ierr = MatShift(A,test%2 ? -77.5 : 77.5);CHKERRQ(ierr); ierr = MatShift(S,test%2 ? -77.5 : 77.5);CHKERRQ(ierr); } if (testgetdiag && cong) { /* MatGetDiagonal() */ Vec dA,dS; ierr = MatCreateVecs(A,&dA,NULL);CHKERRQ(ierr); ierr = MatCreateVecs(S,&dS,NULL);CHKERRQ(ierr); ierr = MatGetDiagonal(A,dA);CHKERRQ(ierr); ierr = MatGetDiagonal(S,dS);CHKERRQ(ierr); ierr = VecAXPY(dA,-1.0,dS);CHKERRQ(ierr); ierr = VecNorm(dA,NORM_INFINITY,&err);CHKERRQ(ierr); if (err >= tol) { ierr = PetscPrintf(PETSC_COMM_WORLD,"[test %D] Error diag %g\n",test,(double)err);CHKERRQ(ierr); } ierr = VecDestroy(&dA);CHKERRQ(ierr); ierr = VecDestroy(&dS);CHKERRQ(ierr); } if (testdup && !test) { Mat A2, S2; ierr = MatDuplicate(A,MAT_COPY_VALUES,&A2);CHKERRQ(ierr); ierr = MatDuplicate(S,MAT_COPY_VALUES,&S2);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = MatDestroy(&S);CHKERRQ(ierr); A = A2; S = S2; } if (testreset && (ntest == 1 || test == ntest-2)) { /* reset MATSHELL */ ierr = MatAssemblyBegin(S,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(S,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); /* reset A */ ierr = MatCopy(user->B,A,DIFFERENT_NONZERO_PATTERN);CHKERRQ(ierr); } } ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = MatDestroy(&user->B);CHKERRQ(ierr); ierr = MatDestroy(&S);CHKERRQ(ierr); ierr = PetscFree(user);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
int main(int argc,char **args) { MatType mtype = MATMPIAIJ; /* matrix format */ Mat A,B; /* matrix */ PetscViewer fd; /* viewer */ char file[PETSC_MAX_PATH_LEN]; /* input file name */ PetscBool flg,viewMats,viewIS,viewVecs; PetscInt ierr,*nlocal,m,n; PetscMPIInt rank,size; MatPartitioning part; IS is,isn; Vec xin, xout; VecScatter scat; PetscInitialize(&argc,&args,(char*)0,help); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); ierr = PetscOptionsHasName(NULL, "-view_mats", &viewMats);CHKERRQ(ierr); ierr = PetscOptionsHasName(NULL, "-view_is", &viewIS);CHKERRQ(ierr); ierr = PetscOptionsHasName(NULL, "-view_vecs", &viewVecs);CHKERRQ(ierr); /* Determine file from which we read the matrix */ ierr = PetscOptionsGetString(NULL,"-f",file,PETSC_MAX_PATH_LEN,&flg);CHKERRQ(ierr); /* Open binary file. Note that we use FILE_MODE_READ to indicate reading from this file. */ ierr = PetscViewerBinaryOpen(PETSC_COMM_WORLD,file,FILE_MODE_READ,&fd);CHKERRQ(ierr); /* Load the matrix and vector; then destroy the viewer. */ ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetType(A,mtype);CHKERRQ(ierr); ierr = MatLoad(A,fd);CHKERRQ(ierr); ierr = VecCreate(PETSC_COMM_WORLD,&xin);CHKERRQ(ierr); ierr = VecLoad(xin,fd);CHKERRQ(ierr); ierr = PetscViewerDestroy(&fd);CHKERRQ(ierr); if (viewMats) { if (!rank) printf("Original matrix:\n"); ierr = MatView(A,PETSC_VIEWER_DRAW_WORLD);CHKERRQ(ierr); } if (viewVecs) { if (!rank) printf("Original vector:\n"); ierr = VecView(xin,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* Partition the graph of the matrix */ ierr = MatPartitioningCreate(PETSC_COMM_WORLD,&part);CHKERRQ(ierr); ierr = MatPartitioningSetAdjacency(part,A);CHKERRQ(ierr); ierr = MatPartitioningSetFromOptions(part);CHKERRQ(ierr); /* get new processor owner number of each vertex */ ierr = MatPartitioningApply(part,&is);CHKERRQ(ierr); if (viewIS) { if (!rank) printf("IS1 - new processor ownership:\n"); ierr = ISView(is,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* get new global number of each old global number */ ierr = ISPartitioningToNumbering(is,&isn);CHKERRQ(ierr); if (viewIS) { if (!rank) printf("IS2 - new global numbering:\n"); ierr = ISView(isn,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* get number of new vertices for each processor */ ierr = PetscMalloc(size*sizeof(PetscInt),&nlocal);CHKERRQ(ierr); ierr = ISPartitioningCount(is,size,nlocal);CHKERRQ(ierr); ierr = ISDestroy(&is);CHKERRQ(ierr); /* get old global number of each new global number */ ierr = ISInvertPermutation(isn,nlocal[rank],&is);CHKERRQ(ierr); ierr = PetscFree(nlocal);CHKERRQ(ierr); ierr = ISDestroy(&isn);CHKERRQ(ierr); ierr = MatPartitioningDestroy(&part);CHKERRQ(ierr); if (viewIS) { if (!rank) printf("IS3=inv(IS2) - old global number of each new global number:\n"); ierr = ISView(is,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* move the matrix rows to the new processes they have been assigned to by the permutation */ ierr = ISSort(is);CHKERRQ(ierr); ierr = MatGetSubMatrix(A,is,is,MAT_INITIAL_MATRIX,&B);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); /* move the vector rows to the new processes they have been assigned to */ ierr = MatGetLocalSize(B,&m,&n);CHKERRQ(ierr); ierr = VecCreateMPI(PETSC_COMM_WORLD,m,PETSC_DECIDE,&xout);CHKERRQ(ierr); ierr = VecScatterCreate(xin,is,xout,NULL,&scat);CHKERRQ(ierr); ierr = VecScatterBegin(scat,xin,xout,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); ierr = VecScatterEnd(scat,xin,xout,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); ierr = VecScatterDestroy(&scat);CHKERRQ(ierr); ierr = ISDestroy(&is);CHKERRQ(ierr); if (viewMats) { if (!rank) printf("Partitioned matrix:\n"); ierr = MatView(B,PETSC_VIEWER_DRAW_WORLD);CHKERRQ(ierr); } if (viewVecs) { if (!rank) printf("Mapped vector:\n"); ierr = VecView(xout,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } { PetscInt rstart,i,*nzd,*nzo,nzl,nzmax = 0,*ncols,nrow,j; Mat J; const PetscInt *cols; const PetscScalar *vals; PetscScalar *nvals; ierr = MatGetOwnershipRange(B,&rstart,NULL);CHKERRQ(ierr); ierr = PetscMalloc(2*m*sizeof(PetscInt),&nzd);CHKERRQ(ierr); ierr = PetscMemzero(nzd,2*m*sizeof(PetscInt));CHKERRQ(ierr); ierr = PetscMalloc(2*m*sizeof(PetscInt),&nzo);CHKERRQ(ierr); ierr = PetscMemzero(nzo,2*m*sizeof(PetscInt));CHKERRQ(ierr); for (i=0; i<m; i++) { ierr = MatGetRow(B,i+rstart,&nzl,&cols,NULL);CHKERRQ(ierr); for (j=0; j<nzl; j++) { if (cols[j] >= rstart && cols[j] < rstart+n) { nzd[2*i] += 2; nzd[2*i+1] += 2; } else { nzo[2*i] += 2; nzo[2*i+1] += 2; } } nzmax = PetscMax(nzmax,nzd[2*i]+nzo[2*i]); ierr = MatRestoreRow(B,i+rstart,&nzl,&cols,NULL);CHKERRQ(ierr); } ierr = MatCreateAIJ(PETSC_COMM_WORLD,2*m,2*m,PETSC_DECIDE,PETSC_DECIDE,0,nzd,0,nzo,&J);CHKERRQ(ierr); ierr = PetscInfo(0,"Created empty Jacobian matrix\n");CHKERRQ(ierr); ierr = PetscFree(nzd);CHKERRQ(ierr); ierr = PetscFree(nzo);CHKERRQ(ierr); ierr = PetscMalloc2(nzmax,PetscInt,&ncols,nzmax,PetscScalar,&nvals);CHKERRQ(ierr); ierr = PetscMemzero(nvals,nzmax*sizeof(PetscScalar));CHKERRQ(ierr); for (i=0; i<m; i++) { ierr = MatGetRow(B,i+rstart,&nzl,&cols,&vals);CHKERRQ(ierr); for (j=0; j<nzl; j++) { ncols[2*j] = 2*cols[j]; ncols[2*j+1] = 2*cols[j]+1; } nrow = 2*(i+rstart); ierr = MatSetValues(J,1,&nrow,2*nzl,ncols,nvals,INSERT_VALUES);CHKERRQ(ierr); nrow = 2*(i+rstart) + 1; ierr = MatSetValues(J,1,&nrow,2*nzl,ncols,nvals,INSERT_VALUES);CHKERRQ(ierr); ierr = MatRestoreRow(B,i+rstart,&nzl,&cols,&vals);CHKERRQ(ierr); } ierr = MatAssemblyBegin(J,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(J,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); if (viewMats) { if (!rank) printf("Jacobian matrix structure:\n"); ierr = MatView(J,PETSC_VIEWER_DRAW_WORLD);CHKERRQ(ierr); } ierr = MatDestroy(&J);CHKERRQ(ierr); ierr = PetscFree2(ncols,nvals);CHKERRQ(ierr); } /* Free work space. All PETSc objects should be destroyed when they are no longer needed. */ ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = VecDestroy(&xin);CHKERRQ(ierr); ierr = VecDestroy(&xout);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
PetscErrorCode PCSetUp_MG(PC pc) { PC_MG *mg = (PC_MG*)pc->data; PC_MG_Levels **mglevels = mg->levels; PetscErrorCode ierr; PetscInt i,n = mglevels[0]->levels; PC cpc; PetscBool preonly,lu,redundant,cholesky,svd,dump = PETSC_FALSE,opsset,use_amat; Mat dA,dB; Vec tvec; DM *dms; PetscViewer viewer = 0; PetscFunctionBegin; /* FIX: Move this to PCSetFromOptions_MG? */ if (mg->usedmfornumberoflevels) { PetscInt levels; ierr = DMGetRefineLevel(pc->dm,&levels);CHKERRQ(ierr); levels++; if (levels > n) { /* the problem is now being solved on a finer grid */ ierr = PCMGSetLevels(pc,levels,NULL);CHKERRQ(ierr); n = levels; ierr = PCSetFromOptions(pc);CHKERRQ(ierr); /* it is bad to call this here, but otherwise will never be called for the new hierarchy */ mglevels = mg->levels; } } ierr = KSPGetPC(mglevels[0]->smoothd,&cpc);CHKERRQ(ierr); /* If user did not provide fine grid operators OR operator was not updated since last global KSPSetOperators() */ /* so use those from global PC */ /* Is this what we always want? What if user wants to keep old one? */ ierr = KSPGetOperatorsSet(mglevels[n-1]->smoothd,NULL,&opsset);CHKERRQ(ierr); if (opsset) { Mat mmat; ierr = KSPGetOperators(mglevels[n-1]->smoothd,NULL,&mmat);CHKERRQ(ierr); if (mmat == pc->pmat) opsset = PETSC_FALSE; } if (!opsset) { ierr = PCGetUseAmat(pc,&use_amat);CHKERRQ(ierr); if(use_amat){ ierr = PetscInfo(pc,"Using outer operators to define finest grid operator \n because PCMGGetSmoother(pc,nlevels-1,&ksp);KSPSetOperators(ksp,...); was not called.\n");CHKERRQ(ierr); ierr = KSPSetOperators(mglevels[n-1]->smoothd,pc->mat,pc->pmat);CHKERRQ(ierr); } else { ierr = PetscInfo(pc,"Using matrix (pmat) operators to define finest grid operator \n because PCMGGetSmoother(pc,nlevels-1,&ksp);KSPSetOperators(ksp,...); was not called.\n");CHKERRQ(ierr); ierr = KSPSetOperators(mglevels[n-1]->smoothd,pc->pmat,pc->pmat);CHKERRQ(ierr); } } /* Skipping this for galerkin==2 (externally managed hierarchy such as ML and GAMG). Cleaner logic here would be great. Wrap ML/GAMG as DMs? */ if (pc->dm && mg->galerkin != 2 && !pc->setupcalled) { /* construct the interpolation from the DMs */ Mat p; Vec rscale; ierr = PetscMalloc1(n,&dms);CHKERRQ(ierr); dms[n-1] = pc->dm; for (i=n-2; i>-1; i--) { DMKSP kdm; ierr = DMCoarsen(dms[i+1],MPI_COMM_NULL,&dms[i]);CHKERRQ(ierr); ierr = KSPSetDM(mglevels[i]->smoothd,dms[i]);CHKERRQ(ierr); if (mg->galerkin) {ierr = KSPSetDMActive(mglevels[i]->smoothd,PETSC_FALSE);CHKERRQ(ierr);} ierr = DMGetDMKSPWrite(dms[i],&kdm);CHKERRQ(ierr); /* Ugly hack so that the next KSPSetUp() will use the RHS that we set. A better fix is to change dmActive to take * a bitwise OR of computing the matrix, RHS, and initial iterate. */ kdm->ops->computerhs = NULL; kdm->rhsctx = NULL; if (!mglevels[i+1]->interpolate) { ierr = DMCreateInterpolation(dms[i],dms[i+1],&p,&rscale);CHKERRQ(ierr); ierr = PCMGSetInterpolation(pc,i+1,p);CHKERRQ(ierr); if (rscale) {ierr = PCMGSetRScale(pc,i+1,rscale);CHKERRQ(ierr);} ierr = VecDestroy(&rscale);CHKERRQ(ierr); ierr = MatDestroy(&p);CHKERRQ(ierr); } } for (i=n-2; i>-1; i--) { ierr = DMDestroy(&dms[i]);CHKERRQ(ierr); } ierr = PetscFree(dms);CHKERRQ(ierr); } if (pc->dm && !pc->setupcalled) { /* finest smoother also gets DM but it is not active, independent of whether galerkin==2 */ ierr = KSPSetDM(mglevels[n-1]->smoothd,pc->dm);CHKERRQ(ierr); ierr = KSPSetDMActive(mglevels[n-1]->smoothd,PETSC_FALSE);CHKERRQ(ierr); } if (mg->galerkin == 1) { Mat B; /* currently only handle case where mat and pmat are the same on coarser levels */ ierr = KSPGetOperators(mglevels[n-1]->smoothd,&dA,&dB);CHKERRQ(ierr); if (!pc->setupcalled) { for (i=n-2; i>-1; i--) { if (mglevels[i+1]->interpolate == mglevels[i+1]->restrct || !mglevels[i+1]->restrct) { ierr = MatPtAP(dB,mglevels[i+1]->interpolate,MAT_INITIAL_MATRIX,1.0,&B);CHKERRQ(ierr); } else { ierr = MatMatMatMult(mglevels[i+1]->restrct,dB,mglevels[i+1]->interpolate,MAT_INITIAL_MATRIX,1.0,&B);CHKERRQ(ierr); } ierr = KSPSetOperators(mglevels[i]->smoothd,B,B);CHKERRQ(ierr); if (i != n-2) {ierr = PetscObjectDereference((PetscObject)dB);CHKERRQ(ierr);} dB = B; } if (n > 1) {ierr = PetscObjectDereference((PetscObject)dB);CHKERRQ(ierr);} } else { for (i=n-2; i>-1; i--) { ierr = KSPGetOperators(mglevels[i]->smoothd,NULL,&B);CHKERRQ(ierr); if (mglevels[i+1]->interpolate == mglevels[i+1]->restrct || !mglevels[i+1]->restrct) { ierr = MatPtAP(dB,mglevels[i+1]->interpolate,MAT_REUSE_MATRIX,1.0,&B);CHKERRQ(ierr); } else { ierr = MatMatMatMult(mglevels[i+1]->restrct,dB,mglevels[i+1]->interpolate,MAT_REUSE_MATRIX,1.0,&B);CHKERRQ(ierr); } ierr = KSPSetOperators(mglevels[i]->smoothd,B,B);CHKERRQ(ierr); dB = B; } } } else if (!mg->galerkin && pc->dm && pc->dm->x) { /* need to restrict Jacobian location to coarser meshes for evaluation */ for (i=n-2; i>-1; i--) { Mat R; Vec rscale; if (!mglevels[i]->smoothd->dm->x) { Vec *vecs; ierr = KSPCreateVecs(mglevels[i]->smoothd,1,&vecs,0,NULL);CHKERRQ(ierr); mglevels[i]->smoothd->dm->x = vecs[0]; ierr = PetscFree(vecs);CHKERRQ(ierr); } ierr = PCMGGetRestriction(pc,i+1,&R);CHKERRQ(ierr); ierr = PCMGGetRScale(pc,i+1,&rscale);CHKERRQ(ierr); ierr = MatRestrict(R,mglevels[i+1]->smoothd->dm->x,mglevels[i]->smoothd->dm->x);CHKERRQ(ierr); ierr = VecPointwiseMult(mglevels[i]->smoothd->dm->x,mglevels[i]->smoothd->dm->x,rscale);CHKERRQ(ierr); } } if (!mg->galerkin && pc->dm) { for (i=n-2; i>=0; i--) { DM dmfine,dmcoarse; Mat Restrict,Inject; Vec rscale; ierr = KSPGetDM(mglevels[i+1]->smoothd,&dmfine);CHKERRQ(ierr); ierr = KSPGetDM(mglevels[i]->smoothd,&dmcoarse);CHKERRQ(ierr); ierr = PCMGGetRestriction(pc,i+1,&Restrict);CHKERRQ(ierr); ierr = PCMGGetRScale(pc,i+1,&rscale);CHKERRQ(ierr); Inject = NULL; /* Callback should create it if it needs Injection */ ierr = DMRestrict(dmfine,Restrict,rscale,Inject,dmcoarse);CHKERRQ(ierr); } } if (!pc->setupcalled) { for (i=0; i<n; i++) { ierr = KSPSetFromOptions(mglevels[i]->smoothd);CHKERRQ(ierr); } for (i=1; i<n; i++) { if (mglevels[i]->smoothu && (mglevels[i]->smoothu != mglevels[i]->smoothd)) { ierr = KSPSetFromOptions(mglevels[i]->smoothu);CHKERRQ(ierr); } } for (i=1; i<n; i++) { ierr = PCMGGetInterpolation(pc,i,&mglevels[i]->interpolate);CHKERRQ(ierr); ierr = PCMGGetRestriction(pc,i,&mglevels[i]->restrct);CHKERRQ(ierr); } for (i=0; i<n-1; i++) { if (!mglevels[i]->b) { Vec *vec; ierr = KSPCreateVecs(mglevels[i]->smoothd,1,&vec,0,NULL);CHKERRQ(ierr); ierr = PCMGSetRhs(pc,i,*vec);CHKERRQ(ierr); ierr = VecDestroy(vec);CHKERRQ(ierr); ierr = PetscFree(vec);CHKERRQ(ierr); } if (!mglevels[i]->r && i) { ierr = VecDuplicate(mglevels[i]->b,&tvec);CHKERRQ(ierr); ierr = PCMGSetR(pc,i,tvec);CHKERRQ(ierr); ierr = VecDestroy(&tvec);CHKERRQ(ierr); } if (!mglevels[i]->x) { ierr = VecDuplicate(mglevels[i]->b,&tvec);CHKERRQ(ierr); ierr = PCMGSetX(pc,i,tvec);CHKERRQ(ierr); ierr = VecDestroy(&tvec);CHKERRQ(ierr); } } if (n != 1 && !mglevels[n-1]->r) { /* PCMGSetR() on the finest level if user did not supply it */ Vec *vec; ierr = KSPCreateVecs(mglevels[n-1]->smoothd,1,&vec,0,NULL);CHKERRQ(ierr); ierr = PCMGSetR(pc,n-1,*vec);CHKERRQ(ierr); ierr = VecDestroy(vec);CHKERRQ(ierr); ierr = PetscFree(vec);CHKERRQ(ierr); } } if (pc->dm) { /* need to tell all the coarser levels to rebuild the matrix using the DM for that level */ for (i=0; i<n-1; i++) { if (mglevels[i]->smoothd->setupstage != KSP_SETUP_NEW) mglevels[i]->smoothd->setupstage = KSP_SETUP_NEWMATRIX; } } for (i=1; i<n; i++) { if (mglevels[i]->smoothu == mglevels[i]->smoothd) { /* if doing only down then initial guess is zero */ ierr = KSPSetInitialGuessNonzero(mglevels[i]->smoothd,PETSC_TRUE);CHKERRQ(ierr); } if (mglevels[i]->eventsmoothsetup) {ierr = PetscLogEventBegin(mglevels[i]->eventsmoothsetup,0,0,0,0);CHKERRQ(ierr);} ierr = KSPSetUp(mglevels[i]->smoothd);CHKERRQ(ierr); if (mglevels[i]->eventsmoothsetup) {ierr = PetscLogEventEnd(mglevels[i]->eventsmoothsetup,0,0,0,0);CHKERRQ(ierr);} if (!mglevels[i]->residual) { Mat mat; ierr = KSPGetOperators(mglevels[i]->smoothd,NULL,&mat);CHKERRQ(ierr); ierr = PCMGSetResidual(pc,i,PCMGResidualDefault,mat);CHKERRQ(ierr); } } for (i=1; i<n; i++) { if (mglevels[i]->smoothu && mglevels[i]->smoothu != mglevels[i]->smoothd) { Mat downmat,downpmat; /* check if operators have been set for up, if not use down operators to set them */ ierr = KSPGetOperatorsSet(mglevels[i]->smoothu,&opsset,NULL);CHKERRQ(ierr); if (!opsset) { ierr = KSPGetOperators(mglevels[i]->smoothd,&downmat,&downpmat);CHKERRQ(ierr); ierr = KSPSetOperators(mglevels[i]->smoothu,downmat,downpmat);CHKERRQ(ierr); } ierr = KSPSetInitialGuessNonzero(mglevels[i]->smoothu,PETSC_TRUE);CHKERRQ(ierr); if (mglevels[i]->eventsmoothsetup) {ierr = PetscLogEventBegin(mglevels[i]->eventsmoothsetup,0,0,0,0);CHKERRQ(ierr);} ierr = KSPSetUp(mglevels[i]->smoothu);CHKERRQ(ierr); if (mglevels[i]->eventsmoothsetup) {ierr = PetscLogEventEnd(mglevels[i]->eventsmoothsetup,0,0,0,0);CHKERRQ(ierr);} } } /* If coarse solver is not direct method then DO NOT USE preonly */ ierr = PetscObjectTypeCompare((PetscObject)mglevels[0]->smoothd,KSPPREONLY,&preonly);CHKERRQ(ierr); if (preonly) { ierr = PetscObjectTypeCompare((PetscObject)cpc,PCLU,&lu);CHKERRQ(ierr); ierr = PetscObjectTypeCompare((PetscObject)cpc,PCREDUNDANT,&redundant);CHKERRQ(ierr); ierr = PetscObjectTypeCompare((PetscObject)cpc,PCCHOLESKY,&cholesky);CHKERRQ(ierr); ierr = PetscObjectTypeCompare((PetscObject)cpc,PCSVD,&svd);CHKERRQ(ierr); if (!lu && !redundant && !cholesky && !svd) { ierr = KSPSetType(mglevels[0]->smoothd,KSPGMRES);CHKERRQ(ierr); } } if (!pc->setupcalled) { ierr = KSPSetFromOptions(mglevels[0]->smoothd);CHKERRQ(ierr); } if (mglevels[0]->eventsmoothsetup) {ierr = PetscLogEventBegin(mglevels[0]->eventsmoothsetup,0,0,0,0);CHKERRQ(ierr);} ierr = KSPSetUp(mglevels[0]->smoothd);CHKERRQ(ierr); if (mglevels[0]->eventsmoothsetup) {ierr = PetscLogEventEnd(mglevels[0]->eventsmoothsetup,0,0,0,0);CHKERRQ(ierr);} /* Dump the interpolation/restriction matrices plus the Jacobian/stiffness on each level. This allows MATLAB users to easily check if the Galerkin condition A_c = R A_f R^T is satisfied. Only support one or the other at the same time. */ #if defined(PETSC_USE_SOCKET_VIEWER) ierr = PetscOptionsGetBool(((PetscObject)pc)->prefix,"-pc_mg_dump_matlab",&dump,NULL);CHKERRQ(ierr); if (dump) viewer = PETSC_VIEWER_SOCKET_(PetscObjectComm((PetscObject)pc)); dump = PETSC_FALSE; #endif ierr = PetscOptionsGetBool(((PetscObject)pc)->prefix,"-pc_mg_dump_binary",&dump,NULL);CHKERRQ(ierr); if (dump) viewer = PETSC_VIEWER_BINARY_(PetscObjectComm((PetscObject)pc)); if (viewer) { for (i=1; i<n; i++) { ierr = MatView(mglevels[i]->restrct,viewer);CHKERRQ(ierr); } for (i=0; i<n; i++) { ierr = KSPGetPC(mglevels[i]->smoothd,&pc);CHKERRQ(ierr); ierr = MatView(pc->mat,viewer);CHKERRQ(ierr); } } PetscFunctionReturn(0); }
int main(int argc,char **argv) { PetscErrorCode ierr; KSP ksp; PC pc; Vec x,b; DM da; Mat A; PetscInt dof=1; PetscBool flg; PetscScalar zero=0.0; PetscInitialize(&argc,&argv,(char*)0,help); ierr = PetscOptionsGetInt(NULL,"-dof",&dof,NULL);CHKERRQ(ierr); ierr = DMDACreate(PETSC_COMM_WORLD,&da);CHKERRQ(ierr); ierr = DMDASetDim(da,3);CHKERRQ(ierr); ierr = DMDASetBoundaryType(da,DMDA_BOUNDARY_NONE,DMDA_BOUNDARY_NONE,DMDA_BOUNDARY_NONE);CHKERRQ(ierr); ierr = DMDASetStencilType(da,DMDA_STENCIL_STAR);CHKERRQ(ierr); ierr = DMDASetSizes(da,3,3,3);CHKERRQ(ierr); ierr = DMDASetNumProcs(da,PETSC_DECIDE,PETSC_DECIDE,PETSC_DECIDE);CHKERRQ(ierr); ierr = DMDASetDof(da,dof);CHKERRQ(ierr); ierr = DMDASetStencilWidth(da,1);CHKERRQ(ierr); ierr = DMDASetOwnershipRanges(da,NULL,NULL,NULL);CHKERRQ(ierr); ierr = DMSetFromOptions(da);CHKERRQ(ierr); ierr = DMSetUp(da);CHKERRQ(ierr); ierr = DMCreateGlobalVector(da,&x);CHKERRQ(ierr); ierr = DMCreateGlobalVector(da,&b);CHKERRQ(ierr); ierr = DMCreateMatrix(da,MATAIJ,&A);CHKERRQ(ierr); ierr = VecSet(b,zero);CHKERRQ(ierr); /* Test sbaij matrix */ flg = PETSC_FALSE; ierr = PetscOptionsGetBool(NULL,"-test_sbaij",&flg,NULL);CHKERRQ(ierr); if (flg) { Mat sA; ierr = MatSetOption(A,MAT_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr); ierr = MatConvert(A,MATSBAIJ,MAT_INITIAL_MATRIX,&sA);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); A = sA; } ierr = KSPCreate(PETSC_COMM_WORLD,&ksp);CHKERRQ(ierr); ierr = KSPSetFromOptions(ksp);CHKERRQ(ierr); ierr = KSPSetOperators(ksp,A,A,SAME_NONZERO_PATTERN);CHKERRQ(ierr); ierr = KSPGetPC(ksp,&pc);CHKERRQ(ierr); ierr = PCSetDM(pc,(DM)da);CHKERRQ(ierr); ierr = KSPSolve(ksp,b,x);CHKERRQ(ierr); /* check final residual */ flg = PETSC_FALSE; ierr = PetscOptionsGetBool(NULL, "-check_final_residual", &flg,NULL);CHKERRQ(ierr); if (flg) { Vec b1; PetscReal norm; ierr = KSPGetSolution(ksp,&x);CHKERRQ(ierr); ierr = VecDuplicate(b,&b1);CHKERRQ(ierr); ierr = MatMult(A,x,b1);CHKERRQ(ierr); ierr = VecAXPY(b1,-1.0,b);CHKERRQ(ierr); ierr = VecNorm(b1,NORM_2,&norm);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Final residual %g\n",norm);CHKERRQ(ierr); ierr = VecDestroy(&b1);CHKERRQ(ierr); } ierr = KSPDestroy(&ksp);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = DMDestroy(&da);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
int main(int argc,char **args) { Vec x,b,u; /* approx solution, RHS, exact solution */ Mat A; /* linear system matrix */ KSP ksp; /* KSP context */ PetscErrorCode ierr; PetscInt i,n = 10,col[3],its,i1,i2; PetscScalar none = -1.0,value[3],avalue; PetscReal norm; PC pc; ierr = PetscInitialize(&argc,&args,(char*)0,help);if (ierr) return ierr; ierr = PetscOptionsGetInt(NULL,NULL,"-n",&n,NULL);CHKERRQ(ierr); /* Create vectors */ ierr = VecCreate(PETSC_COMM_WORLD,&x);CHKERRQ(ierr); ierr = VecSetSizes(x,PETSC_DECIDE,n);CHKERRQ(ierr); ierr = VecSetFromOptions(x);CHKERRQ(ierr); ierr = VecDuplicate(x,&b);CHKERRQ(ierr); ierr = VecDuplicate(x,&u);CHKERRQ(ierr); /* create a solution that is orthogonal to the constants */ ierr = VecGetOwnershipRange(u,&i1,&i2);CHKERRQ(ierr); for (i=i1; i<i2; i++) { avalue = i; VecSetValues(u,1,&i,&avalue,INSERT_VALUES); } ierr = VecAssemblyBegin(u);CHKERRQ(ierr); ierr = VecAssemblyEnd(u);CHKERRQ(ierr); ierr = VecSum(u,&avalue);CHKERRQ(ierr); avalue = -avalue/(PetscReal)n; ierr = VecShift(u,avalue);CHKERRQ(ierr); /* Create and assemble matrix */ ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetSizes(A,PETSC_DECIDE,PETSC_DECIDE,n,n);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); value[0] = -1.0; value[1] = 2.0; value[2] = -1.0; for (i=1; i<n-1; i++) { col[0] = i-1; col[1] = i; col[2] = i+1; ierr = MatSetValues(A,1,&i,3,col,value,INSERT_VALUES);CHKERRQ(ierr); } i = n - 1; col[0] = n - 2; col[1] = n - 1; value[1] = 1.0; ierr = MatSetValues(A,1,&i,2,col,value,INSERT_VALUES);CHKERRQ(ierr); i = 0; col[0] = 0; col[1] = 1; value[0] = 1.0; value[1] = -1.0; ierr = MatSetValues(A,1,&i,2,col,value,INSERT_VALUES);CHKERRQ(ierr); ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatMult(A,u,b);CHKERRQ(ierr); /* Create KSP context; set operators and options; solve linear system */ ierr = KSPCreate(PETSC_COMM_WORLD,&ksp);CHKERRQ(ierr); ierr = KSPSetOperators(ksp,A,A);CHKERRQ(ierr); /* Insure that preconditioner has same null space as matrix */ /* currently does not do anything */ ierr = KSPGetPC(ksp,&pc);CHKERRQ(ierr); ierr = KSPSetFromOptions(ksp);CHKERRQ(ierr); ierr = KSPSolve(ksp,b,x);CHKERRQ(ierr); /* ierr = KSPView(ksp,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); */ /* Check error */ ierr = VecAXPY(x,none,u);CHKERRQ(ierr); ierr = VecNorm(x,NORM_2,&norm);CHKERRQ(ierr); ierr = KSPGetIterationNumber(ksp,&its);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Norm of error %g, Iterations %D\n",(double)norm,its);CHKERRQ(ierr); /* Free work space */ ierr = VecDestroy(&x);CHKERRQ(ierr);ierr = VecDestroy(&u);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr);ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = KSPDestroy(&ksp);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
int main(int argc,char **args) { Mat *A,B; /* matrix */ PetscErrorCode ierr; Vec x,y,v,v2,z; PetscReal rnorm; PetscInt n = 20; /* size of the matrix */ PetscInt nmat = 3; /* number of matrices */ PetscInt i; PetscRandom rctx; MatCompositeType type; ierr = PetscInitialize(&argc,&args,(char*)0,help);if (ierr) return ierr; ierr = PetscOptionsGetInt(NULL,NULL,"-n",&n,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,NULL,"-nmat",&nmat,NULL);CHKERRQ(ierr); /* Create random matrices */ ierr = PetscMalloc1(nmat+3,&A);CHKERRQ(ierr); ierr = PetscRandomCreate(PETSC_COMM_WORLD,&rctx);CHKERRQ(ierr); ierr = MatCreateAIJ(PETSC_COMM_WORLD,PETSC_DECIDE,PETSC_DECIDE,n,n/2,3,NULL,3,NULL,&A[0]);CHKERRQ(ierr); for (i = 1; i < nmat+1; i++) { ierr = MatCreateAIJ(PETSC_COMM_WORLD,PETSC_DECIDE,PETSC_DECIDE,n,n,3,NULL,3,NULL,&A[i]);CHKERRQ(ierr); } ierr = MatCreateAIJ(PETSC_COMM_WORLD,PETSC_DECIDE,PETSC_DECIDE,n/2,n,3,NULL,3,NULL,&A[nmat+1]);CHKERRQ(ierr); for (i = 0; i < nmat+2; i++) { ierr = MatSetRandom(A[i],rctx);CHKERRQ(ierr); } ierr = MatCreateVecs(A[1],&x,&y);CHKERRQ(ierr); ierr = VecDuplicate(y,&z);CHKERRQ(ierr); ierr = MatCreateVecs(A[0],&v,NULL);CHKERRQ(ierr); ierr = VecDuplicate(v,&v2);CHKERRQ(ierr); ierr = VecSet(x,1.0);CHKERRQ(ierr); ierr = VecSet(y,0.0);CHKERRQ(ierr); ierr = MatMult(A[1],x,z);CHKERRQ(ierr); for (i = 2; i < nmat+1; i++) { ierr = MatMultAdd(A[i],x,z,z);CHKERRQ(ierr); } ierr = MatCreateComposite(PETSC_COMM_WORLD,nmat,A+1,&B);CHKERRQ(ierr); ierr = MatMultAdd(B,x,y,y);CHKERRQ(ierr); ierr = VecAXPY(y,-1.0,z);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&rnorm);CHKERRQ(ierr); if (rnorm > 10000.0*PETSC_MACHINE_EPSILON) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with composite add %g\n",(double)rnorm);CHKERRQ(ierr); } ierr = MatCompositeSetMatStructure(B,DIFFERENT_NONZERO_PATTERN);CHKERRQ(ierr); /* default */ ierr = MatCompositeMerge(B);CHKERRQ(ierr); ierr = MatMult(B,x,y);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = VecAXPY(y,-1.0,z);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&rnorm);CHKERRQ(ierr); if (rnorm > 10000.0*PETSC_MACHINE_EPSILON) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with composite add after merge %g\n",(double)rnorm);CHKERRQ(ierr); } /* Test n x n/2 multiplicative composite */ ierr = VecSet(v,1.0);CHKERRQ(ierr); ierr = MatMult(A[0],v,z);CHKERRQ(ierr); for (i = 1; i < nmat; i++) { ierr = MatMult(A[i],z,y);CHKERRQ(ierr); ierr = VecCopy(y,z);CHKERRQ(ierr); } ierr = MatCreateComposite(PETSC_COMM_WORLD,nmat,A,&B);CHKERRQ(ierr); ierr = MatCompositeSetType(B,MAT_COMPOSITE_MULTIPLICATIVE);CHKERRQ(ierr); ierr = MatCompositeSetMergeType(B,MAT_COMPOSITE_MERGE_LEFT);CHKERRQ(ierr); ierr = MatSetFromOptions(B);CHKERRQ(ierr); ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); /* do MatCompositeMerge() if -mat_composite_merge 1 */ ierr = MatMult(B,v,y);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = VecAXPY(y,-1.0,z);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&rnorm);CHKERRQ(ierr); if (rnorm > 10000.0*PETSC_MACHINE_EPSILON) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with composite multiplicative %g\n",(double)rnorm);CHKERRQ(ierr); } /* Test n/2 x n multiplicative composite */ ierr = VecSet(x,1.0);CHKERRQ(ierr); ierr = MatMult(A[2],x,z);CHKERRQ(ierr); for (i = 3; i < nmat+1; i++) { ierr = MatMult(A[i],z,y);CHKERRQ(ierr); ierr = VecCopy(y,z);CHKERRQ(ierr); } ierr = MatMult(A[nmat+1],z,v);CHKERRQ(ierr); ierr = MatCreateComposite(PETSC_COMM_WORLD,nmat,A+2,&B);CHKERRQ(ierr); ierr = MatCompositeSetType(B,MAT_COMPOSITE_MULTIPLICATIVE);CHKERRQ(ierr); ierr = MatSetFromOptions(B);CHKERRQ(ierr); ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); /* do MatCompositeMerge() if -mat_composite_merge 1 */ ierr = MatMult(B,x,v2);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = VecAXPY(v2,-1.0,v);CHKERRQ(ierr); ierr = VecNorm(v2,NORM_2,&rnorm);CHKERRQ(ierr); if (rnorm > 10000.0*PETSC_MACHINE_EPSILON) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with composite multiplicative %g\n",(double)rnorm);CHKERRQ(ierr); } /* Test get functions */ ierr = MatCreateComposite(PETSC_COMM_WORLD,nmat,A,&B);CHKERRQ(ierr); ierr = MatCompositeGetNumberMat(B,&n);CHKERRQ(ierr); if (nmat != n) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with GetNumberMat %D != %D\n",nmat,n);CHKERRQ(ierr); } ierr = MatCompositeGetMat(B,0,&A[nmat+2]);CHKERRQ(ierr); if (A[0] != A[nmat+2]) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with GetMat\n");CHKERRQ(ierr); } ierr = MatCompositeGetType(B,&type);CHKERRQ(ierr); if (type != MAT_COMPOSITE_ADDITIVE) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with GetType\n");CHKERRQ(ierr); } ierr = MatDestroy(&B);CHKERRQ(ierr); /* Free work space. All PETSc objects should be destroyed when they are no longer needed. */ ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&y);CHKERRQ(ierr); ierr = VecDestroy(&v);CHKERRQ(ierr); ierr = VecDestroy(&v2);CHKERRQ(ierr); ierr = VecDestroy(&z);CHKERRQ(ierr); ierr = PetscRandomDestroy(&rctx);CHKERRQ(ierr); for (i = 0; i < nmat+2; i++) { ierr = MatDestroy(&A[i]);CHKERRQ(ierr); } ierr = PetscFree(A);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
int main(int argc, char *argv[]) { PetscErrorCode ierr; Mat A,B,Asub,Bsub; PetscInt ms,idxrow[3],idxcol[4]; Vec left,right,X,Y,X1,Y1; IS isrow,iscol; PetscBool random = PETSC_TRUE; ierr = PetscInitialize(&argc,&argv,PETSC_NULL,help);CHKERRQ(ierr); ierr = AssembleMatrix(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = AssembleMatrix(PETSC_COMM_WORLD,&B);CHKERRQ(ierr); ierr = MatShellSetOperation(B,MATOP_GET_SUBMATRIX,PETSC_NULL);CHKERRQ(ierr); ierr = MatShellSetOperation(B,MATOP_GET_SUBMATRICES,PETSC_NULL);CHKERRQ(ierr); ierr = MatGetOwnershipRange(A,&ms,PETSC_NULL);CHKERRQ(ierr); idxrow[0] = ms+1; idxrow[1] = ms+2; idxrow[2] = ms+4; ierr = ISCreateGeneral(PETSC_COMM_WORLD,3,idxrow,PETSC_USE_POINTER,&isrow);CHKERRQ(ierr); idxcol[0] = ms+1; idxcol[1] = ms+2; idxcol[2] = ms+4; idxcol[3] = ms+5; ierr = ISCreateGeneral(PETSC_COMM_WORLD,4,idxcol,PETSC_USE_POINTER,&iscol);CHKERRQ(ierr); ierr = MatGetSubMatrix(A,isrow,iscol,MAT_INITIAL_MATRIX,&Asub);CHKERRQ(ierr); ierr = MatGetSubMatrix(B,isrow,iscol,MAT_INITIAL_MATRIX,&Bsub);CHKERRQ(ierr); ierr = MatGetVecs(Asub,&right,&left);CHKERRQ(ierr); ierr = VecDuplicate(right,&X);CHKERRQ(ierr); ierr = VecDuplicate(right,&X1);CHKERRQ(ierr); ierr = VecDuplicate(left,&Y);CHKERRQ(ierr); ierr = VecDuplicate(left,&Y1);CHKERRQ(ierr); ierr = PetscOptionsGetBool(PETSC_NULL,"-random",&random,PETSC_NULL);CHKERRQ(ierr); if (random) { ierr = VecSetRandom(right,PETSC_NULL);CHKERRQ(ierr); ierr = VecSetRandom(left,PETSC_NULL);CHKERRQ(ierr); ierr = VecSetRandom(X,PETSC_NULL);CHKERRQ(ierr); ierr = VecSetRandom(Y,PETSC_NULL);CHKERRQ(ierr); ierr = VecSetRandom(X1,PETSC_NULL);CHKERRQ(ierr); ierr = VecSetRandom(Y1,PETSC_NULL);CHKERRQ(ierr); } else { ierr = VecSet(right,1.0);CHKERRQ(ierr); ierr = VecSet(left,2.0);CHKERRQ(ierr); ierr = VecSet(X,3.0);CHKERRQ(ierr); ierr = VecSet(Y,4.0);CHKERRQ(ierr); ierr = VecSet(X1,3.0);CHKERRQ(ierr); ierr = VecSet(Y1,4.0);CHKERRQ(ierr); } ierr = CheckMatrices(Asub,Bsub,left,right,X,Y,X1,Y1);CHKERRQ(ierr); ierr = ISDestroy(&isrow);CHKERRQ(ierr); ierr = ISDestroy(&iscol);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = MatDestroy(&Asub);CHKERRQ(ierr); ierr = MatDestroy(&Bsub);CHKERRQ(ierr); ierr = VecDestroy(&left);CHKERRQ(ierr); ierr = VecDestroy(&right);CHKERRQ(ierr); ierr = VecDestroy(&X);CHKERRQ(ierr); ierr = VecDestroy(&Y);CHKERRQ(ierr); ierr = VecDestroy(&X1);CHKERRQ(ierr); ierr = VecDestroy(&Y1);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
int main(int argc, char **argv) { PetscErrorCode ierr; PetscInt n=10000,its,dfid=1; Vec x,b,u; Mat A; KSP ksp; PC pc,pcnoise; PCNoise_Ctx ctx={0,NULL}; PetscReal eta=0.1,norm; PetscScalar(*diagfunc)(PetscInt,PetscInt); ierr = PetscInitialize(&argc,&argv,(char*)0,help);if (ierr) return ierr; /* Process command line options */ ierr = PetscOptionsGetInt(NULL,NULL,"-n",&n,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetReal(NULL,NULL,"-eta",&eta,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,NULL,"-diagfunc",&dfid,NULL);CHKERRQ(ierr); switch(dfid){ case 1: diagfunc = diagFunc1; break; case 2: diagfunc = diagFunc2; break; case 3: diagfunc = diagFunc3; break; default: SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Unrecognized diagfunc option"); } /* Create a diagonal matrix with a given distribution of diagonal elements */ ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetSizes(A,PETSC_DECIDE,PETSC_DECIDE,n,n);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatSetUp(A);CHKERRQ(ierr); ierr = AssembleDiagonalMatrix(A,diagfunc);CHKERRQ(ierr); /* Allocate vectors and manufacture an exact solution and rhs */ ierr = MatCreateVecs(A,&x,NULL);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)x,"Computed Solution");CHKERRQ(ierr); ierr = MatCreateVecs(A,&b,NULL);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)b,"RHS");CHKERRQ(ierr); ierr = MatCreateVecs(A,&u,NULL);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)u,"Reference Solution");CHKERRQ(ierr); ierr = VecSet(u,1.0);CHKERRQ(ierr); ierr = MatMult(A,u,b);CHKERRQ(ierr); /* Create a KSP object */ ierr = KSPCreate(PETSC_COMM_WORLD,&ksp);CHKERRQ(ierr); ierr = KSPSetOperators(ksp,A,A);CHKERRQ(ierr); /* Set up a composite preconditioner */ ierr = KSPGetPC(ksp,&pc);CHKERRQ(ierr); ierr = PCSetType(pc,PCCOMPOSITE);CHKERRQ(ierr); /* default composite with single Identity PC */ ierr = PCCompositeSetType(pc,PC_COMPOSITE_ADDITIVE);CHKERRQ(ierr); ierr = PCCompositeAddPC(pc,PCNONE);CHKERRQ(ierr); if(eta > 0){ ierr = PCCompositeAddPC(pc,PCSHELL);CHKERRQ(ierr); ierr = PCCompositeGetPC(pc,1,&pcnoise);CHKERRQ(ierr); ctx.eta = eta; ierr = PCShellSetContext(pcnoise,&ctx);CHKERRQ(ierr); ierr = PCShellSetApply(pcnoise,PCApply_Noise);CHKERRQ(ierr); ierr = PCShellSetSetUp(pcnoise,PCSetup_Noise);CHKERRQ(ierr); ierr = PCShellSetDestroy(pcnoise,PCDestroy_Noise);CHKERRQ(ierr); ierr = PCShellSetName(pcnoise,"Noise PC");CHKERRQ(ierr); } /* Set KSP from options (this can override the PC just defined) */ ierr = KSPSetFromOptions(ksp);CHKERRQ(ierr); /* Solve */ ierr = KSPSolve(ksp,b,x);CHKERRQ(ierr); /* Compute error */ ierr = VecAXPY(x,-1.0,u);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)x,"Error");CHKERRQ(ierr); ierr = VecNorm(x,NORM_2,&norm);CHKERRQ(ierr); ierr = KSPGetIterationNumber(ksp,&its);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Norm of error %g, Iterations %D\n",(double)norm,its);CHKERRQ(ierr); /* Destroy objects and finalize */ ierr = KSPDestroy(&ksp);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr); ierr = VecDestroy(&u);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
int main(int argc,char **argv) { SNES snes; /* nonlinear solver context */ Vec x,r; /* solution, residual vectors */ Mat J; /* Jacobian matrix */ PetscErrorCode ierr; PetscInt its; PetscScalar *xx; SNESConvergedReason reason; PetscInitialize(&argc,&argv,(char*)0,help); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Create nonlinear solver context - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = SNESCreate(PETSC_COMM_WORLD,&snes);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Create matrix and vector data structures; set corresponding routines - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ /* Create vectors for solution and nonlinear function */ ierr = VecCreate(PETSC_COMM_WORLD,&x);CHKERRQ(ierr); ierr = VecSetSizes(x,PETSC_DECIDE,2);CHKERRQ(ierr); ierr = VecSetFromOptions(x);CHKERRQ(ierr); ierr = VecDuplicate(x,&r);CHKERRQ(ierr); /* Create Jacobian matrix data structure */ ierr = MatCreate(PETSC_COMM_WORLD,&J);CHKERRQ(ierr); ierr = MatSetSizes(J,PETSC_DECIDE,PETSC_DECIDE,2,2);CHKERRQ(ierr); ierr = MatSetFromOptions(J);CHKERRQ(ierr); ierr = MatSetUp(J);CHKERRQ(ierr); /* Set function evaluation routine and vector. */ ierr = SNESSetFunction(snes,r,FormFunction1,NULL);CHKERRQ(ierr); /* Set Jacobian matrix data structure and Jacobian evaluation routine */ ierr = SNESSetJacobian(snes,J,J,FormJacobian1,NULL);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Customize nonlinear solver; set runtime options - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = SNESSetFromOptions(snes);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Evaluate initial guess; then solve nonlinear system - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = VecGetArray(x,&xx);CHKERRQ(ierr); xx[0] = -1.2; xx[1] = 1.0; ierr = VecRestoreArray(x,&xx);CHKERRQ(ierr); /* Note: The user should initialize the vector, x, with the initial guess for the nonlinear solver prior to calling SNESSolve(). In particular, to employ an initial guess of zero, the user should explicitly set this vector to zero by calling VecSet(). */ ierr = SNESSolve(snes,NULL,x);CHKERRQ(ierr); ierr = VecView(x,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = SNESGetIterationNumber(snes,&its);CHKERRQ(ierr); ierr = SNESGetConvergedReason(snes,&reason);CHKERRQ(ierr); /* Some systems computes a residual that is identically zero, thus converging due to FNORM_ABS, others converge due to FNORM_RELATIVE. Here, we only report the reason if the iteration did not converge so that the tests are reproducible. */ ierr = PetscPrintf(PETSC_COMM_WORLD,"%s number of SNES iterations = %D\n\n",reason>0 ? "CONVERGED" : SNESConvergedReasons[reason],its);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Free work space. All PETSc objects should be destroyed when they are no longer needed. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&r);CHKERRQ(ierr); ierr = MatDestroy(&J);CHKERRQ(ierr); ierr = SNESDestroy(&snes);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
int main(int argc,char **args) { Mat A; PetscInt i,j; PetscErrorCode ierr; PetscMPIInt size; PetscViewer fd; PetscScalar values[16],one = 1.0; Vec x; ierr = PetscInitialize(&argc,&args,(char*)0,help);if (ierr) return ierr; ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); if (size > 1) SETERRQ(PETSC_COMM_WORLD,1,"Can only run on one processor"); /* Open binary file. Note that we use FILE_MODE_WRITE to indicate writing to this file. */ ierr = PetscViewerBinaryOpen(PETSC_COMM_WORLD,"4by4",FILE_MODE_WRITE,&fd);CHKERRQ(ierr); ierr = MatCreateSeqBAIJ(PETSC_COMM_WORLD,4,12,12,0,0,&A);CHKERRQ(ierr); for (i=0; i<16; i++) values[i] = i; for (i=0; i<4; i++) values[4*i+i] += 5; i = 0; j = 0; ierr = MatSetValuesBlocked(A,1,&i,1,&j,values,INSERT_VALUES);CHKERRQ(ierr); for (i=0; i<16; i++) values[i] = i; i = 0; j = 2; ierr = MatSetValuesBlocked(A,1,&i,1,&j,values,INSERT_VALUES);CHKERRQ(ierr); for (i=0; i<16; i++) values[i] = i; i = 1; j = 0; ierr = MatSetValuesBlocked(A,1,&i,1,&j,values,INSERT_VALUES);CHKERRQ(ierr); for (i=0; i<16; i++) values[i] = i;for (i=0; i<4; i++) values[4*i+i] += 6; i = 1; j = 1; ierr = MatSetValuesBlocked(A,1,&i,1,&j,values,INSERT_VALUES);CHKERRQ(ierr); for (i=0; i<16; i++) values[i] = i; i = 2; j = 0; ierr = MatSetValuesBlocked(A,1,&i,1,&j,values,INSERT_VALUES);CHKERRQ(ierr); for (i=0; i<16; i++) values[i] = i;for (i=0; i<4; i++) values[4*i+i] += 7; i = 2; j = 2; ierr = MatSetValuesBlocked(A,1,&i,1,&j,values,INSERT_VALUES);CHKERRQ(ierr); ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatView(A,fd);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = VecCreateSeq(PETSC_COMM_WORLD,12,&x);CHKERRQ(ierr); ierr = VecSet(x,one);CHKERRQ(ierr); ierr = VecView(x,fd);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = PetscViewerDestroy(&fd);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
int main(int argc,char **argv) { Mat A,F,B,X,C,Aher,G; Vec b,x,c,d,e; PetscErrorCode ierr; PetscInt m = 5,n,p,i,j,nrows,ncols; PetscScalar *v,*barray,rval; PetscReal norm,tol=1.e-12; PetscMPIInt size,rank; PetscRandom rand; const PetscInt *rows,*cols; IS isrows,iscols; PetscBool mats_view=PETSC_FALSE; MatFactorInfo finfo; PetscInitialize(&argc,&argv,(char*) 0,help); ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); ierr = PetscRandomCreate(PETSC_COMM_WORLD,&rand);CHKERRQ(ierr); ierr = PetscRandomSetFromOptions(rand);CHKERRQ(ierr); /* Get local dimensions of matrices */ ierr = PetscOptionsGetInt(NULL,"-m",&m,NULL);CHKERRQ(ierr); n = m; ierr = PetscOptionsGetInt(NULL,"-n",&n,NULL);CHKERRQ(ierr); p = m/2; ierr = PetscOptionsGetInt(NULL,"-p",&p,NULL);CHKERRQ(ierr); ierr = PetscOptionsHasName(NULL,"-mats_view",&mats_view);CHKERRQ(ierr); /* Create matrix A */ ierr = PetscPrintf(PETSC_COMM_WORLD," Create Elemental matrix A\n");CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetSizes(A,m,n,PETSC_DECIDE,PETSC_DECIDE);CHKERRQ(ierr); ierr = MatSetType(A,MATELEMENTAL);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatSetUp(A);CHKERRQ(ierr); /* Set local matrix entries */ ierr = MatGetOwnershipIS(A,&isrows,&iscols);CHKERRQ(ierr); ierr = ISGetLocalSize(isrows,&nrows);CHKERRQ(ierr); ierr = ISGetIndices(isrows,&rows);CHKERRQ(ierr); ierr = ISGetLocalSize(iscols,&ncols);CHKERRQ(ierr); ierr = ISGetIndices(iscols,&cols);CHKERRQ(ierr); ierr = PetscMalloc1(nrows*ncols,&v);CHKERRQ(ierr); for (i=0; i<nrows; i++) { for (j=0; j<ncols; j++) { ierr = PetscRandomGetValue(rand,&rval);CHKERRQ(ierr); v[i*ncols+j] = rval; } } ierr = MatSetValues(A,nrows,rows,ncols,cols,v,INSERT_VALUES);CHKERRQ(ierr); ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = ISRestoreIndices(isrows,&rows);CHKERRQ(ierr); ierr = ISRestoreIndices(iscols,&cols);CHKERRQ(ierr); ierr = ISDestroy(&isrows);CHKERRQ(ierr); ierr = ISDestroy(&iscols);CHKERRQ(ierr); ierr = PetscFree(v);CHKERRQ(ierr); if (mats_view) { ierr = PetscPrintf(PETSC_COMM_WORLD, "A: nrows %d, m %d; ncols %d, n %d\n",nrows,m,ncols,n);CHKERRQ(ierr); ierr = MatView(A,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* Create rhs matrix B */ ierr = PetscPrintf(PETSC_COMM_WORLD," Create rhs matrix B\n");CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&B);CHKERRQ(ierr); ierr = MatSetSizes(B,m,p,PETSC_DECIDE,PETSC_DECIDE);CHKERRQ(ierr); ierr = MatSetType(B,MATELEMENTAL);CHKERRQ(ierr); ierr = MatSetFromOptions(B);CHKERRQ(ierr); ierr = MatSetUp(B);CHKERRQ(ierr); ierr = MatGetOwnershipIS(B,&isrows,&iscols);CHKERRQ(ierr); ierr = ISGetLocalSize(isrows,&nrows);CHKERRQ(ierr); ierr = ISGetIndices(isrows,&rows);CHKERRQ(ierr); ierr = ISGetLocalSize(iscols,&ncols);CHKERRQ(ierr); ierr = ISGetIndices(iscols,&cols);CHKERRQ(ierr); ierr = PetscMalloc1(nrows*ncols,&v);CHKERRQ(ierr); for (i=0; i<nrows; i++) { for (j=0; j<ncols; j++) { ierr = PetscRandomGetValue(rand,&rval);CHKERRQ(ierr); v[i*ncols+j] = rval; } } ierr = MatSetValues(B,nrows,rows,ncols,cols,v,INSERT_VALUES);CHKERRQ(ierr); ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = ISRestoreIndices(isrows,&rows);CHKERRQ(ierr); ierr = ISRestoreIndices(iscols,&cols);CHKERRQ(ierr); ierr = ISDestroy(&isrows);CHKERRQ(ierr); ierr = ISDestroy(&iscols);CHKERRQ(ierr); ierr = PetscFree(v);CHKERRQ(ierr); if (mats_view) { ierr = PetscPrintf(PETSC_COMM_WORLD, "B: nrows %d, m %d; ncols %d, p %d\n",nrows,m,ncols,p);CHKERRQ(ierr); ierr = MatView(B,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* Create rhs vector b and solution x (same size as b) */ ierr = VecCreate(PETSC_COMM_WORLD,&b);CHKERRQ(ierr); ierr = VecSetSizes(b,m,PETSC_DECIDE);CHKERRQ(ierr); ierr = VecSetFromOptions(b);CHKERRQ(ierr); ierr = VecGetArray(b,&barray);CHKERRQ(ierr); for (j=0; j<m; j++) { ierr = PetscRandomGetValue(rand,&rval);CHKERRQ(ierr); barray[j] = rval; } ierr = VecRestoreArray(b,&barray);CHKERRQ(ierr); ierr = VecAssemblyBegin(b);CHKERRQ(ierr); ierr = VecAssemblyEnd(b);CHKERRQ(ierr); if (mats_view) { ierr = PetscSynchronizedPrintf(PETSC_COMM_WORLD, "[%d] b: m %d\n",rank,m);CHKERRQ(ierr); ierr = PetscSynchronizedFlush(PETSC_COMM_WORLD,PETSC_STDOUT);CHKERRQ(ierr); ierr = VecView(b,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } ierr = VecDuplicate(b,&x);CHKERRQ(ierr); /* Create matrix X - same size as B */ ierr = PetscPrintf(PETSC_COMM_WORLD," Create solution matrix X\n");CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&X);CHKERRQ(ierr); ierr = MatSetSizes(X,m,p,PETSC_DECIDE,PETSC_DECIDE);CHKERRQ(ierr); ierr = MatSetType(X,MATELEMENTAL);CHKERRQ(ierr); ierr = MatSetFromOptions(X);CHKERRQ(ierr); ierr = MatSetUp(X);CHKERRQ(ierr); ierr = MatAssemblyBegin(X,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(X,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); /* Cholesky factorization */ /*------------------------*/ ierr = PetscPrintf(PETSC_COMM_WORLD," Create Elemental matrix Aher\n");CHKERRQ(ierr); ierr = MatHermitianTranspose(A,MAT_INITIAL_MATRIX,&Aher);CHKERRQ(ierr); ierr = MatAXPY(Aher,1.0,A,SAME_NONZERO_PATTERN);CHKERRQ(ierr); /* Aher = A + A^T */ if (!rank) { /* add 100.0 to diagonals of Aher to make it spd */ PetscInt M,N; ierr = MatGetSize(Aher,&M,&N);CHKERRQ(ierr); for (i=0; i<M; i++) { rval = 100.0; ierr = MatSetValues(Aher,1,&i,1,&i,&rval,ADD_VALUES);CHKERRQ(ierr); } } ierr = MatAssemblyBegin(Aher,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(Aher,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); if (mats_view) { ierr = PetscPrintf(PETSC_COMM_WORLD, "Aher:\n");CHKERRQ(ierr); ierr = MatView(Aher,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* Cholesky factorization */ /*------------------------*/ ierr = PetscPrintf(PETSC_COMM_WORLD," Test Cholesky Solver \n");CHKERRQ(ierr); /* In-place Cholesky */ /* Create matrix factor G, then copy Aher to G */ ierr = MatCreate(PETSC_COMM_WORLD,&G);CHKERRQ(ierr); ierr = MatSetSizes(G,m,n,PETSC_DECIDE,PETSC_DECIDE);CHKERRQ(ierr); ierr = MatSetType(G,MATELEMENTAL);CHKERRQ(ierr); ierr = MatSetFromOptions(G);CHKERRQ(ierr); ierr = MatSetUp(G);CHKERRQ(ierr); ierr = MatAssemblyBegin(G,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(G,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatCopy(Aher,G,SAME_NONZERO_PATTERN);CHKERRQ(ierr); /* Only G = U^T * U is implemented for now */ ierr = MatCholeskyFactor(G,0,0);CHKERRQ(ierr); if (mats_view) { ierr = PetscPrintf(PETSC_COMM_WORLD, "Cholesky Factor G:\n");CHKERRQ(ierr); ierr = MatView(G,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* Solve U^T * U x = b and U^T * U X = B */ ierr = MatSolve(G,b,x);CHKERRQ(ierr); ierr = MatMatSolve(G,B,X);CHKERRQ(ierr); ierr = MatDestroy(&G);CHKERRQ(ierr); /* Out-place Cholesky */ ierr = MatGetFactor(Aher,MATSOLVERELEMENTAL,MAT_FACTOR_CHOLESKY,&G);CHKERRQ(ierr); ierr = MatCholeskyFactorSymbolic(G,Aher,0,&finfo);CHKERRQ(ierr); ierr = MatCholeskyFactorNumeric(G,Aher,&finfo);CHKERRQ(ierr); if (mats_view) { ierr = MatView(G,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } ierr = MatSolve(G,b,x);CHKERRQ(ierr); ierr = MatMatSolve(G,B,X);CHKERRQ(ierr); ierr = MatDestroy(&G);CHKERRQ(ierr); /* Check norm(Aher*x - b) */ ierr = VecCreate(PETSC_COMM_WORLD,&c);CHKERRQ(ierr); ierr = VecSetSizes(c,m,PETSC_DECIDE);CHKERRQ(ierr); ierr = VecSetFromOptions(c);CHKERRQ(ierr); ierr = MatMult(Aher,x,c);CHKERRQ(ierr); ierr = VecAXPY(c,-1.0,b);CHKERRQ(ierr); ierr = VecNorm(c,NORM_1,&norm);CHKERRQ(ierr); if (norm > tol) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Warning: |Aher*x - b| for Cholesky %g\n",(double)norm);CHKERRQ(ierr); } /* Check norm(Aher*X - B) */ ierr = MatMatMult(Aher,X,MAT_INITIAL_MATRIX,PETSC_DEFAULT,&C);CHKERRQ(ierr); ierr = MatAXPY(C,-1.0,B,SAME_NONZERO_PATTERN);CHKERRQ(ierr); ierr = MatNorm(C,NORM_1,&norm);CHKERRQ(ierr); if (norm > tol) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Warning: |Aher*X - B| for Cholesky %g\n",(double)norm);CHKERRQ(ierr); } /* LU factorization */ /*------------------*/ ierr = PetscPrintf(PETSC_COMM_WORLD," Test LU Solver \n");CHKERRQ(ierr); /* In-place LU */ /* Create matrix factor F, then copy A to F */ ierr = MatCreate(PETSC_COMM_WORLD,&F);CHKERRQ(ierr); ierr = MatSetSizes(F,m,n,PETSC_DECIDE,PETSC_DECIDE);CHKERRQ(ierr); ierr = MatSetType(F,MATELEMENTAL);CHKERRQ(ierr); ierr = MatSetFromOptions(F);CHKERRQ(ierr); ierr = MatSetUp(F);CHKERRQ(ierr); ierr = MatAssemblyBegin(F,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(F,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatCopy(A,F,SAME_NONZERO_PATTERN);CHKERRQ(ierr); /* Create vector d to test MatSolveAdd() */ ierr = VecDuplicate(x,&d);CHKERRQ(ierr); ierr = VecCopy(x,d);CHKERRQ(ierr); /* PF=LU or F=LU factorization - perms is ignored by Elemental; set finfo.dtcol !0 or 0 to enable/disable partial pivoting */ finfo.dtcol = 0.1; ierr = MatLUFactor(F,0,0,&finfo);CHKERRQ(ierr); /* Solve LUX = PB or LUX = B */ ierr = MatSolveAdd(F,b,d,x);CHKERRQ(ierr); ierr = MatMatSolve(F,B,X);CHKERRQ(ierr); ierr = MatDestroy(&F);CHKERRQ(ierr); /* Check norm(A*X - B) */ ierr = VecCreate(PETSC_COMM_WORLD,&e);CHKERRQ(ierr); ierr = VecSetSizes(e,m,PETSC_DECIDE);CHKERRQ(ierr); ierr = VecSetFromOptions(e);CHKERRQ(ierr); ierr = MatMult(A,x,c);CHKERRQ(ierr); ierr = MatMult(A,d,e);CHKERRQ(ierr); ierr = VecAXPY(c,-1.0,e);CHKERRQ(ierr); ierr = VecAXPY(c,-1.0,b);CHKERRQ(ierr); ierr = VecNorm(c,NORM_1,&norm);CHKERRQ(ierr); if (norm > tol) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Warning: |A*x - b| for LU %g\n",(double)norm);CHKERRQ(ierr); } ierr = MatMatMult(A,X,MAT_REUSE_MATRIX,PETSC_DEFAULT,&C);CHKERRQ(ierr); ierr = MatAXPY(C,-1.0,B,SAME_NONZERO_PATTERN);CHKERRQ(ierr); ierr = MatNorm(C,NORM_1,&norm);CHKERRQ(ierr); if (norm > tol) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Warning: |A*X - B| for LU %g\n",(double)norm);CHKERRQ(ierr); } /* Out-place LU */ ierr = MatGetFactor(A,MATSOLVERELEMENTAL,MAT_FACTOR_LU,&F);CHKERRQ(ierr); ierr = MatLUFactorSymbolic(F,A,0,0,&finfo);CHKERRQ(ierr); ierr = MatLUFactorNumeric(F,A,&finfo);CHKERRQ(ierr); if (mats_view) { ierr = MatView(F,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } ierr = MatSolve(F,b,x);CHKERRQ(ierr); ierr = MatMatSolve(F,B,X);CHKERRQ(ierr); ierr = MatDestroy(&F);CHKERRQ(ierr); /* Free space */ ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = MatDestroy(&Aher);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = MatDestroy(&C);CHKERRQ(ierr); ierr = MatDestroy(&X);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr); ierr = VecDestroy(&c);CHKERRQ(ierr); ierr = VecDestroy(&d);CHKERRQ(ierr); ierr = VecDestroy(&e);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = PetscRandomDestroy(&rand);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
int testBSplineHAtom() { PrintTimeStamp(PETSC_COMM_SELF, "H atom", NULL); MPI_Comm comm = PETSC_COMM_SELF; BPS bps; BPSCreate(comm, &bps); BPSSetExp(bps, 30.0, 61, 3.0); int order = 5; BSS bss; BSSCreate(comm, &bss); BSSSetKnots(bss, order, bps); BSSSetUp(bss); Mat H; BSSCreateR1Mat(bss, &H); Mat S; BSSCreateR1Mat(bss, &S); Mat V; BSSCreateR1Mat(bss, &V); BSSD2R1Mat(bss, H); MatScale(H, -0.5); BSSENR1Mat(bss, 0, 0.0, V); MatAXPY(H, -1.0, V, DIFFERENT_NONZERO_PATTERN); BSSSR1Mat(bss, S); // -- initial space -- Pot psi0; PotCreate(comm, &psi0); PotSetSlater(psi0, 2.0, 1, 1.1); int n_init_space = 1; Vec *xs; PetscMalloc1(n_init_space, &xs); MatCreateVecs(H, &xs[0], NULL); BSSPotR1Vec(bss, psi0, xs[0]); EEPS eps; EEPSCreate(comm, &eps); EEPSSetOperators(eps, H, S); // EPSSetType(eps->eps, EPSJD); EPSSetInitialSpace(eps->eps, 1, xs); EEPSSetTarget(eps, -0.6); // EPSSetInitialSpace(eps->eps, 1, xs); EEPSSolve(eps); int nconv; PetscScalar kr; EPSGetConverged(eps->eps, &nconv); ASSERT_TRUE(nconv > 0); EPSGetEigenpair(eps->eps, 0, &kr, NULL, NULL, NULL); ASSERT_DOUBLE_NEAR(-0.5, kr, pow(10.0, -6.0)); Vec cs; MatCreateVecs(H, &cs, NULL); EEPSGetEigenvector(eps, 0, cs); PetscReal x=1.1; PetscScalar y=0.0; PetscScalar dy=0.0; BSSPsiOne(bss, cs, x, &y); BSSDerivPsiOne(bss, cs, x, &dy); ASSERT_DOUBLE_NEAR(creal(y), 2.0*x*exp(-x), pow(10.0, -6)); ASSERT_DOUBLE_NEAR(creal(dy), 2.0*exp(-x)-2.0*x*exp(-x), pow(10.0, -6)); VecDestroy(&xs[0]); PetscFree(xs); PFDestroy(&psi0); BSSDestroy(&bss); MatDestroy(&H); MatDestroy(&V); MatDestroy(&S); EEPSDestroy(&eps); VecDestroy(&cs); return 0; }
int main(int argc,char **args) { Vec x,y,b; Mat A; /* linear system matrix */ Mat sA,sC; /* symmetric part of the matrices */ PetscInt n,mbs=16,bs=1,nz=3,prob=1,i,j,col[3],block, row,Ii,J,n1,lvl; PetscErrorCode ierr; PetscMPIInt size; PetscReal norm2,tol=1.e-10,err[10]; PetscScalar neg_one = -1.0,four=4.0,value[3]; IS perm,cperm; PetscRandom rdm; PetscInt reorder=0,displ=0; MatFactorInfo factinfo; PetscBool equal; PetscBool TestAIJ =PETSC_FALSE,TestBAIJ=PETSC_TRUE; PetscInt TestShift=0; PetscInitialize(&argc,&args,(char*)0,help); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); if (size != 1) SETERRQ(PETSC_COMM_WORLD,1,"This is a uniprocessor example only!"); ierr = PetscOptionsGetInt(NULL,"-bs",&bs,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,"-mbs",&mbs,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,"-reorder",&reorder,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,"-testaij",&TestAIJ,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,"-testShift",&TestShift,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,"-displ",&displ,NULL);CHKERRQ(ierr); n = mbs*bs; if (TestAIJ) { /* A is in aij format */ ierr = MatCreateSeqAIJ(PETSC_COMM_WORLD,n,n,nz,NULL,&A);CHKERRQ(ierr); TestBAIJ = PETSC_FALSE; } else { /* A is in baij format */ ierr =MatCreateSeqBAIJ(PETSC_COMM_WORLD,bs,n,n,nz,NULL,&A);CHKERRQ(ierr); TestAIJ = PETSC_FALSE; } /* Assemble matrix */ if (bs == 1) { ierr = PetscOptionsGetInt(NULL,"-test_problem",&prob,NULL);CHKERRQ(ierr); if (prob == 1) { /* tridiagonal matrix */ value[0] = -1.0; value[1] = 2.0; value[2] = -1.0; for (i=1; i<n-1; i++) { col[0] = i-1; col[1] = i; col[2] = i+1; ierr = MatSetValues(A,1,&i,3,col,value,INSERT_VALUES);CHKERRQ(ierr); } i = n - 1; col[0]=0; col[1] = n - 2; col[2] = n - 1; value[0]= 0.1; value[1]=-1; value[2]=2; ierr = MatSetValues(A,1,&i,3,col,value,INSERT_VALUES);CHKERRQ(ierr); i = 0; col[0] = 0; col[1] = 1; col[2]=n-1; value[0] = 2.0; value[1] = -1.0; value[2]=0.1; ierr = MatSetValues(A,1,&i,3,col,value,INSERT_VALUES);CHKERRQ(ierr); } else if (prob ==2) { /* matrix for the five point stencil */ n1 = (PetscInt) (PetscSqrtReal((PetscReal)n) + 0.001); if (n1*n1 - n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"sqrt(n) must be a positive interger!"); for (i=0; i<n1; i++) { for (j=0; j<n1; j++) { Ii = j + n1*i; if (i>0) { J = Ii - n1; ierr = MatSetValues(A,1,&Ii,1,&J,&neg_one,INSERT_VALUES);CHKERRQ(ierr); } if (i<n1-1) { J = Ii + n1; ierr = MatSetValues(A,1,&Ii,1,&J,&neg_one,INSERT_VALUES);CHKERRQ(ierr); } if (j>0) { J = Ii - 1; ierr = MatSetValues(A,1,&Ii,1,&J,&neg_one,INSERT_VALUES);CHKERRQ(ierr); } if (j<n1-1) { J = Ii + 1; ierr = MatSetValues(A,1,&Ii,1,&J,&neg_one,INSERT_VALUES);CHKERRQ(ierr); } ierr = MatSetValues(A,1,&Ii,1,&Ii,&four,INSERT_VALUES);CHKERRQ(ierr); } } } } else { /* bs > 1 */ for (block=0; block<n/bs; block++) { /* diagonal blocks */ value[0] = -1.0; value[1] = 4.0; value[2] = -1.0; for (i=1+block*bs; i<bs-1+block*bs; i++) { col[0] = i-1; col[1] = i; col[2] = i+1; ierr = MatSetValues(A,1,&i,3,col,value,INSERT_VALUES);CHKERRQ(ierr); } i = bs - 1+block*bs; col[0] = bs - 2+block*bs; col[1] = bs - 1+block*bs; value[0]=-1.0; value[1]=4.0; ierr = MatSetValues(A,1,&i,2,col,value,INSERT_VALUES);CHKERRQ(ierr); i = 0+block*bs; col[0] = 0+block*bs; col[1] = 1+block*bs; value[0]=4.0; value[1] = -1.0; ierr = MatSetValues(A,1,&i,2,col,value,INSERT_VALUES);CHKERRQ(ierr); } /* off-diagonal blocks */ value[0]=-1.0; for (i=0; i<(n/bs-1)*bs; i++) { col[0]=i+bs; ierr = MatSetValues(A,1,&i,1,col,value,INSERT_VALUES);CHKERRQ(ierr); col[0]=i; row=i+bs; ierr = MatSetValues(A,1,&row,1,col,value,INSERT_VALUES);CHKERRQ(ierr); } } if (TestShift) { /* set diagonals in the 0-th block as 0 for testing shift numerical factor */ for (i=0; i<bs; i++) { row = i; col[0] = i; value[0] = 0.0; ierr = MatSetValues(A,1,&row,1,col,value,INSERT_VALUES);CHKERRQ(ierr); } } ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); /* Test MatConvert */ ierr = MatSetOption(A,MAT_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr); ierr = MatConvert(A,MATSEQSBAIJ,MAT_INITIAL_MATRIX,&sA);CHKERRQ(ierr); ierr = MatMultEqual(A,sA,20,&equal);CHKERRQ(ierr); if (!equal) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_USER,"A != sA"); /* Test MatGetOwnershipRange() */ ierr = MatGetOwnershipRange(A,&Ii,&J);CHKERRQ(ierr); ierr = MatGetOwnershipRange(sA,&i,&j);CHKERRQ(ierr); if (i-Ii || j-J) { PetscPrintf(PETSC_COMM_SELF,"Error: MatGetOwnershipRange() in MatSBAIJ format\n"); } /* Vectors */ ierr = PetscRandomCreate(PETSC_COMM_SELF,&rdm);CHKERRQ(ierr); ierr = PetscRandomSetFromOptions(rdm);CHKERRQ(ierr); ierr = VecCreateSeq(PETSC_COMM_SELF,n,&x);CHKERRQ(ierr); ierr = VecDuplicate(x,&b);CHKERRQ(ierr); ierr = VecDuplicate(x,&y);CHKERRQ(ierr); ierr = VecSetRandom(x,rdm);CHKERRQ(ierr); /* Test MatReordering() - not work on sbaij matrix */ if (reorder) { ierr = MatGetOrdering(A,MATORDERINGRCM,&perm,&cperm);CHKERRQ(ierr); } else { ierr = MatGetOrdering(A,MATORDERINGNATURAL,&perm,&cperm);CHKERRQ(ierr); } ierr = ISDestroy(&cperm);CHKERRQ(ierr); /* initialize factinfo */ ierr = MatFactorInfoInitialize(&factinfo);CHKERRQ(ierr); if (TestShift == 1) { factinfo.shifttype = (PetscReal)MAT_SHIFT_NONZERO; factinfo.shiftamount = 0.1; } else if (TestShift == 2) { factinfo.shifttype = (PetscReal)MAT_SHIFT_POSITIVE_DEFINITE; } /* Test MatCholeskyFactor(), MatICCFactor() */ /*------------------------------------------*/ /* Test aij matrix A */ if (TestAIJ) { if (displ>0) { ierr = PetscPrintf(PETSC_COMM_SELF,"AIJ: \n"); } i = 0; for (lvl=-1; lvl<10; lvl++) { if (lvl==-1) { /* Cholesky factor */ factinfo.fill = 5.0; ierr = MatGetFactor(A,MATSOLVERPETSC,MAT_FACTOR_CHOLESKY,&sC);CHKERRQ(ierr); ierr = MatCholeskyFactorSymbolic(sC,A,perm,&factinfo);CHKERRQ(ierr); } else { /* incomplete Cholesky factor */ factinfo.fill = 5.0; factinfo.levels = lvl; ierr = MatGetFactor(A,MATSOLVERPETSC,MAT_FACTOR_ICC,&sC);CHKERRQ(ierr); ierr = MatICCFactorSymbolic(sC,A,perm,&factinfo);CHKERRQ(ierr); } ierr = MatCholeskyFactorNumeric(sC,A,&factinfo);CHKERRQ(ierr); ierr = MatMult(A,x,b);CHKERRQ(ierr); ierr = MatSolve(sC,b,y);CHKERRQ(ierr); ierr = MatDestroy(&sC);CHKERRQ(ierr); /* Check the error */ ierr = VecAXPY(y,neg_one,x);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&norm2);CHKERRQ(ierr); if (displ>0) { ierr = PetscPrintf(PETSC_COMM_SELF," lvl: %D, error: %g\n", lvl,(double)norm2); } err[i++] = norm2; } } /* Test baij matrix A */ if (TestBAIJ) { if (displ>0) { ierr = PetscPrintf(PETSC_COMM_SELF,"BAIJ: \n"); } i = 0; for (lvl=-1; lvl<10; lvl++) { if (lvl==-1) { /* Cholesky factor */ factinfo.fill = 5.0; ierr = MatGetFactor(A,MATSOLVERPETSC,MAT_FACTOR_CHOLESKY,&sC);CHKERRQ(ierr); ierr = MatCholeskyFactorSymbolic(sC,A,perm,&factinfo);CHKERRQ(ierr); } else { /* incomplete Cholesky factor */ factinfo.fill = 5.0; factinfo.levels = lvl; ierr = MatGetFactor(A,MATSOLVERPETSC,MAT_FACTOR_ICC,&sC);CHKERRQ(ierr); ierr = MatICCFactorSymbolic(sC,A,perm,&factinfo);CHKERRQ(ierr); } ierr = MatCholeskyFactorNumeric(sC,A,&factinfo);CHKERRQ(ierr); ierr = MatMult(A,x,b);CHKERRQ(ierr); ierr = MatSolve(sC,b,y);CHKERRQ(ierr); ierr = MatDestroy(&sC);CHKERRQ(ierr); /* Check the error */ ierr = VecAXPY(y,neg_one,x);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&norm2);CHKERRQ(ierr); if (displ>0) { ierr = PetscPrintf(PETSC_COMM_SELF," lvl: %D, error: %g\n", lvl,(double)norm2); } err[i++] = norm2; } } /* Test sbaij matrix sA */ if (displ>0) { ierr = PetscPrintf(PETSC_COMM_SELF,"SBAIJ: \n"); } i = 0; for (lvl=-1; lvl<10; lvl++) { if (lvl==-1) { /* Cholesky factor */ factinfo.fill = 5.0; ierr = MatGetFactor(sA,MATSOLVERPETSC,MAT_FACTOR_CHOLESKY,&sC);CHKERRQ(ierr); ierr = MatCholeskyFactorSymbolic(sC,sA,perm,&factinfo);CHKERRQ(ierr); } else { /* incomplete Cholesky factor */ factinfo.fill = 5.0; factinfo.levels = lvl; ierr = MatGetFactor(sA,MATSOLVERPETSC,MAT_FACTOR_ICC,&sC);CHKERRQ(ierr); ierr = MatICCFactorSymbolic(sC,sA,perm,&factinfo);CHKERRQ(ierr); } ierr = MatCholeskyFactorNumeric(sC,sA,&factinfo);CHKERRQ(ierr); if (lvl==0 && bs==1) { /* Test inplace ICC(0) for sbaij sA - does not work for new datastructure */ /* Mat B; ierr = MatDuplicate(sA,MAT_COPY_VALUES,&B);CHKERRQ(ierr); ierr = MatICCFactor(B,perm,&factinfo);CHKERRQ(ierr); ierr = MatEqual(sC,B,&equal);CHKERRQ(ierr); if (!equal) { SETERRQ(PETSC_COMM_SELF,PETSC_ERR_USER,"in-place Cholesky factor != out-place Cholesky factor"); } ierr = MatDestroy(&B);CHKERRQ(ierr); */ } ierr = MatMult(sA,x,b);CHKERRQ(ierr); ierr = MatSolve(sC,b,y);CHKERRQ(ierr); /* Test MatSolves() */ if (bs == 1) { Vecs xx,bb; ierr = VecsCreateSeq(PETSC_COMM_SELF,n,4,&xx);CHKERRQ(ierr); ierr = VecsDuplicate(xx,&bb);CHKERRQ(ierr); ierr = MatSolves(sC,bb,xx);CHKERRQ(ierr); ierr = VecsDestroy(xx);CHKERRQ(ierr); ierr = VecsDestroy(bb);CHKERRQ(ierr); } ierr = MatDestroy(&sC);CHKERRQ(ierr); /* Check the error */ ierr = VecAXPY(y,neg_one,x);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&norm2);CHKERRQ(ierr); if (displ>0) { ierr = PetscPrintf(PETSC_COMM_SELF," lvl: %D, error: %g\n", lvl,(double)norm2); } err[i] -= norm2; if (err[i] > tol) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_USER," level: %d, err: %g\n", lvl,(double)err[i]); } ierr = ISDestroy(&perm);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = MatDestroy(&sA);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&y);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr); ierr = PetscRandomDestroy(&rdm);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
PetscInt main(PetscInt argc,char **args) { PetscErrorCode ierr; PetscMPIInt rank,size; PetscInt N0=4096,N1=4096,N2=256,N3=10,N4=10,N=N0*N1; PetscRandom rdm; PetscReal enorm; Vec x,y,z,input,output; Mat A; PetscInt DIM, dim[5],vsize,row,col; PetscReal fac; ierr = PetscInitialize(&argc,&args,(char*)0,help);CHKERRQ(ierr); ierr = MPI_Comm_size(PETSC_COMM_WORLD, &size);CHKERRQ(ierr); ierr = MPI_Comm_rank(PETSC_COMM_WORLD, &rank);CHKERRQ(ierr); #if defined(PETSC_USE_COMPLEX) SETERRQ(PETSC_COMM_WORLD,PETSC_ERR_SUP, "Example for Real DFT. Your current data type is complex!"); #endif ierr = PetscRandomCreate(PETSC_COMM_WORLD, &rdm);CHKERRQ(ierr); ierr = PetscRandomSetFromOptions(rdm);CHKERRQ(ierr); ierr = VecCreate(PETSC_COMM_WORLD,&input);CHKERRQ(ierr); ierr = VecSetSizes(input,PETSC_DECIDE,N);CHKERRQ(ierr); ierr = VecSetFromOptions(input);CHKERRQ(ierr); ierr = VecSetRandom(input,rdm);CHKERRQ(ierr); ierr = VecDuplicate(input,&output); DIM = 2; dim[0] = N0; dim[1] = N1; dim[2] = N2; dim[3] = N3; dim[4] = N4; ierr = MatCreateFFT(PETSC_COMM_WORLD,DIM,dim,MATFFTW,&A);CHKERRQ(ierr); ierr = MatGetLocalSize(A,&row,&col);CHKERRQ(ierr); printf("The Matrix size is %d and %d from process %d\n",row,col,rank); ierr = MatCreateVecsFFTW(A,&x,&y,&z);CHKERRQ(ierr); ierr = VecGetSize(x,&vsize);CHKERRQ(ierr); ierr = VecGetSize(z,&vsize);CHKERRQ(ierr); printf("The vector size of output from the main routine is %d\n",vsize); ierr = VecScatterPetscToFFTW(A,input,x);CHKERRQ(ierr); /*ierr = VecDestroy(&input);CHKERRQ(ierr);*/ ierr = MatMult(A,x,y);CHKERRQ(ierr); ierr = MatMultTranspose(A,y,z);CHKERRQ(ierr); ierr = VecScatterFFTWToPetsc(A,z,output);CHKERRQ(ierr); /*ierr = VecDestroy(&z);CHKERRQ(ierr);*/ fac = 1.0/(PetscReal)N; ierr = VecScale(output,fac);CHKERRQ(ierr); ierr = VecAssemblyBegin(input);CHKERRQ(ierr); ierr = VecAssemblyEnd(input);CHKERRQ(ierr); ierr = VecAssemblyBegin(output);CHKERRQ(ierr); ierr = VecAssemblyEnd(output);CHKERRQ(ierr); /* ierr = VecView(input,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr);*/ /* ierr = VecView(output,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr);*/ ierr = VecAXPY(output,-1.0,input);CHKERRQ(ierr); ierr = VecNorm(output,NORM_1,&enorm);CHKERRQ(ierr); if (enorm > 1.e-14) { ierr = PetscPrintf(PETSC_COMM_SELF," Error norm of |x - z| %e\n",enorm);CHKERRQ(ierr); } ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&y);CHKERRQ(ierr); ierr = VecDestroy(&z);CHKERRQ(ierr); ierr = VecDestroy(&output);CHKERRQ(ierr); ierr = VecDestroy(&input);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = PetscRandomDestroy(&rdm);CHKERRQ(ierr); PetscFinalize(); return 0; }
int main(int argc,char **args) { Mat A; Vec min,max,maxabs; PetscInt m,n; PetscInt imin[M],imax[M],imaxabs[M],indices[N],row; PetscScalar values[N]; PetscErrorCode ierr; MatType type; PetscMPIInt size; PetscBool doTest=PETSC_TRUE; ierr = PetscInitialize(&argc,&args,(char*)0,help);if (ierr) return ierr; ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetSizes(A,PETSC_DECIDE,PETSC_DECIDE,M,N);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatSetUp(A);CHKERRQ(ierr); row = 0; indices[0] = 0; indices[1] = 1; indices[2] = 2; indices[3] = 3; indices[4] = 4; indices[5] = 5; values[0] = -1.0; values[1] = 0.0; values[2] = 1.0; values[3] = 3.0; values[4] = 4.0; values[5] = -5.0; ierr = MatSetValues(A,1,&row,6,indices,values,INSERT_VALUES);CHKERRQ(ierr); row = 1; ierr = MatSetValues(A,1,&row,3,indices,values,INSERT_VALUES);CHKERRQ(ierr); row = 4; ierr = MatSetValues(A,1,&row,1,indices+4,values+4,INSERT_VALUES);CHKERRQ(ierr); row = 4; ierr = MatSetValues(A,1,&row,2,indices+4,values+4,INSERT_VALUES);CHKERRQ(ierr); ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatView(A,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = MatGetLocalSize(A, &m,&n);CHKERRQ(ierr); ierr = VecCreate(PETSC_COMM_WORLD,&min);CHKERRQ(ierr); ierr = VecSetSizes(min,m,PETSC_DECIDE);CHKERRQ(ierr); ierr = VecSetFromOptions(min);CHKERRQ(ierr); ierr = VecDuplicate(min,&max);CHKERRQ(ierr); ierr = VecDuplicate(min,&maxabs);CHKERRQ(ierr); /* Test MatGetRowMin, MatGetRowMax and MatGetRowMaxAbs */ if (size == 1) { ierr = MatGetRowMin(A,min,imin);CHKERRQ(ierr); ierr = MatGetRowMax(A,max,imax);CHKERRQ(ierr); ierr = MatGetRowMaxAbs(A,maxabs,imaxabs);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row Minimums\n");CHKERRQ(ierr); ierr = VecView(min,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscIntView(5,imin,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row Maximums\n");CHKERRQ(ierr); ierr = VecView(max,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscIntView(5,imax,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row Maximum Absolute Values\n");CHKERRQ(ierr); ierr = VecView(maxabs,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscIntView(5,imaxabs,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } else { ierr = MatGetType(A,&type);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"\nMatrix type: %s\n",type);CHKERRQ(ierr); /* AIJ */ ierr = PetscObjectTypeCompare((PetscObject)A,MATMPIAIJ,&doTest);CHKERRQ(ierr); if (doTest) { ierr = MatGetRowMaxAbs(A,maxabs,NULL);CHKERRQ(ierr); ierr = MatGetRowMaxAbs(A,maxabs,imaxabs);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row Maximum Absolute Values:\n");CHKERRQ(ierr); ierr = VecView(maxabs,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } /* BAIJ */ ierr = PetscObjectTypeCompare((PetscObject)A,MATMPIBAIJ,&doTest);CHKERRQ(ierr); if (doTest) { ierr = MatGetRowMaxAbs(A,maxabs,NULL);CHKERRQ(ierr); ierr = MatGetRowMaxAbs(A,maxabs,imaxabs);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row Maximum Absolute Values:\n");CHKERRQ(ierr); ierr = VecView(maxabs,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } } if (size == 1) { ierr = MatConvert(A,MATDENSE,MAT_INPLACE_MATRIX,&A);CHKERRQ(ierr); ierr = MatGetRowMin(A,min,imin);CHKERRQ(ierr); ierr = MatGetRowMax(A,max,imax);CHKERRQ(ierr); ierr = MatGetRowMaxAbs(A,maxabs,imaxabs);CHKERRQ(ierr); ierr = MatView(A,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row Minimums\n");CHKERRQ(ierr); ierr = VecView(min,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscIntView(5,imin,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row Maximums\n");CHKERRQ(ierr); ierr = VecView(max,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscIntView(5,imax,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"Row Maximum Absolute Values\n");CHKERRQ(ierr); ierr = VecView(maxabs,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscIntView(5,imaxabs,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); } ierr = VecDestroy(&min);CHKERRQ(ierr); ierr = VecDestroy(&max);CHKERRQ(ierr); ierr = VecDestroy(&maxabs);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
static PetscErrorCode MatPartitioningApply_Parmetis(MatPartitioning part,IS *partitioning) { MatPartitioning_Parmetis *pmetis = (MatPartitioning_Parmetis*)part->data; PetscErrorCode ierr; PetscInt *locals = NULL; Mat mat = part->adj,amat,pmat; PetscBool flg; PetscInt bs = 1; PetscFunctionBegin; ierr = PetscObjectTypeCompare((PetscObject)mat,MATMPIADJ,&flg);CHKERRQ(ierr); if (flg) { amat = mat; PetscObjectReference((PetscObject)amat);CHKERRQ(ierr); } else { /* bs indicates if the converted matrix is "reduced" from the original and hence the resulting partition results need to be stretched to match the original matrix */ ierr = MatConvert(mat,MATMPIADJ,MAT_INITIAL_MATRIX,&amat);CHKERRQ(ierr); if (amat->rmap->n > 0) bs = mat->rmap->n/amat->rmap->n; } ierr = MatMPIAdjCreateNonemptySubcommMat(amat,&pmat);CHKERRQ(ierr); ierr = MPI_Barrier(PetscObjectComm((PetscObject)part));CHKERRQ(ierr); if (pmat) { MPI_Comm pcomm,comm; Mat_MPIAdj *adj = (Mat_MPIAdj*)pmat->data; PetscInt *vtxdist = pmat->rmap->range; PetscInt *xadj = adj->i; PetscInt *adjncy = adj->j; PetscInt itmp = 0,wgtflag=0, numflag=0, ncon=1, nparts=part->n, options[24], i, j; real_t *tpwgts,*ubvec; int status; ierr = PetscObjectGetComm((PetscObject)pmat,&pcomm);CHKERRQ(ierr); #if defined(PETSC_USE_DEBUG) /* check that matrix has no diagonal entries */ { PetscInt rstart; ierr = MatGetOwnershipRange(pmat,&rstart,NULL);CHKERRQ(ierr); for (i=0; i<pmat->rmap->n; i++) { for (j=xadj[i]; j<xadj[i+1]; j++) { if (adjncy[j] == i+rstart) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Row %d has diagonal entry; Parmetis forbids diagonal entry",i+rstart); } } } #endif ierr = PetscMalloc(amat->rmap->n*sizeof(PetscInt),&locals);CHKERRQ(ierr); if (PetscLogPrintInfo) {itmp = pmetis->printout; pmetis->printout = 127;} ierr = PetscMalloc(ncon*nparts*sizeof(real_t),&tpwgts);CHKERRQ(ierr); for (i=0; i<ncon; i++) { for (j=0; j<nparts; j++) { if (part->part_weights) { tpwgts[i*nparts+j] = part->part_weights[i*nparts+j]; } else { tpwgts[i*nparts+j] = 1./nparts; } } } ierr = PetscMalloc(ncon*sizeof(real_t),&ubvec);CHKERRQ(ierr); for (i=0; i<ncon; i++) { ubvec[i] = 1.05; } /* This sets the defaults */ options[0] = 0; for (i=1; i<24; i++) { options[i] = -1; } /* Duplicate the communicator to be sure that ParMETIS attribute caching does not interfere with PETSc. */ ierr = MPI_Comm_dup(pcomm,&comm);CHKERRQ(ierr); PetscStackCallParmetis(ParMETIS_V3_PartKway,(vtxdist,xadj,adjncy,part->vertex_weights,adj->values,&wgtflag,&numflag,&ncon,&nparts,tpwgts,ubvec,options,&pmetis->cuts,locals,&comm)); ierr = MPI_Comm_free(&comm);CHKERRQ(ierr); ierr = PetscFree(tpwgts);CHKERRQ(ierr); ierr = PetscFree(ubvec);CHKERRQ(ierr); if (PetscLogPrintInfo) pmetis->printout = itmp; } if (bs > 1) { PetscInt i,j,*newlocals; ierr = PetscMalloc(bs*amat->rmap->n*sizeof(PetscInt),&newlocals);CHKERRQ(ierr); for (i=0; i<amat->rmap->n; i++) { for (j=0; j<bs; j++) { newlocals[bs*i + j] = locals[i]; } } ierr = PetscFree(locals);CHKERRQ(ierr); ierr = ISCreateGeneral(PetscObjectComm((PetscObject)part),bs*amat->rmap->n,newlocals,PETSC_OWN_POINTER,partitioning);CHKERRQ(ierr); } else { ierr = ISCreateGeneral(PetscObjectComm((PetscObject)part),amat->rmap->n,locals,PETSC_OWN_POINTER,partitioning);CHKERRQ(ierr); } ierr = MatDestroy(&pmat);CHKERRQ(ierr); ierr = MatDestroy(&amat);CHKERRQ(ierr); PetscFunctionReturn(0); }
PetscErrorCode LoadTestMatrices(Mat *_A,Vec *_x,Vec *_b,IS *_isu,IS *_isp) { Vec f,h,x,b,bX[2]; Mat A,Auu,Aup,Apu,App,bA[2][2]; IS is_u,is_p,bis[2]; PetscInt lnu,lnp,nu,np,i,start_u,end_u,start_p,end_p; VecScatter *vscat; PetscMPIInt rank; PetscErrorCode ierr; PetscFunctionBeginUser; /* fetch test matrices and vectors */ ierr = LSCLoadTestOperators(&Auu,&Aup,&Apu,&App,&f,&h);CHKERRQ(ierr); /* build the mat-nest */ ierr = VecGetSize(f,&nu);CHKERRQ(ierr); ierr = VecGetSize(h,&np);CHKERRQ(ierr); ierr = VecGetLocalSize(f,&lnu);CHKERRQ(ierr); ierr = VecGetLocalSize(h,&lnp);CHKERRQ(ierr); ierr = VecGetOwnershipRange(f,&start_u,&end_u);CHKERRQ(ierr); ierr = VecGetOwnershipRange(h,&start_p,&end_p);CHKERRQ(ierr); ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); ierr = PetscSynchronizedPrintf(PETSC_COMM_WORLD,"[%d] lnu = %D | lnp = %D \n", rank, lnu, lnp);CHKERRQ(ierr); ierr = PetscSynchronizedPrintf(PETSC_COMM_WORLD,"[%d] s_u = %D | e_u = %D \n", rank, start_u, end_u);CHKERRQ(ierr); ierr = PetscSynchronizedPrintf(PETSC_COMM_WORLD,"[%d] s_p = %D | e_p = %D \n", rank, start_p, end_p);CHKERRQ(ierr); ierr = PetscSynchronizedPrintf(PETSC_COMM_WORLD,"[%d] is_u (offset) = %D \n", rank, start_u+start_p);CHKERRQ(ierr); ierr = PetscSynchronizedPrintf(PETSC_COMM_WORLD,"[%d] is_p (offset) = %D \n", rank, start_u+start_p+lnu);CHKERRQ(ierr); ierr = PetscSynchronizedFlush(PETSC_COMM_WORLD,PETSC_STDOUT);CHKERRQ(ierr); ierr = ISCreateStride(PETSC_COMM_WORLD,lnu,start_u+start_p,1,&is_u);CHKERRQ(ierr); ierr = ISCreateStride(PETSC_COMM_WORLD,lnp,start_u+start_p+lnu,1,&is_p);CHKERRQ(ierr); bis[0] = is_u; bis[1] = is_p; bA[0][0] = Auu; bA[0][1] = Aup; bA[1][0] = Apu; bA[1][1] = App; ierr = MatCreateNest(PETSC_COMM_WORLD,2,bis,2,bis,&bA[0][0],&A);CHKERRQ(ierr); ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); /* Pull f,h into b */ ierr = MatCreateVecs(A,&b,&x);CHKERRQ(ierr); bX[0] = f; bX[1] = h; ierr = PetscMalloc1(2,&vscat);CHKERRQ(ierr); for (i=0; i<2; i++) { ierr = VecScatterCreateWithData(b,bis[i],bX[i],NULL,&vscat[i]);CHKERRQ(ierr); ierr = VecScatterBegin(vscat[i],bX[i],b,INSERT_VALUES,SCATTER_REVERSE);CHKERRQ(ierr); } for (i=0; i<2; i++) { ierr = VecScatterEnd(vscat[i],bX[i],b,INSERT_VALUES,SCATTER_REVERSE);CHKERRQ(ierr); } /* tidy up */ for (i=0; i<2; i++) { ierr = VecScatterDestroy(&vscat[i]);CHKERRQ(ierr); } ierr = PetscFree(vscat);CHKERRQ(ierr); ierr = MatDestroy(&Auu);CHKERRQ(ierr); ierr = MatDestroy(&Aup);CHKERRQ(ierr); ierr = MatDestroy(&Apu);CHKERRQ(ierr); ierr = MatDestroy(&App);CHKERRQ(ierr); ierr = VecDestroy(&f);CHKERRQ(ierr); ierr = VecDestroy(&h);CHKERRQ(ierr); *_isu = is_u; *_isp = is_p; *_A = A; *_x = x; *_b = b; PetscFunctionReturn(0); }
int main(int argc,char **args) { Mat C; int i,m = 5,rank,size,N,start,end,M; int ierr,idx[4]; PetscBool flg; PetscScalar Ke[16]; PetscReal h; Vec u,b; KSP ksp; MatNullSpace nullsp; PetscInitialize(&argc,&args,(char *)0,help); ierr = PetscOptionsGetInt(PETSC_NULL,"-m",&m,PETSC_NULL);CHKERRQ(ierr); N = (m+1)*(m+1); /* dimension of matrix */ M = m*m; /* number of elements */ h = 1.0/m; /* mesh width */ ierr = MPI_Comm_rank(PETSC_COMM_WORLD,&rank);CHKERRQ(ierr); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); /* Create stiffness matrix */ ierr = MatCreate(PETSC_COMM_WORLD,&C);CHKERRQ(ierr); ierr = MatSetSizes(C,PETSC_DECIDE,PETSC_DECIDE,N,N);CHKERRQ(ierr); ierr = MatSetFromOptions(C);CHKERRQ(ierr); start = rank*(M/size) + ((M%size) < rank ? (M%size) : rank); end = start + M/size + ((M%size) > rank); /* Assemble matrix */ ierr = FormElementStiffness(h*h,Ke); /* element stiffness for Laplacian */ for (i=start; i<end; i++) { /* location of lower left corner of element */ /* node numbers for the four corners of element */ idx[0] = (m+1)*(i/m) + (i % m); idx[1] = idx[0]+1; idx[2] = idx[1] + m + 1; idx[3] = idx[2] - 1; ierr = MatSetValues(C,4,idx,4,idx,Ke,ADD_VALUES);CHKERRQ(ierr); } ierr = MatAssemblyBegin(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); /* Create right-hand-side and solution vectors */ ierr = VecCreate(PETSC_COMM_WORLD,&u);CHKERRQ(ierr); ierr = VecSetSizes(u,PETSC_DECIDE,N);CHKERRQ(ierr); ierr = VecSetFromOptions(u);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)u,"Approx. Solution");CHKERRQ(ierr); ierr = VecDuplicate(u,&b);CHKERRQ(ierr); ierr = PetscObjectSetName((PetscObject)b,"Right hand side");CHKERRQ(ierr); ierr = VecSet(u,1.0);CHKERRQ(ierr); ierr = MatMult(C,u,b);CHKERRQ(ierr); ierr = VecSet(u,0.0);CHKERRQ(ierr); /* Solve linear system */ ierr = KSPCreate(PETSC_COMM_WORLD,&ksp);CHKERRQ(ierr); ierr = KSPSetOperators(ksp,C,C,DIFFERENT_NONZERO_PATTERN);CHKERRQ(ierr); ierr = KSPSetFromOptions(ksp);CHKERRQ(ierr); ierr = KSPSetInitialGuessNonzero(ksp,PETSC_TRUE);CHKERRQ(ierr); flg = PETSC_FALSE; ierr = PetscOptionsGetBool(PETSC_NULL,"-fixnullspace",&flg,PETSC_NULL);CHKERRQ(ierr); if (flg) { ierr = MatNullSpaceCreate(PETSC_COMM_WORLD,PETSC_TRUE,0,PETSC_NULL,&nullsp);CHKERRQ(ierr); ierr = KSPSetNullSpace(ksp,nullsp);CHKERRQ(ierr); ierr = MatNullSpaceDestroy(&&nullsp);CHKERRQ(ierr); } ierr = KSPSolve(ksp,b,u);CHKERRQ(ierr); /* Free work space */ ierr = KSPDestroy(&ksp);CHKERRQ(ierr); ierr = VecDestroy(&u);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr); ierr = MatDestroy(&C);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
int main(int argc,char **args) { Mat C,A; PetscInt i, n = 10,midx[3],bs=1; PetscErrorCode ierr; PetscScalar v[3]; PetscBool flg,isAIJ; MatType type; PetscMPIInt size; PetscInitialize(&argc,&args,(char*)0,help); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,"-n",&n,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetInt(NULL,"-mat_block_size",&bs,NULL);CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&C);CHKERRQ(ierr); ierr = MatSetSizes(C,PETSC_DECIDE,PETSC_DECIDE,n,n);CHKERRQ(ierr); ierr = MatSetType(C,MATAIJ);CHKERRQ(ierr); ierr = MatSetFromOptions(C);CHKERRQ(ierr); ierr = MatGetType(C,&type);CHKERRQ(ierr); if (size == 1) { ierr = PetscObjectTypeCompare((PetscObject)C,MATSEQAIJ,&isAIJ);CHKERRQ(ierr); } else { ierr = PetscObjectTypeCompare((PetscObject)C,MATMPIAIJ,&isAIJ);CHKERRQ(ierr); } ierr = MatSeqAIJSetPreallocation(C,3,NULL); ierr = MatMPIAIJSetPreallocation(C,3,NULL,3,NULL);CHKERRQ(ierr); ierr = MatSeqBAIJSetPreallocation(C,bs,3,NULL); ierr = MatMPIBAIJSetPreallocation(C,bs,3,NULL,3,NULL);CHKERRQ(ierr); v[0] = -1.; v[1] = 2.; v[2] = -1.; for (i=1; i<n-1; i++) { midx[2] = i-1; midx[1] = i; midx[0] = i+1; ierr = MatSetValues(C,1,&i,3,midx,v,INSERT_VALUES);CHKERRQ(ierr); } i = 0; midx[0] = 0; midx[1] = 1; v[0] = 2.0; v[1] = -1.; ierr = MatSetValues(C,1,&i,2,midx,v,INSERT_VALUES);CHKERRQ(ierr); i = n-1; midx[0] = n-2; midx[1] = n-1; v[0] = -1.0; v[1] = 2.; ierr = MatSetValues(C,1,&i,2,midx,v,INSERT_VALUES);CHKERRQ(ierr); ierr = MatAssemblyBegin(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetSizes(A,PETSC_DECIDE,PETSC_DECIDE,n,n);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatSetUp(A);CHKERRQ(ierr); ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); /* test matrices with different nonzero patterns - Note: A is created with different nonzero pattern of C! */ ierr = MatCopy(C,A,DIFFERENT_NONZERO_PATTERN);CHKERRQ(ierr); ierr = MatEqual(A,C,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_SELF,1,"MatCopy(C,A,DIFFERENT_NONZERO_PATTERN): Matrices are NOT equal"); ierr = PetscViewerSetFormat(PETSC_VIEWER_STDOUT_WORLD,PETSC_VIEWER_ASCII_INFO);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"A is obtained with MatCopy(,,DIFFERENT_NONZERO_PATTERN):\n");CHKERRQ(ierr); ierr = MatView(A,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); /* test matrices with same nonzero pattern */ ierr = MatDuplicate(C,MAT_DO_NOT_COPY_VALUES,&A);CHKERRQ(ierr); ierr = MatCopy(C,A,SAME_NONZERO_PATTERN);CHKERRQ(ierr); ierr = MatEqual(A,C,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_SELF,1,"MatCopy(C,A,SAME_NONZERO_PATTERN): Matrices are NOT equal"); ierr = PetscViewerSetFormat(PETSC_VIEWER_STDOUT_WORLD,PETSC_VIEWER_ASCII_INFO);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"\nA is obtained with MatCopy(,,SAME_NONZERO_PATTERN):\n");CHKERRQ(ierr); ierr = MatView(A,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = PetscViewerSetFormat(PETSC_VIEWER_STDOUT_WORLD,PETSC_VIEWER_ASCII_COMMON);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"A:\n");CHKERRQ(ierr); ierr = MatView(A,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); /* test MatStore/RetrieveValues() */ if (isAIJ) { ierr = MatSetOption(A,MAT_NEW_NONZERO_LOCATIONS,PETSC_FALSE);CHKERRQ(ierr); ierr = MatStoreValues(A);CHKERRQ(ierr); ierr = MatZeroEntries(A);CHKERRQ(ierr); ierr = MatRetrieveValues(A);CHKERRQ(ierr); } ierr = MatDestroy(&C);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = PetscFinalize(); return 0; }
int main(int argc, char **argv) { MPI_Comm comm; SNES snes; /* nonlinear solver */ Vec u,r,b; /* solution, residual, and rhs vectors */ Mat A,J; /* Jacobian matrix */ PetscInt problem = 1, N = 10; PetscErrorCode ierr; ierr = PetscInitialize(&argc, &argv, NULL,help);if (ierr) return ierr; comm = PETSC_COMM_WORLD; ierr = PetscOptionsGetInt(NULL,NULL, "-problem", &problem, NULL);CHKERRQ(ierr); ierr = VecCreate(comm, &u);CHKERRQ(ierr); ierr = VecSetSizes(u, PETSC_DETERMINE, N);CHKERRQ(ierr); ierr = VecSetFromOptions(u);CHKERRQ(ierr); ierr = VecDuplicate(u, &r);CHKERRQ(ierr); ierr = VecDuplicate(u, &b);CHKERRQ(ierr); ierr = MatCreate(comm, &A);CHKERRQ(ierr); ierr = MatSetSizes(A, PETSC_DETERMINE, PETSC_DETERMINE, N, N);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatSeqAIJSetPreallocation(A, 5, NULL);CHKERRQ(ierr); J = A; switch (problem) { case 1: ierr = ConstructProblem1(A, b);CHKERRQ(ierr); break; case 2: ierr = ConstructProblem2(A, b);CHKERRQ(ierr); break; default: SETERRQ1(comm, PETSC_ERR_ARG_OUTOFRANGE, "Invalid problem number %d", problem); } ierr = SNESCreate(PETSC_COMM_WORLD, &snes);CHKERRQ(ierr); ierr = SNESSetJacobian(snes, A, J, ComputeJacobianLinear, NULL);CHKERRQ(ierr); ierr = SNESSetFunction(snes, r, ComputeFunctionLinear, A);CHKERRQ(ierr); ierr = SNESSetFromOptions(snes);CHKERRQ(ierr); ierr = SNESSolve(snes, b, u);CHKERRQ(ierr); ierr = VecView(u, NULL);CHKERRQ(ierr); switch (problem) { case 1: ierr = CheckProblem1(A, b, u);CHKERRQ(ierr); break; case 2: ierr = CheckProblem2(A, b, u);CHKERRQ(ierr); break; default: SETERRQ1(comm, PETSC_ERR_ARG_OUTOFRANGE, "Invalid problem number %d", problem); } if (A != J) { ierr = MatDestroy(&A);CHKERRQ(ierr); } ierr = MatDestroy(&J);CHKERRQ(ierr); ierr = VecDestroy(&u);CHKERRQ(ierr); ierr = VecDestroy(&r);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr); ierr = SNESDestroy(&snes);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
int main(int argc,char **argv) { DM da; /* distributed array */ Vec x,b,u; /* approx solution, RHS, exact solution */ Mat A; /* linear system matrix */ KSP ksp; /* linear solver context */ PetscRandom rctx; /* random number generator context */ PetscReal norm; /* norm of solution error */ PetscInt i,j,its; PetscErrorCode ierr; PetscBool flg = PETSC_FALSE; PetscLogStage stage; DMDALocalInfo info; ierr = PetscInitialize(&argc,&argv,(char*)0,help);if (ierr) return ierr; /* Create distributed array to handle parallel distribution. The problem size will default to 8 by 7, but this can be changed using -da_grid_x M -da_grid_y N */ ierr = DMDACreate2d(PETSC_COMM_WORLD, DM_BOUNDARY_NONE, DM_BOUNDARY_NONE,DMDA_STENCIL_STAR,-8,-7,PETSC_DECIDE,PETSC_DECIDE,1,1,NULL,NULL,&da);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Compute the matrix and right-hand-side vector that define the linear system, Ax = b. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ /* Create parallel matrix preallocated according to the DMDA, format AIJ by default. To use symmetric storage, run with -dm_mat_type sbaij -mat_ignore_lower_triangular */ ierr = DMCreateMatrix(da,&A);CHKERRQ(ierr); /* Set matrix elements for the 2-D, five-point stencil in parallel. - Each processor needs to insert only elements that it owns locally (but any non-local elements will be sent to the appropriate processor during matrix assembly). - Rows and columns are specified by the stencil - Entries are normalized for a domain [0,1]x[0,1] */ ierr = PetscLogStageRegister("Assembly", &stage);CHKERRQ(ierr); ierr = PetscLogStagePush(stage);CHKERRQ(ierr); ierr = DMDAGetLocalInfo(da,&info);CHKERRQ(ierr); for (j=info.ys; j<info.ys+info.ym; j++) { for (i=info.xs; i<info.xs+info.xm; i++) { PetscReal hx = 1./info.mx,hy = 1./info.my; MatStencil row = {0},col[5] = {{0}}; PetscScalar v[5]; PetscInt ncols = 0; row.j = j; row.i = i; col[ncols].j = j; col[ncols].i = i; v[ncols++] = 2*(hx/hy + hy/hx); /* boundaries */ if (i>0) {col[ncols].j = j; col[ncols].i = i-1; v[ncols++] = -hy/hx;} if (i<info.mx-1) {col[ncols].j = j; col[ncols].i = i+1; v[ncols++] = -hy/hx;} if (j>0) {col[ncols].j = j-1; col[ncols].i = i; v[ncols++] = -hx/hy;} if (j<info.my-1) {col[ncols].j = j+1; col[ncols].i = i; v[ncols++] = -hx/hy;} ierr = MatSetValuesStencil(A,1,&row,ncols,col,v,INSERT_VALUES);CHKERRQ(ierr); } } /* Assemble matrix, using the 2-step process: MatAssemblyBegin(), MatAssemblyEnd() Computations can be done while messages are in transition by placing code between these two statements. */ ierr = MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); ierr = PetscLogStagePop();CHKERRQ(ierr); /* Create parallel vectors compatible with the DMDA. */ ierr = DMCreateGlobalVector(da,&u);CHKERRQ(ierr); ierr = VecDuplicate(u,&b);CHKERRQ(ierr); ierr = VecDuplicate(u,&x);CHKERRQ(ierr); /* Set exact solution; then compute right-hand-side vector. By default we use an exact solution of a vector with all elements of 1.0; Alternatively, using the runtime option -random_sol forms a solution vector with random components. */ ierr = PetscOptionsGetBool(NULL,NULL,"-random_exact_sol",&flg,NULL);CHKERRQ(ierr); if (flg) { ierr = PetscRandomCreate(PETSC_COMM_WORLD,&rctx);CHKERRQ(ierr); ierr = PetscRandomSetFromOptions(rctx);CHKERRQ(ierr); ierr = VecSetRandom(u,rctx);CHKERRQ(ierr); ierr = PetscRandomDestroy(&rctx);CHKERRQ(ierr); } else { ierr = VecSet(u,1.);CHKERRQ(ierr); } ierr = MatMult(A,u,b);CHKERRQ(ierr); /* View the exact solution vector if desired */ flg = PETSC_FALSE; ierr = PetscOptionsGetBool(NULL,NULL,"-view_exact_sol",&flg,NULL);CHKERRQ(ierr); if (flg) {ierr = VecView(u,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr);} /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Create the linear solver and set various options - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ /* Create linear solver context */ ierr = KSPCreate(PETSC_COMM_WORLD,&ksp);CHKERRQ(ierr); /* Set operators. Here the matrix that defines the linear system also serves as the preconditioning matrix. */ ierr = KSPSetOperators(ksp,A,A);CHKERRQ(ierr); /* Set runtime options, e.g., -ksp_type <type> -pc_type <type> -ksp_monitor -ksp_rtol <rtol> These options will override those specified above as long as KSPSetFromOptions() is called _after_ any other customization routines. */ ierr = KSPSetFromOptions(ksp);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Solve the linear system - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = KSPSolve(ksp,b,x);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Check solution and clean up - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ /* Check the error */ ierr = VecAXPY(x,-1.,u);CHKERRQ(ierr); ierr = VecNorm(x,NORM_2,&norm);CHKERRQ(ierr); ierr = KSPGetIterationNumber(ksp,&its);CHKERRQ(ierr); /* Print convergence information. PetscPrintf() produces a single print statement from all processes that share a communicator. An alternative is PetscFPrintf(), which prints to a file. */ ierr = PetscPrintf(PETSC_COMM_WORLD,"Norm of error %g iterations %D\n",(double)norm,its);CHKERRQ(ierr); /* Free work space. All PETSc objects should be destroyed when they are no longer needed. */ ierr = KSPDestroy(&ksp);CHKERRQ(ierr); ierr = VecDestroy(&u);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&b);CHKERRQ(ierr); ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = DMDestroy(&da);CHKERRQ(ierr); /* Always call PetscFinalize() before exiting a program. This routine - finalizes the PETSc libraries as well as MPI - provides summary and diagnostic information if certain runtime options are chosen (e.g., -log_summary). */ ierr = PetscFinalize(); return ierr; }
int main(int argc,char **args) { Mat A[3],B; /* matrix */ PetscViewer fd; /* viewer */ char file[PETSC_MAX_PATH_LEN]; /* input file name */ PetscErrorCode ierr; PetscBool flg; Vec x,y,z,work; PetscReal rnorm; ierr = PetscInitialize(&argc,&args,(char*)0,help);if (ierr) return ierr; /* Determine files from which we read the two linear systems (matrix and right-hand-side vector). */ ierr = PetscOptionsGetString(NULL,NULL,"-f",file,PETSC_MAX_PATH_LEN,&flg);CHKERRQ(ierr); if (!flg) SETERRQ(PETSC_COMM_WORLD,1,"Must indicate binary file with the -f option"); /* Open binary file. Note that we use FILE_MODE_READ to indicate reading from this file. */ ierr = PetscViewerBinaryOpen(PETSC_COMM_WORLD,file,FILE_MODE_READ,&fd);CHKERRQ(ierr); /* Load the matrix; then destroy the viewer. */ ierr = MatCreate(PETSC_COMM_WORLD,&A[0]);CHKERRQ(ierr); ierr = MatLoad(A[0],fd);CHKERRQ(ierr); ierr = PetscViewerDestroy(&fd);CHKERRQ(ierr); ierr = MatDuplicate(A[0],MAT_COPY_VALUES,&A[1]);CHKERRQ(ierr); ierr = MatDuplicate(A[0],MAT_COPY_VALUES,&A[2]);CHKERRQ(ierr); ierr = MatShift(A[1],1.0);CHKERRQ(ierr); ierr = MatShift(A[1],2.0);CHKERRQ(ierr); ierr = MatCreateVecs(A[0],&x,&y);CHKERRQ(ierr); ierr = VecDuplicate(y,&work);CHKERRQ(ierr); ierr = VecDuplicate(y,&z);CHKERRQ(ierr); ierr = VecSet(x,1.0);CHKERRQ(ierr); ierr = MatMult(A[0],x,z);CHKERRQ(ierr); ierr = MatMultAdd(A[1],x,z,z);CHKERRQ(ierr); ierr = MatMultAdd(A[2],x,z,z);CHKERRQ(ierr); ierr = MatCreateComposite(PETSC_COMM_WORLD,3,A,&B);CHKERRQ(ierr); ierr = MatMult(B,x,y);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = VecAXPY(y,-1.0,z);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&rnorm);CHKERRQ(ierr); if (rnorm > 1.e-10) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with composite add %g\n",(double)rnorm);CHKERRQ(ierr); } ierr = MatCreateComposite(PETSC_COMM_WORLD,3,A,&B);CHKERRQ(ierr); ierr = MatCompositeMerge(B);CHKERRQ(ierr); ierr = MatMult(B,x,y);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = VecAXPY(y,-1.0,z);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&rnorm);CHKERRQ(ierr); if (rnorm > 1.e-10) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with composite add after merge %g\n",(double)rnorm);CHKERRQ(ierr); } ierr = VecSet(x,1.0);CHKERRQ(ierr); ierr = MatMult(A[0],x,z);CHKERRQ(ierr); ierr = MatMult(A[1],z,work);CHKERRQ(ierr); ierr = MatMult(A[2],work,z);CHKERRQ(ierr); ierr = MatCreateComposite(PETSC_COMM_WORLD,3,A,&B);CHKERRQ(ierr); ierr = MatCompositeSetType(B,MAT_COMPOSITE_MULTIPLICATIVE);CHKERRQ(ierr); ierr = MatMult(B,x,y);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = VecAXPY(y,-1.0,z);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&rnorm);CHKERRQ(ierr); if (rnorm > 1.e-10) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with composite multiplicative %g\n",(double)rnorm);CHKERRQ(ierr); } ierr = MatCreateComposite(PETSC_COMM_WORLD,3,A,&B);CHKERRQ(ierr); ierr = MatCompositeSetType(B,MAT_COMPOSITE_MULTIPLICATIVE);CHKERRQ(ierr); ierr = MatCompositeMerge(B);CHKERRQ(ierr); ierr = MatMult(B,x,y);CHKERRQ(ierr); ierr = MatDestroy(&B);CHKERRQ(ierr); ierr = VecAXPY(y,-1.0,z);CHKERRQ(ierr); ierr = VecNorm(y,NORM_2,&rnorm);CHKERRQ(ierr); if (rnorm > 1.e-10) { ierr = PetscPrintf(PETSC_COMM_WORLD,"Error with composite multiplicative after merge %g\n",(double)rnorm);CHKERRQ(ierr); } /* Free work space. All PETSc objects should be destroyed when they are no longer needed. */ ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&y);CHKERRQ(ierr); ierr = VecDestroy(&work);CHKERRQ(ierr); ierr = VecDestroy(&z);CHKERRQ(ierr); ierr = MatDestroy(&A[0]);CHKERRQ(ierr); ierr = MatDestroy(&A[1]);CHKERRQ(ierr); ierr = MatDestroy(&A[2]);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
int main(int argc,char **argv) { TS ts; /* ODE integrator */ Vec Y; /* solution will be stored here */ Mat A; /* Jacobian matrix */ PetscErrorCode ierr; PetscMPIInt size; PetscInt n = 6; PetscScalar *y; /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Initialize program - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = PetscInitialize(&argc,&argv,(char*)0,help);if (ierr) return ierr; ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); if (size > 1) SETERRQ(PETSC_COMM_WORLD,PETSC_ERR_SUP,"Only for sequential runs"); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Create necessary matrix and vectors - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetSizes(A,n,n,PETSC_DETERMINE,PETSC_DETERMINE);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatSetUp(A);CHKERRQ(ierr); ierr = MatCreateVecs(A,&Y,NULL);CHKERRQ(ierr); ierr = VecGetArray(Y,&y);CHKERRQ(ierr); y[0] = 0.0; y[1] = 3.0; y[2] = y[1]; y[3] = 6.0; y[4] = 0.0; y[5] = 0.0; ierr = VecRestoreArray(Y,&y);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Create timestepping solver context - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = TSCreate(PETSC_COMM_WORLD,&ts);CHKERRQ(ierr); ierr = TSSetProblemType(ts,TS_NONLINEAR);CHKERRQ(ierr); ierr = TSSetType(ts,TSARKIMEX);CHKERRQ(ierr); ierr = TSSetEquationType(ts,TS_EQ_DAE_IMPLICIT_INDEX1);CHKERRQ(ierr); ierr = TSARKIMEXSetFullyImplicit(ts,PETSC_TRUE);CHKERRQ(ierr); /*ierr = TSSetType(ts,TSROSW);CHKERRQ(ierr);*/ ierr = TSSetIFunction(ts,NULL,IFunctionImplicit,NULL);CHKERRQ(ierr); ierr = TSSetIJacobian(ts,A,A,IJacobianImplicit,NULL);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Set initial conditions - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = TSSetSolution(ts,Y);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Set solver options - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = TSSetDuration(ts,100000,0.15);CHKERRQ(ierr); ierr = TSSetExactFinalTime(ts,TS_EXACTFINALTIME_STEPOVER);CHKERRQ(ierr); ierr = TSSetInitialTimeStep(ts,0.0,.001);CHKERRQ(ierr); ierr = TSSetFromOptions(ts);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Do Time stepping - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = TSSolve(ts,Y);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Free work space. All PETSc objects should be destroyed when they are no longer needed. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = VecDestroy(&Y);CHKERRQ(ierr); ierr = TSDestroy(&ts);CHKERRQ(ierr); ierr = PetscFinalize(); return ierr; }
int main(int argc,char **argv) { TS ts; /* nonlinear solver */ Vec x; /* solution, residual vectors */ Mat A; /* Jacobian matrix */ Mat Jacp; /* JacobianP matrix */ PetscInt steps; PetscReal ftime =0.5; PetscBool monitor = PETSC_FALSE; PetscScalar *x_ptr; PetscMPIInt size; struct _n_User user; PetscErrorCode ierr; Vec lambda[2],mu[2]; /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Initialize program - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ PetscInitialize(&argc,&argv,NULL,help); ierr = MPI_Comm_size(PETSC_COMM_WORLD,&size);CHKERRQ(ierr); if (size != 1) SETERRQ(PETSC_COMM_SELF,1,"This is a uniprocessor example only!"); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Set runtime options - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ user.mu = 1; user.next_output = 0.0; ierr = PetscOptionsGetReal(NULL,"-mu",&user.mu,NULL);CHKERRQ(ierr); ierr = PetscOptionsGetBool(NULL,"-monitor",&monitor,NULL);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Create necessary matrix and vectors, solve same ODE on every process - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = MatCreate(PETSC_COMM_WORLD,&A);CHKERRQ(ierr); ierr = MatSetSizes(A,PETSC_DECIDE,PETSC_DECIDE,2,2);CHKERRQ(ierr); ierr = MatSetFromOptions(A);CHKERRQ(ierr); ierr = MatSetUp(A);CHKERRQ(ierr); ierr = MatCreateVecs(A,&x,NULL);CHKERRQ(ierr); ierr = MatCreate(PETSC_COMM_WORLD,&Jacp);CHKERRQ(ierr); ierr = MatSetSizes(Jacp,PETSC_DECIDE,PETSC_DECIDE,2,1);CHKERRQ(ierr); ierr = MatSetFromOptions(Jacp);CHKERRQ(ierr); ierr = MatSetUp(Jacp);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Create timestepping solver context - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = TSCreate(PETSC_COMM_WORLD,&ts);CHKERRQ(ierr); ierr = TSSetType(ts,TSRK);CHKERRQ(ierr); ierr = TSSetRHSFunction(ts,NULL,RHSFunction,&user);CHKERRQ(ierr); ierr = TSSetDuration(ts,PETSC_DEFAULT,ftime);CHKERRQ(ierr); ierr = TSSetExactFinalTime(ts,TS_EXACTFINALTIME_MATCHSTEP);CHKERRQ(ierr); if (monitor) { ierr = TSMonitorSet(ts,Monitor,&user,NULL);CHKERRQ(ierr); } /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Set initial conditions - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = VecGetArray(x,&x_ptr);CHKERRQ(ierr); x_ptr[0] = 2; x_ptr[1] = 0.66666654321; ierr = VecRestoreArray(x,&x_ptr);CHKERRQ(ierr); ierr = TSSetInitialTimeStep(ts,0.0,.001);CHKERRQ(ierr); /* Have the TS save its trajectory so that TSAdjointSolve() may be used */ ierr = TSSetSaveTrajectory(ts);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Set runtime options - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = TSSetFromOptions(ts);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Solve nonlinear system - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = TSSolve(ts,x);CHKERRQ(ierr); ierr = TSGetSolveTime(ts,&ftime);CHKERRQ(ierr); ierr = TSGetTimeStepNumber(ts,&steps);CHKERRQ(ierr); ierr = PetscPrintf(PETSC_COMM_WORLD,"mu %g, steps %D, ftime %g\n",(double)user.mu,steps,(double)ftime);CHKERRQ(ierr); ierr = VecView(x,PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Start the Adjoint model - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = MatCreateVecs(A,&lambda[0],NULL);CHKERRQ(ierr); ierr = MatCreateVecs(A,&lambda[1],NULL);CHKERRQ(ierr); /* Reset initial conditions for the adjoint integration */ ierr = VecGetArray(lambda[0],&x_ptr);CHKERRQ(ierr); x_ptr[0] = 1.0; x_ptr[1] = 0.0; ierr = VecRestoreArray(lambda[0],&x_ptr);CHKERRQ(ierr); ierr = VecGetArray(lambda[1],&x_ptr);CHKERRQ(ierr); x_ptr[0] = 0.0; x_ptr[1] = 1.0; ierr = VecRestoreArray(lambda[1],&x_ptr);CHKERRQ(ierr); ierr = MatCreateVecs(Jacp,&mu[0],NULL);CHKERRQ(ierr); ierr = MatCreateVecs(Jacp,&mu[1],NULL);CHKERRQ(ierr); ierr = VecGetArray(mu[0],&x_ptr);CHKERRQ(ierr); x_ptr[0] = 0.0; ierr = VecRestoreArray(mu[0],&x_ptr);CHKERRQ(ierr); ierr = VecGetArray(mu[1],&x_ptr);CHKERRQ(ierr); x_ptr[0] = 0.0; ierr = VecRestoreArray(mu[1],&x_ptr);CHKERRQ(ierr); ierr = TSSetCostGradients(ts,2,lambda,mu);CHKERRQ(ierr); /* Set RHS Jacobian for the adjoint integration */ ierr = TSSetRHSJacobian(ts,A,A,RHSJacobian,&user);CHKERRQ(ierr); /* Set RHS JacobianP */ ierr = TSAdjointSetRHSJacobian(ts,Jacp,RHSJacobianP,&user);CHKERRQ(ierr); ierr = TSAdjointSolve(ts);CHKERRQ(ierr); ierr = VecView(lambda[0],PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = VecView(lambda[1],PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = VecView(mu[0],PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); ierr = VecView(mu[1],PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Free work space. All PETSc objects should be destroyed when they are no longer needed. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ ierr = MatDestroy(&A);CHKERRQ(ierr); ierr = MatDestroy(&Jacp);CHKERRQ(ierr); ierr = VecDestroy(&x);CHKERRQ(ierr); ierr = VecDestroy(&lambda[0]);CHKERRQ(ierr); ierr = VecDestroy(&lambda[1]);CHKERRQ(ierr); ierr = VecDestroy(&mu[0]);CHKERRQ(ierr); ierr = VecDestroy(&mu[1]);CHKERRQ(ierr); ierr = TSDestroy(&ts);CHKERRQ(ierr); ierr = PetscFinalize(); PetscFunctionReturn(0); }