Liczby pierwsze spoj

0

Mam problem z tym zadaniem. Wiem, że powinienem je wykonać za pomocą sita Eratostenesa ale najpierw chcę poznać błąd jaki poczyniłem w moim rozwiązaniu.
http://pl.spoj.com/problems/PRIME_T/

import java.util.ArrayList;
import java.util.Scanner;

public class Pierwsze {

	public static void main(String[] args) {

		ArrayList<Integer> lista = new ArrayList<Integer>();
		Scanner skaner = new Scanner(System.in);

		int ileLiczb = skaner.nextInt();

		for (int i = 0; i < ileLiczb; i++) {
			lista.add(skaner.nextInt());
		}

		for (int i = 0; i < ileLiczb; i++) {

			int ile = 0;

			if (lista.get(i) <= 2) {
				System.out.println("NIE");
			}

			else {

				for (int j = 2; j <= Math.sqrt(lista.get(i)); j++) {

					if (lista.get(i) % j == 0) {
						ile++;
					}

				}

				if (ile > 0) {
					System.out.println("NIE");
				} else {

					System.out.println("TAK");
				}
			}

		}

	}

}
0

Dobra znalazłem. W końcu 2 jest liczbą pierwszą. :)

0

Napisałem taki kod i otrzymuje "Przekroczono limit czasu ". Nie wiem czy coś niepoprawnie napisałem czy rzeczywiście przekroczyłem czas -Limit czasu wykonania programu: 5s wiec wydaje mi się to mało prawdopodobne. U nie program działa poprawnie a przynajmniej tak mi się zdaje

import java.util.*;
import java.lang.*;

class Main
{
	public static void main (String[] args) throws java.lang.Exception
	{
		int tablica[] = new int[100000];
		int p=0;

		ArrayList<Integer> liczba = new ArrayList<Integer>();
		Scanner skaner = new Scanner(System.in);

		int ileLiczb = skaner.nextInt();

		for (int i = 0; i < ileLiczb; i++) {
			liczba.add(skaner.nextInt());
		}

		for (int j = 0; j < ileLiczb; j++) {

			for (int y = 1; y <= 100000 - 1; y++)
				tablica[y] = y;
			tablica[1] = 0;

			for (int i = 2; i <= Math.sqrt(liczba.get(j)); i++) {
				if (tablica[i] != 0) {
					p = i + i;
					while (p <= liczba.get(j)) {
						tablica[p] = 0;
						p += i;
					}
				}
			}

			if (tablica[liczba.get(j)] == 0)
				System.out.println("NIE");
			else
				System.out.println("TAK");

		}
	}
}
0

Eee, zdajesz sobie sprawę, że dla każdej iteracji od 0 do 100k ustawiasz wartości zmiennej tablica?

0

piszesz o Sicie Eratostenesa, a go nie używasz!

0

Zanim zaczniesz sprawdzać, czy liczba jest pierwsza czy nie, skorzystaj z Sita i usuń z niego wszystkie liczby złożone. I Sito przygotuj raz, nie dla każdej liczby z osobna. Wtedy czas działania drastycznie spadnie.

0

dzięki za podpowiedzi
udało mi się napisać taki kod, kod uzyskał czas 0,51 więc wciąż bez szału. Wie ktoś co mogę jeszcze zmienić aby kod działał szybciej?

import java.util.*;
import java.lang.*;

class Main
{
	public static void main (String[] args) throws java.lang.Exception
	{
		
		int p;
		int najwieksza;
		

		ArrayList<Integer> liczba = new ArrayList<Integer>();
		
		Scanner skaner = new Scanner(System.in);
		int ileLiczb = skaner.nextInt();

		for (int i = 0; i < ileLiczb; i++) {
			liczba.add(skaner.nextInt());
		}
		
		najwieksza= liczba.get(0);
		for(int i=0;i<ileLiczb;i++){
			
			if(liczba.get(i)>najwieksza)
			najwieksza = liczba.get(i);
			
		}
		
		int tablica[] = new int[najwieksza+1];
		for (int y = 2; y <= najwieksza; y++)
			tablica[y] = y;
			tablica[1] = 0;
		

			for (int i = 2; i <= najwieksza; i++) {
				if (tablica[i] != 0) {
					p = i + i;
					while (p <= najwieksza) {
						tablica[p] = 0;
						p += i;
					}
				}
			}

			for (int x = 0; x < ileLiczb; x++) {
			if (tablica[liczba.get(x)] == 0)
				System.out.println("NIE");
			else
				System.out.println("TAK");
			

		}

	}
}
0
import math
import sys

pierw = [2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97]


def czypierw(liczba):
	if liczba < 2:
		return False
	pierwiast = math.sqrt(liczba)
	for dzielnik in pierw:
		if dzielnik > pierwiast:
			return True
		if liczba % dzielnik == 0:
			return False
	return True


ileliczb = int(sys.stdin.readline())
lista = []
for i in range(0, 10001):
	lista.append(czypierw(i))
for test in range(ileliczb):
	liczba = int(sys.stdin.readline())
	if lista[liczba] is True:
		sys.stdout.write("TAK\n")
	else:
		sys.stdout.write("NIE\n")

Nie znam javy, ale masz kod w Pythonie3 na 0.14s. To prosty język powinieneś się połapać co i jak. Ten sam algorytm w c++ przechodzi w 0.1s więc bardzo go raczej nie przyśpieszysz (no chyba że wkleisz "na sztywno" tablicę tych 10000 zer lub jedynek). Generalnie założenie jest takie że skoro maksymalna liczba na wejściu to 10000, a pierwiastek z niej to 100 (liczba nie pierwsza), więc każda nie pierwsza liczba będzie podzielna przez liczbę pierwszą mniejszą niż 100.

1 użytkowników online, w tym zalogowanych: 0, gości: 1