Actual source code: ex2.c
1: /*$Id: ex2.c,v 1.24 2001/03/23 23:23:50 balay Exp $*/
3: static char help[] = "Demonstrates running several independent tasks in PETSc.nn";
5: /*T
6: Concepts: SLES^solving linear equations
7: Processors: n
9: Comments: Demonstrates how to use PetscSetCommWorld() to tell a subset of
10: processors (in this case each individual processor) to run
11: as if it was all the processors that PETSc is using. ADVANCED
12: example, not for beginning PETSc users.
14: T*/
16: /*
17: Include "petscsles.h" so that we can use SLES solvers. Note that this file
18: automatically includes:
19: petsc.h - base PETSc routines petscvec.h - vectors
20: petscsys.h - system routines petscmat.h - matrices
21: petscis.h - index sets petscksp.h - Krylov subspace methods
22: petscviewer.h - viewers petscpc.h - preconditioners
23: */
24: #include petscsles.h
26: EXTERN int slesex(int,char**);
28: int main(int argc,char **argv)
29: {
30: MPI_Init(&argc,&argv);
31: slesex(argc,argv);
32: MPI_Finalize();
33: return 0;
34: }
36: int slesex(int argc,char **args)
37: {
38: Vec x,b,u; /* approx solution, RHS, exact solution */
39: Mat A; /* linear system matrix */
40: SLES sles; /* linear solver context */
41: PC pc; /* preconditioner context */
42: KSP ksp; /* Krylov subspace method context */
43: double norm; /* norm of solution error */
44: int i,j,I,J,Istart,Iend,ierr,m = 8,n = 7,its;
45: Scalar v,one = 1.0,none = -1.0;
47: PetscSetCommWorld(PETSC_COMM_SELF);
48: PetscInitialize(&argc,&args,(char *)0,help);
50: PetscOptionsGetInt(PETSC_NULL,"-m",&m,PETSC_NULL);
51: PetscOptionsGetInt(PETSC_NULL,"-n",&n,PETSC_NULL);
53: /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
54: Compute the matrix and right-hand-side vector that define
55: the linear system, Ax = b.
56: - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
57: /*
58: Create parallel matrix, specifying only its global dimensions.
59: When using MatCreate(), the matrix format can be specified at
60: runtime. Also, the parallel partitioning of the matrix is
61: determined by PETSc at runtime.
62: */
63: MatCreate(PETSC_COMM_WORLD,PETSC_DECIDE,PETSC_DECIDE,m*n,m*n,&A);
64: MatSetFromOptions(A);
66: /*
67: Currently, all PETSc parallel matrix formats are partitioned by
68: contiguous chunks of rows across the processors. Determine which
69: rows of the matrix are locally owned.
70: */
71: MatGetOwnershipRange(A,&Istart,&Iend);
73: /*
74: Set matrix elements for the 2-D, five-point stencil in parallel.
75: - Each processor needs to insert only elements that it owns
76: locally (but any non-local elements will be sent to the
77: appropriate processor during matrix assembly).
78: - Always specify global row and columns of matrix entries.
79: */
80: for (I=Istart; I<Iend; I++) {
81: v = -1.0; i = I/n; j = I - i*n;
82: if (i>0) {J = I - n; MatSetValues(A,1,&I,1,&J,&v,INSERT_VALUES);}
83: if (i<m-1) {J = I + n; MatSetValues(A,1,&I,1,&J,&v,INSERT_VALUES);}
84: if (j>0) {J = I - 1; MatSetValues(A,1,&I,1,&J,&v,INSERT_VALUES);}
85: if (j<n-1) {J = I + 1; MatSetValues(A,1,&I,1,&J,&v,INSERT_VALUES);}
86: v = 4.0; MatSetValues(A,1,&I,1,&I,&v,INSERT_VALUES);
87: }
89: /*
90: Assemble matrix, using the 2-step process:
91: MatAssemblyBegin(), MatAssemblyEnd()
92: Computations can be done while messages are in transition,
93: by placing code between these two statements.
94: */
95: MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY);
96: MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY);
98: /*
99: Create parallel vectors.
100: - When using VecCreate() and VecSetFromOptions(), we specify only the vector's global
101: dimension; the parallel partitioning is determined at runtime.
102: - Note: We form 1 vector from scratch and then duplicate as needed.
103: */
104: VecCreate(PETSC_COMM_WORLD,PETSC_DECIDE,m*n,&u);
105: VecSetFromOptions(u);
106: VecDuplicate(u,&b);
107: VecDuplicate(b,&x);
109: /*
110: Set exact solution; then compute right-hand-side vector.
111: */
112: VecSet(&one,u);
113: MatMult(A,u,b);
115: /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
116: Create the linear solver and set various options
117: - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
119: /*
120: Create linear solver context
121: */
122: SLESCreate(PETSC_COMM_WORLD,&sles);
124: /*
125: Set operators. Here the matrix that defines the linear system
126: also serves as the preconditioning matrix.
127: */
128: SLESSetOperators(sles,A,A,DIFFERENT_NONZERO_PATTERN);
130: /*
131: Set linear solver defaults for this problem (optional).
132: - By extracting the KSP and PC contexts from the SLES context,
133: we can then directly directly call any KSP and PC routines
134: to set various options.
135: - The following four statements are optional; all of these
136: parameters could alternatively be specified at runtime via
137: SLESSetFromOptions();
138: */
139: SLESGetKSP(sles,&ksp);
140: SLESGetPC(sles,&pc);
141: PCSetType(pc,PCJACOBI);
142: KSPSetTolerances(ksp,1.e-7,PETSC_DEFAULT,PETSC_DEFAULT,PETSC_DEFAULT);
144: /*
145: Set runtime options, e.g.,
146: -ksp_type <type> -pc_type <type> -ksp_monitor -ksp_rtol <rtol>
147: These options will override those specified above as long as
148: SLESSetFromOptions() is called _after_ any other customization
149: routines.
150: */
151: SLESSetFromOptions(sles);
153: /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
154: Solve the linear system
155: - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
157: SLESSolve(sles,b,x,&its);
159: /* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
160: Check solution and clean up
161: - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
163: /*
164: Check the error
165: */
166: VecAXPY(&none,u,x);
167: VecNorm(x,NORM_2,&norm);
168: PetscPrintf(PETSC_COMM_WORLD,"Norm of error %A iterations %dn",norm,its);
170: /*
171: Free work space. All PETSc objects should be destroyed when they
172: are no longer needed.
173: */
174: SLESDestroy(sles);
175: VecDestroy(u); VecDestroy(x);
176: VecDestroy(b); MatDestroy(A);
177: PetscFinalize();
178: return 0;
179: }