001    import java.io.BufferedReader;
002    import java.io.IOException;
003    import java.io.InputStreamReader;
004    
005    import mpp.*;
006    
007    /**
008     * Computes Pi. To compile and run:
009     *  javac -classpath mpp.jar Pi.java
010     *  java -classpath mpp.jar:. Pi
011     */
012    public class Pi {
013    
014      public static void main(String[] args) throws IOException {
015        Communicator comm = new BlockCommunicator();
016        BufferedReader read =
017          new BufferedReader(new InputStreamReader(System.in));
018    
019        int size = comm.size(), rank = comm.rank();
020    
021        while (true) {
022          int[] n = new int[1];
023          if (rank == 0) {
024            System.out.print("Enter the number of intervals: (0 quits) ");
025            n[0] = Integer.parseInt((read.readLine()+" 0").trim().split(" ")[0]);
026          }
027    
028          long startTime = System.currentTimeMillis();
029          comm.bcast(n, 0);
030    
031          if (n[0] == 0)
032            break;
033    
034          double[] pi = compPi(size, rank, n[0]);
035          double[] mypi = new double[1];
036          comm.reduce(pi, mypi, Reductions.sum(), 0);
037    
038          long endTime = System.currentTimeMillis() - startTime;
039          if (rank == 0) {
040            System.out.println(
041              "pi is approximately "
042                + mypi[0]
043                + ", error is "
044                + Math.abs(mypi[0] - Math.PI));
045            System.out.println("time is " + endTime / 1000. + " seconds");
046          }
047        }
048    
049        comm.close();
050      }
051    
052      private static double[] compPi(int size, int rank, int n) {
053        double h = 1. / n;
054        double sum = 0.;
055        for (int i = rank + 1; i < n; i += size) {
056          double x = h * (i - 0.5);
057          sum += (4. / (1. + x * x));
058        }
059    
060        return new double[] { h * sum };
061      }
062    }