static const char help[] = "Uses KSPComputeRitz() on a matrix loaded from disk\n"; #include int main(int argc, char **argv) { Mat A; KSP ksp; char file[PETSC_MAX_PATH_LEN]; PetscReal *tetar, *tetai; Vec b, x, *S; PetscInt i, N = 10, Na = N; PetscViewer fd; PC pc; PetscBool harmonic = PETSC_FALSE; PetscFunctionBeginUser; PetscCall(PetscInitialize(&argc, &argv, 0, help)); PetscCall(PetscOptionsGetString(NULL, NULL, "-f", file, sizeof(file), NULL)); PetscCall(PetscViewerBinaryOpen(PETSC_COMM_WORLD, file, FILE_MODE_READ, &fd)); PetscCall(MatCreate(PETSC_COMM_WORLD, &A)); PetscCall(MatLoad(A, fd)); PetscCall(PetscViewerDestroy(&fd)); PetscCall(MatView(A, PETSC_VIEWER_STDOUT_WORLD)); PetscCall(MatCreateVecs(A, &b, &x)); PetscCall(VecSetRandom(b, NULL)); PetscCall(VecDuplicateVecs(b, N, &S)); PetscCall(PetscMalloc2(N, &tetar, N, &tetai)); PetscCall(KSPCreate(PETSC_COMM_WORLD, &ksp)); PetscCall(KSPSetType(ksp, KSPGMRES)); PetscCall(KSPSetTolerances(ksp, 10000 * PETSC_MACHINE_EPSILON, PETSC_CURRENT, PETSC_CURRENT, PETSC_CURRENT)); PetscCall(KSPGetPC(ksp, &pc)); PetscCall(PCSetType(pc, PCNONE)); PetscCall(KSPSetComputeRitz(ksp, PETSC_TRUE)); PetscCall(KSPSetOperators(ksp, A, A)); PetscCall(KSPSetFromOptions(ksp)); PetscCall(KSPSolve(ksp, b, x)); PetscCall(PetscOptionsHasName(NULL, NULL, "-harmonic", &harmonic)); PetscCall(KSPComputeRitz(ksp, harmonic ? PETSC_FALSE : PETSC_TRUE, PETSC_TRUE, &Na, S, tetar, tetai)); PetscCall(PetscPrintf(PETSC_COMM_WORLD, "%% Number of Ritz pairs %" PetscInt_FMT "\n", Na)); for (i = 0; i < Na; i++) { PetscCall(PetscPrintf(PETSC_COMM_WORLD, "%% Eigenvalue(s) %g ", (double)tetar[i])); if (tetai[i]) { PetscCall(PetscPrintf(PETSC_COMM_WORLD, "%+gi", (double)tetai[i])); #if !defined(PETSC_USE_COMPLEX) PetscCall(PetscPrintf(PETSC_COMM_WORLD, " %g ", (double)tetar[i])); PetscCall(PetscPrintf(PETSC_COMM_WORLD, "%+gi", (double)-tetai[i])); #endif } PetscCall(PetscPrintf(PETSC_COMM_WORLD, "\n")); PetscCall(PetscPrintf(PETSC_COMM_WORLD, "%% Eigenvector\n")); PetscCall(VecView(S[i], PETSC_VIEWER_STDOUT_WORLD)); #if !defined(PETSC_USE_COMPLEX) if (tetai[i]) { PetscCall(PetscPrintf(PETSC_COMM_WORLD, "%% Imaginary part of Eigenvector\n")); PetscCall(VecView(S[i + 1], PETSC_VIEWER_STDOUT_WORLD)); i++; } #endif } PetscCall(PetscFree2(tetar, tetai)); PetscCall(VecDestroy(&x)); PetscCall(VecDestroy(&b)); PetscCall(VecDestroyVecs(N, &S)); PetscCall(KSPDestroy(&ksp)); PetscCall(MatDestroy(&A)); PetscCall(PetscFinalize()); return 0; } /*TEST test: requires: !defined(PETSC_USE_64BIT_INDICES) !complex double args: -f ${wPETSC_DIR}/share/petsc/datafiles/matrices/ritz2 -ksp_monitor test: suffix: 2 requires: !defined(PETSC_USE_64BIT_INDICES) !complex double args: -f ${wPETSC_DIR}/share/petsc/datafiles/matrices/ritz5 -ksp_monitor test: suffix: harmonic requires: !defined(PETSC_USE_64BIT_INDICES) !complex double args: -f ${wPETSC_DIR}/share/petsc/datafiles/matrices/ritz5 -ksp_monitor -harmonic TEST*/