Actual source code: ex18.c
2: static char help[] = "Computes the integral of 2*x/(1+x^2) from x=0..1 \nThis is equal to the ln(2).\n\n";
4: /*
5: Contributed by Mike McCourt <mccomic@iit.edu> and Nathan Johnston <johnnat@iit.edu>
6: */
8: /*
9: Include "petscvec.h" so that we can use vectors. Note that this file
10: automatically includes:
11: petscsys.h - base PETSc routines petscis.h - index sets
12: petscviewer.h - viewers
13: */
14: #include <petscvec.h>
16: PetscScalar func(PetscScalar a)
17: {
18: return (PetscScalar)2. * a / ((PetscScalar)1. + a * a);
19: }
21: int main(int argc, char **argv)
22: {
23: PetscMPIInt rank, size;
24: PetscInt rstart, rend, i, k, N, numPoints = 1000000;
25: PetscScalar dummy, result = 0, h = 1.0 / numPoints, *xarray;
26: Vec x, xend;
29: PetscInitialize(&argc, &argv, (char *)0, help);
30: MPI_Comm_rank(PETSC_COMM_WORLD, &rank);
31: MPI_Comm_size(PETSC_COMM_WORLD, &size);
33: /*
34: Create a parallel vector.
35: Here we set up our x vector which will be given values below.
36: The xend vector is a dummy vector to find the value of the
37: elements at the endpoints for use in the trapezoid rule.
38: */
39: VecCreate(PETSC_COMM_WORLD, &x);
40: VecSetSizes(x, PETSC_DECIDE, numPoints);
41: VecSetFromOptions(x);
42: VecGetSize(x, &N);
43: VecSet(x, result);
44: VecDuplicate(x, &xend);
45: result = 0.5;
46: if (rank == 0) {
47: i = 0;
48: VecSetValues(xend, 1, &i, &result, INSERT_VALUES);
49: }
50: if (rank == size - 1) {
51: i = N - 1;
52: VecSetValues(xend, 1, &i, &result, INSERT_VALUES);
53: }
54: /*
55: Assemble vector, using the 2-step process:
56: VecAssemblyBegin(), VecAssemblyEnd()
57: Computations can be done while messages are in transition
58: by placing code between these two statements.
59: */
60: VecAssemblyBegin(xend);
61: VecAssemblyEnd(xend);
63: /*
64: Set the x vector elements.
65: i*h will return 0 for i=0 and 1 for i=N-1.
66: The function evaluated (2x/(1+x^2)) is defined above.
67: Each evaluation is put into the local array of the vector without message passing.
68: */
69: VecGetOwnershipRange(x, &rstart, &rend);
70: VecGetArray(x, &xarray);
71: k = 0;
72: for (i = rstart; i < rend; i++) {
73: xarray[k] = (PetscScalar)i * h;
74: xarray[k] = func(xarray[k]);
75: k++;
76: }
77: VecRestoreArray(x, &xarray);
79: /*
80: Evaluates the integral. First the sum of all the points is taken.
81: That result is multiplied by the step size for the trapezoid rule.
82: Then half the value at each endpoint is subtracted,
83: this is part of the composite trapezoid rule.
84: */
85: VecSum(x, &result);
86: result = result * h;
87: VecDot(x, xend, &dummy);
88: result = result - h * dummy;
90: /*
91: Return the value of the integral.
92: */
93: PetscPrintf(PETSC_COMM_WORLD, "ln(2) is %g\n", (double)PetscRealPart(result));
94: VecDestroy(&x);
95: VecDestroy(&xend);
97: PetscFinalize();
98: return 0;
99: }
101: /*TEST
103: test:
104: nsize: 1
106: test:
107: nsize: 2
108: suffix: 2
109: output_file: output/ex18_1.out
111: TEST*/