约数之和
题目描述:
输入A,B,求
的所有约数之和在 下的值
思路:
根据唯一分解定理可以把A分解成:
则
所以约数之和
所以我们只需要解决因数分解以及求类似
假设
- x是偶数时,利用指数相乘时底数不变,指数想加的方法可以得出 $sum(a,x) = sum(a, x/2) + sum(a, x/2)*a^{x/2}$
- x是奇数时,只需要把最后一项拿出来,则可以利用偶数方法计算,
这其实就是递归的过程
当然,这个题的模数只有9901,任何一个数字的幂次最多经过9900次就会产生重复,所以我们可以记录循环节来直接计算
,计算一次最多需要循环9901次,A最多也就十几个质因子,所以复杂度差不多是1e5级别的
#include<bits/stdc++.h>
using namespace std;
#define endl '\n'
#define io ios::sync_with_stdio(false), cin.tie(0), cout.tie(0)
#define m_p(a, b) make_pair(a, b)
typedef long long ll;
typedef pair<int, int> pii;
#define MAX 300005
#define mod 9901
int n, m, d, x, k;
ll sum[MAX];
ll p_qow(ll a, ll b){
ll ans = 1;
while(b){
if(b&1)ans = (ans * a) % mod;
(a *= a) %= mod;
b >>= 1;
}
return ans;
}
ll fuck(ll x, ll k){
if(k == 1)return 1;
if(k % 2 == 0){
return (fuck(x, k/2) * (1ll + p_qow(x, k/2)))%mod;
}
else return (fuck(x, k-1) + p_qow(x, k-1))%mod;
}
void work(){
cin >> n >> m;
ll ans = 1ll;
for(ll i = 2; i * i <= n; ++i){
if(n % i == 0){
ll num = 0;
while(n % i == 0){
++num;
n /= i;
}
num *= m;
(ans *= fuck(i, num+1))%=mod;
}
}
if(n > 1)(ans *= fuck(n, 1+m))%=mod;
if(!n)cout << 0 << endl;
else cout << ans << endl;
}
int main(){
//int t;cin >> t;while(t--)
work();
return 0;
}