1 求最大公约数
int gcd (int a, int b){
return b ? gcd(b, a % b) : a;
}
2 求最大公倍数
int gcd (int a, int b){
return b ? gcd(b, a % b) : a;
}
int mcu(int a, int b) {
int t = gcd(a, b);
return a * b / t;
}
3 判断是否为质数
- 判断是否为质数(试除法)
bool is_prime(int x)
{
if (x < 2) return false;
for (int i = 2; i <= x / i; i ++ )
if (x % i == 0)
return false;
return true;
}
- 筛选质数
- 朴素筛选
const int N = 100010;
int primes[N];
int st[N], cnt = 0;
void get_primes(int n) // 朴素筛选
{
for (int i = 2; i <= n; i ++ )
{
if (!st[i]) primes[cnt ++ ] = i;
for (int j = i + i; j <= n; j += i )
st[j] = 1;
}
}
时间复杂度:O(nlogn)
- 朴素优化
int primes[N];
int st[N], cnt = 0;
void get_primes(int n) // 朴素筛选
{
for (int i = 2; i <= n; i ++ )
{
if (!st[i]){ // 将质数的倍数筛掉
primes[cnt ++] = i;
for (int j = i + i; j <= n; j += i )
st[j] = 1;
}
}
}
时间复杂度接近O(n)
线性筛法
const int N = 100010;
int primes[N];
int cnt = 0;
// 保证每个数被自己的最小质因子筛掉
void get_primes(int n) // 线性筛质数
{
for (int i = 2; i <= n; i ++ )
{
if (!st[i]) primes[cnt ++ ] = i;
for (int j = 0; primes[j] <= n / i; j ++ )
{
st[primes[j] * i] = true;
// 如果判断成立则primes[j]是i的最小质因子
// 如果判断不成立, primes[j]一定是小于i的
// 所有质因子,因此primes[j]一定是i * primes[j]
// 的最小质因子
if (i % primes[j] == 0) break;
}
}
}
时间复杂度O(n)
4 分解质因数
void divide(int x) {
for (int i = 2; i <= x / i; i ++) {
if (x % i == 0) {
int s = 0;
while(x % i == 0) {
s ++;
x /= i;
}
// 包含s个质因子i
cout << i << " "<< s << endl;
}
}
// 有且只有一个大于根号x的质因子,如果存在就删除
if (x > 1) cout << x << ' ' << 1 << endl;
cout << endl;
}
5 求约数个数
如果 N = p1^c1 * p2^c2 * … *pk^ck (分解质因数, 所有的约数一定可以用这些质因子的不同选法相乘得到)由此得到下面的个数公式:
(c1 + 1) * (c2 + 1) * … * (ck + 1) (次数 + 1相乘)
unordered_map<int, int> primes;
while (n -- )
{
int x;
cin >> x;
for (int i = 2; i <= x / i; i ++ )
while (x % i == 0)
{
x /= i;
primes[i] ++ ;
}
if (x > 1) primes[x] ++ ;
}
LL res = 1;
for (auto p : primes) res = res * (p.second + 1) % mod;
约数之和: (p1^0 + p1^1 + … + p1^c1) * … * (pk^0 + pk^1 + … + pk^ck) (乘出来,每一项都是一个约数)
unordered_map<int, int> primes;
while (n -- )
{
int x;
cin >> x;
for (int i = 2; i <= x / i; i ++ )
while (x % i == 0)
{
x /= i;
primes[i] ++ ;
}
if (x > 1) primes[x] ++ ;
}
LL res = 1;
for (auto p : primes)
{
LL a = p.first, b = p.second;
LL t = 1;
while (b -- ) t = (t * a + 1) % mod;
res = res * t % mod;
}
资料来源:
https://www.acwing.com/
鸣谢:
yxc YYDS