View Single Post
Old 17-09-2014, 15:43   #18
DoctorT
Senior Member
 
Iscritto dal: Jul 2005
Messaggi: 736
intanto posto la mia implementazione in java :

Codice:
import java.util.BitSet;
import java.util.Vector;
import java.lang.Math;
import java.io.*;

class Eratostene{
    
	static int segmented_sieve(long limit, int segment_size) {
		int sqrt = (int) Math.sqrt((double)limit);
		int count = 1;
		long s = 2;
		long n = 3;
		
		BitSet sieve = new BitSet(segment_size);
		// togli il commento se vuoi i numeri stampati a video
		// System.out.println(2);
		System.out.println("sqrt="+ sqrt);
		
		// crea un array di numeri primi < di sqrt(limit)
		
		boolean[] is_prime = new boolean[sqrt+1];
		for (int i=0;i<=sqrt;i++) is_prime[i] = true;
		for (int i = 2; i * i <= sqrt; i++)
		  {
			if (is_prime[i])
				for (int j = i * i; j <= sqrt; j += i)
					is_prime[j] = false;
		}
	
		Vector<Integer> primes = new Vector<Integer> ();
		Vector<Integer> next = new Vector<Integer> ();
		
		for (long low = 0; low <= limit; low += segment_size)
		{
			sieve.set(0, segment_size-1);		
			// current segment = interval [low, high]
			long high = Math.min(low + segment_size - 1,  limit) ;
			// memorizza i primi occorrenti per incrociare i multiple
			for (; s * s <= high; s++)
			{
				if (is_prime[(int)s])
				{
					primes.add((int)s);
					next.add((int)(s * s - low));
				}
			}
		
			// crivello per il segmento corrente
			for (int i = 1; i < primes.size(); i++)
			{
				int j = next.get(i);
				for (int k = primes.get(i) * 2; j < segment_size; j += k)
					sieve.clear(j);
				next.set(i, j - segment_size);
			}

			for (; n <= high; n += 2) // ricerca i bit con indice dispari
				if (sieve.get((int)(n - low))) // n is a prime
				{
					count++;
					// togli il commento se vuoi i numeri stampati a video
					// System.out.println(n); 
				}
		};
		return count;
	}
	
	public static void main(String [] args) throws IOException {	

		int sieve_size = 65536;
		long n = 8000000000L;
		long inizio = System.nanoTime();

		System.out.println("Attendere");	
		System.out.println("generazione numeri primi ..."); 
		System.out.println("I primi generati sono: " + segmented_sieve(n,sieve_size));

		long fine = System.nanoTime();
		float time = (fine-inizio)/1000000;
		System.out.println(time + " ms");

	} // end main
} // end class
il tempo di esecuzione sul mio sistema è di circa 130 secondi ... mi sa che c'è un bel po' da ottimizzare
__________________
O.S.: WIN 10 64-bit CPU: INTEL I5 12400F RAM: 16 GB Corsair Vengeance LPX 3200 Mhz VGA: MSI ARMOR RX570 4GB OC MOBO: ASROCK B660M PRO RS HDD: Seagate 1TB SDD: CRUCIAL MX500 500GB ALI: BE QUIET PURE POWER CM 11 600W
DoctorT è offline   Rispondi citando il messaggio o parte di esso