求素數篩法總結

2021-08-10 20:08:05 字數 814 閱讀 7631

當使用一般演算法 i->sqrt(n) 超時時, 就必須思考對整個程式的優化。

優化的地方在於降低重複率。即降低對2,4,6這種有共同因數的運算列舉,而只是對乙個更小的迴圈週期範圍(如6n演算法,任何乙個自然數都可以表述為6n,6n+1,6n+2,6n+3…6n+5,而顯然當n>=1時,6n,6n+2,6n+3,6n+4一定不為質數,即縮小了需要遍歷的範圍)甚至對素陣列來求解。

埃式篩法

演算法思想: 從2開始向下遍歷,每找到乙個素數,則從陣列中剔除以這個素數為因子的數(仍具有重複性的浪費,如6會在檢查2和檢查3時被重複剔除)

#define maxsize 100000

bool prime[max];

void isprime()

if(!prime[i])}}

}

此處仍可對函式進行部分優化。

將最後函式內的迴圈改為

for(int j = i*i,j <= max; j += 2*n) //進一步降低了重複率.
尤拉篩

與埃式篩法的區別:

埃式篩法有可能對乙個資料篩去多次,

而尤拉篩只用每個合數的最小質因數去篩。

#define max 1000000

int primes[max/3]; //大概..防止堆疊溢位

bool judge[max] = ;

void isprime()

for(int j = 0;i * primes[j] <= max;j++)}}

}

篩法求素數 線性篩法求素數

2021年更新版 篩法求素數 線性篩法求素數 要理解篩法求素數首先要知道乙個定理,整數唯一分解定理 任意大於等於2的正整數都有且只有一種方式寫出其質因子的乘積表示式。a p1p2p3p4 pn pi是素數且pi pj eg 2 2 4 22 12 223 36 2233 也就是說任意乙個合數都能分成...

素數篩法求素數

素數篩類似於打表標記,預先處理掉非素數的數,即素數的倍數 任意非素數都可以由幾個素數相乘得到 於是效率比暴力求解快得多。埃氏篩法的效率為o n loglog n 簡單易懂,但是會重複標記,比如當i為2時,6會被標記掉,然而當i為3時,6又會被重複標記,這樣的重複訪問加大了時間複雜度,於是有了尤拉篩。...

篩法求素數

素數篩法就是每次把已知的素數的倍數曬去,篩掉前sqrt n 中素數的倍數就可以了 先把n個自然數按次序排列起來。1不是質數,也不是合數,要划去。第二個數2是質數留下來,而把2後面所有能被2整除的數都劃去。2後面第乙個沒劃去的數是3,把3留下,再把3後面所有能被3整除的數都劃去。3後面第乙個沒劃去的數...