Отвратително огромен цикъл, излишно сложен,
Сметна ли изобщо колко ти е максималния брой итереации? При положение че имаме по дефалт 2499 итерации на j + броя на итерациите за i e = на аритметична прогресия 3+5+7+...+4999, общия брой итерации + това че извършваш допълнителни действия, закръгляне, корен, и делене със проверка за остатъка, направо майко мила..
Ами ако исках да сметна до 1 милион простите числа какво правим?
Първо като ще се пише алгоритъм и то още повече математически най-добре прочети, кой ще ти е най-изгоден от програмистка гледна точка, компютъра няма безкраен ресурс за товарене.
После вече помисли как би го завъртял със цикъл,
Най-простия алгоритъм(за числа по-малки от 10 милиона) за намиране на прости числа е на Ератостен(Eratosthenes), идеята е следната:
Числото едно не е просто, поради очевидни причини(дели се само на себе си, 1).
Започваме от числото 2, то е просто, записваме го в външен списък,
След това като първо просто число го използваме за да определим кои след него не са прости, защото ако се делят, на 2 то тогава са композитни(съставни, съставните числа са тези, които не са прости без 0,1).
Всяко число след 2 до n(числото до което търсим простите числа) трябва дабъде подложено на тази проверка, докато не стигнем до умножение x*2, което ще даде резултат по-голям от n.
Същата проверка се повтаря, когато стигнем до числото 3, ако е просто го записваме, ако е съставно го пропускаме, ако стигнем до съставно число, което сме определили вече(каквото е числото 4), то тогава минаваме направо на 5 и така.
Това е идеята на алгоритъма, ето го и нагледно:

Сега със алгоритъма на лице е време да си зададем въпроса как да го имплементираме най-добре с програмен език, как ще бъде най ефикасен и как да си спестим най-много итерации.
Започваме така(ще пиша на c++, мога да го преведа и на Delphi ако се наложи)
Код:
int top_number = 5000;
int prime_numbers[top_number];
//Записваме 2,3 като първите прости числа
prime_numbers[] = 2;
prime_numbers[] = 3;
for(int i = 4; i <= top_number; i++){
/*
Проверка за просто число, най простата проверка, а именно дали се дели на 2 без остатък, я правим винаги първа, за да е максимално бърз алгоритъма, така ако числото е четно итерацията ще минава без други проверки.
*/
//ако мине проверката продължаваме с цикъла
if(i % prime_numbers[0] == 0) continue;
/*
Ако остановим че не е минала проверката за четно число, значи имаме нечетно, но дали е просто? За да сме сигурни използваме другите прости числа вече записани в масива prime_numbers Ако не е четно и масива е само с един елемент, то тогава е ясно че сме на числото 3, всяко друго ще е по-голямо от 3 Но не е изгодно от гледна точка на ресурс на компютъра да броим всеки път колко е голям масива, тъйкато знам че след 2 веднага следва просто число за това цикъла започва от 4; с други думи записали сме вече 2 елемента в масива и продължаваме нататък. Алгоритъма ще работи и ако не го направим, но е важно да е бърз и ефикасен.
*/
/*
Ако не мине проверката, циклим простите числа, които сме записали започвайки от най-малките, тъйкато е най-голяма вероятноста числото в моментната итерация да се дели на по-малко число от колкото на по-голямо. Забележи че пропускам първия елемент, тъйкато вече съм го проверил по горе.
*/
int current_array_count = count(prime_numbers);
for(int i2 = 1; i2 < current_array_count; i2++){
//ако числото се окаже съставно спираме вътрешния цикъл
if(i % prime_numbers[i2] == 0) break;
/*
ако се окаже че не е така записвам числото, разбирам че трябва да го запиша ако цикъла е стигнал до последна итерация, без да открие деление без остатък
*/
if(i2 == current_array_count - 1) prime_numbers[] = i;
}
}
/*
В края на цикъла в масива prime_numbers ще разполагаш с всички прости числа.
*/