線性篩法
[介紹]
今天特地學了下線篩,感覺棒棒噠。。。線性篩法,顧名思義,就是每個數篩一遍,即每個合數只標記一
次,我們知道,一個合數可以寫成一個素數和一個數的乘積的形式,而要想每個數篩一遍,需要找到每個數
的獨特之處,每個合數都有唯一的最小質因數,這樣我們篩t這個數時確保枚舉的素數p是t的最小質因數即
可,每這樣個合數都有最小質因數,這樣所有合數都可以篩掉,又每個合數只有唯一確定的最小質因數,因
此每個合數只被篩一次,這是大致思想,根據下面的代碼理解一下
#include<cstdio>
using namespace std;
const int maxnp = 1000000;
bool isp[maxnp];
int prime[maxnp];
int number = 0;
int main()
{
for(int i = 2; i <= maxnp; i++)
{
if(!isp[i])
prime[number++] = i;
for(int j = 0; j < number && i*prime[j] <= maxnp; j++)
{
isp[i*prime[j]] = true;
if (i % prime[j] == 0)
break;
}
}
}
[思考]
通過枚舉素數p與數k的乘積來篩數(廢話…..),關鍵會如何確保要篩掉的數(p*k)的最小質因子是p呢?只要
確保k中不含有比p小的質因子就可以了啊。
if (i % prime[j] == 0) break;
當i中含有prime[j]這個因子時,k* prime[j + 1]、k*prime[j + 2]等等都不在合法了,因爲他們的最小質因
子應該是primej[j + 1]、prime[j + 2]
最大公約數
[吐槽]
gcd(a,b)常寫作(a,b), 滿足(a,b)=(a+k*b,b)
int gcd(int a, int b)
{
if (!b)
return a;
return gcd(b, a % b);
}
快速冪
[介紹]3^
快速冪的思想實際上就是把b寫成二進制的形式,即:
a^13=a^1101=a^(8 + 4 + 1)=a^8 * a^4 * a
然後對於a^1、a^2、a^4、a^8等便可以通過logb的複雜度自身相乘出來
int quick(int a, int b)
{
int ans = 1;
while (b)
{
if (b & 1)
ans *= a;
a *= a;
b /= 2;
}
return ans;
}