欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

Java parallel programming to calculate PI using Dart algorithm

程序员文章站 2022-04-01 17:21:54
...

study it, I don’t want to explain too much about these code segment. Starting from :
public class TestDartThread
at the end of this article.
you can change long num_trails = 1000000000 to make it shorter according to your hardware.

public class MyTimer {
    private static long begin;

    public static void time_start(){
        begin = System.nanoTime();
    }

    public static double time_end_milli_seconds(){
        return System.nanoTime()-begin/1e6;

    }

    public static double time_end_seconds(){
        double total_time =  (System.nanoTime()-begin)/1e6;
        return ((double)((int)total_time))/1000;

    }

}
public class DartThread extends Thread{

    public long hitting_times=0;
    public long begin_index=0;
    public long numtrials=0;

    public DartThread(long begin_index,long numtrials) {
        this.begin_index = begin_index;
        this.numtrials = numtrials;
    }

    @Override
    public void run() {
        hit_point();
    }

    // radius = 1
    public boolean hit_in_circle(double x,double y){
        return (x*x+y*y)<=1?true:false;
    }

    // Evaluate ( ax+c ) mod m

    long modlin(long a, long x, long c, long m)
    {
        return (a * x + c) % m;
    }
    // Put integer n in range x1 , x2 with the maximum integer value
    double rescale(long N, long n, double x1, double x2)
    {
        double f = Double.valueOf(n)/Double.valueOf(N);
        return x1 + f * (x2 - x1);
    }

    public void hit_point() {
        // For the s e q u e n t i a l random number generator
        long a = 1664525;
        long c = 1013904223;
        long m = 4294967296L;
        long sidelen = 65536;


        // s q r t of m
        // long numtrials = 1000000;
        long i_prev = 12345; // Seed value
        for (long n = begin_index; n < numtrials; n+=4) {

            long i_next = modlin(a, i_prev, c, m);
            i_prev = i_next;

            // Scale the random number to a random 2−d position
            long ix = i_next % sidelen;
            long iy = i_next / sidelen;

            // Scale current random integer to value from 0−1
            double x = rescale(sidelen, ix, -1, 1);
            double y = rescale(sidelen, iy, -1, 1);
            // Now we have an (x , y) pair generated from a s i n g l e random integer

            if (hit_in_circle(x, y)) {
                hitting_times++;
            }

        }
    }
}
public class TestDartThread {

    // radius = 1
    public static boolean hit_in_circle(double x,double y){
        return (x*x+y*y)<=1?true:false;
    }

    // Evaluate ( ax+c ) mod m

    static long modlin(long a, long x, long c, long m)
    {
        return (a * x + c) % m;
    }
    // Put integer n in range x1 , x2 with the maximum integer value
    static double rescale(long N, long n, double x1, double x2)
    {
        double f = Double.valueOf(n)/Double.valueOf(N);
        return x1 + f * (x2 - x1);
    }

    public static double parallel(long num_trails) throws InterruptedException {

        MyTimer.time_start();

        long hitting_times_result = 0;

        DartThread thread1 = new DartThread(1,num_trails);
        thread1.start();

        DartThread thread2 = new DartThread(2,num_trails);
        thread2.start();

        DartThread thread3 = new DartThread(3,num_trails);
        thread3.start();

        DartThread thread4 = new DartThread(4,num_trails);
        thread4.start();

        thread1.join();
        thread2.join();
        thread3.join();
        thread4.join();

        hitting_times_result += thread1.hitting_times + thread2.hitting_times + thread3.hitting_times+ thread4.hitting_times;

        double time_end = MyTimer.time_end_seconds();

        //System.out.println("parallel time elapse: "+ time_end);
        System.out.println("parallel time elapse: "+ time_end+"s parallel hitting times: "+hitting_times_result);
        double pi = 4*(Double.valueOf(hitting_times_result)/Double.valueOf(num_trails));
        System.out.println("parallel PI : "+pi);

        return time_end;
    }

    public static double sequential(long numtrials){

        MyTimer.time_start();

        // For the s e q u e n t i a l random number generator
        long a = 1664525;
        long c = 1013904223;
        long m = 4294967296L;
        long sidelen = 65536;

        long hit_times = 0;
        // s q r t of m
        // long numtrials = 1000000;
        long i_prev = 12345; // Seed value
        for (long n = 0; n < numtrials; ++n) {

            long i_next = modlin(a, i_prev, c, m);
            i_prev = i_next;

            // Scale the random number to a random 2−d position
            long ix = i_next % sidelen;
            long iy = i_next / sidelen;

            // Scale current random integer to value from 0−1
            double x = rescale(sidelen, ix, -1, 1);
            double y = rescale(sidelen, iy, -1, 1);
            // Now we have an (x , y) pair generated from a s i n g l e random integer

            if(hit_in_circle(x,y))
            {
                hit_times++;
            }

        }

        double end_time = MyTimer.time_end_seconds();
        System.out.println("sequential time elapse : "+end_time+"s sequential hitting times: "+hit_times);
        double pi = 4*(Double.valueOf(hit_times)/Double.valueOf(numtrials));
        System.out.println(" sequential PI : "+pi);

        return end_time;
    }


    public static void main(String[] args) throws InterruptedException {
        long num_trails = 1000000000;
      System.out.println("speed up: "+sequential(num_trails)/parallel(num_trails));

    }
}

sequential time elapse : 19.278s sequential hitting times: 785383696
sequential PI : 3.141534784
parallel time elapse: 6.429s parallel hitting times: 785401631
parallel PI : 3.141606524
speed up: 2.998600093327111