All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.coode.oppl.utils.PrimeNumbersUtils Maven / Gradle / Ivy

package org.coode.oppl.utils;

import java.util.ArrayList;
import java.util.List;

/** @author Luigi Iannone */
public class PrimeNumbersUtils {
    /** Retrieves the first n prime numbers
     * 
     * @param n
     *            a non-negative integer
     * @return The first n prime numbers. */
    public static List getNPrimes(int n) {
        if (n < 0) {
            throw new IllegalArgumentException(
                    "The input n must be >=0, it is in fact:  " + n);
        }
        int upperBound = n * 10;
        List primes = runEratosthenesSieve(upperBound);
        boolean enough = primes.size() >= n;
        while (!enough) {
            upperBound += upperBound;
            primes = runEratosthenesSieve(upperBound);
            enough = primes.size() >= n;
        }
        return primes.subList(0, n);
    }

    /** @param upperBound
     *            upperBound
     * @return list of primes */
    public static List runEratosthenesSieve(int upperBound) {
        int upperBoundSquareRoot = (int) Math.sqrt(upperBound);
        List toReturn = new ArrayList(upperBound / 2);
        boolean[] isComposite = new boolean[upperBound + 1];
        for (int m = 2; m <= upperBoundSquareRoot; m++) {
            if (!isComposite[m]) {
                for (int k = m * m; k <= upperBound; k += m) {
                    isComposite[k] = true;
                }
            }
        }
        for (int m = 1; m <= upperBound; m++) {
            if (!isComposite[m]) {
                toReturn.add(m);
            }
        }
        return toReturn;
    }

    /** @param n
     *            n
     * @return next prime from n */
    public static int getNextPrime(int n) {
        int toReturn = n + 1;
        boolean found = isPrime(toReturn);
        while (!found) {
            toReturn++;
            found = isPrime(toReturn);
        }
        return toReturn;
    }

    /** @param n
     *            n
     * @return true if prime */
    public static boolean isPrime(int n) {
        // int dividersUpperbound = (int) Math.sqrt(n);
        // boolean found = false;
        // for (int i = 2; i < dividersUpperbound && !found; i++) {
        // found = n % i == 0;
        // }
        // return !found;
        return millerRabin32(n);
    }

    // Primality Test function source
    // http://en.literateprograms.org/Miller-Rabin_primality_test_(Java)
    private static boolean millerRabinPass32(int a, int n) {
        // 32-bit compute s and d
        int d = n - 1;
        int s = Integer.numberOfTrailingZeros(d);
        d >>= s;
        int a_to_power = modularExponent32(a, d, n);
        if (a_to_power == 1) {
            return true;
        }
        for (int i = 0; i < s - 1; i++) {
            if (a_to_power == n - 1) {
                return true;
            }
            a_to_power = modularExponent32(a_to_power, 2, n);
        }
        if (a_to_power == n - 1) {
            return true;
        }
        return false;
    }

    private static int modularExponent32(int base, int power, int modulus) {
        long result = 1;
        for (int i = 31; i >= 0; i--) {
            result = result * result % modulus;
            if ((power & 1 << i) != 0) {
                result = result * base % modulus;
            }
        }
        return (int) result; // Will not truncate since modulus is an int
    }

    /** @param n
     *            n
     * @return true if prime */
    public static boolean millerRabin32(int n) {
        if (n <= 1) {
            return false;
        } else if (n == 2) {
            return true;
        } else if (millerRabinPass32(2, n) && (n <= 7 || millerRabinPass32(7, n))
                && (n <= 61 || millerRabinPass32(61, n))) {
            return true;
        } else {
            return false;
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy