给你一个整数数组
nums
,请你返回该数组中恰有四个因数的这些整数的各因数之和。如果数组中不存在满足题意的整数,则返回0
。
思路:
假设这个数是n,质因数分解后可以写成
n=a1^k1*a2^k2*……*ai^ki
所求的数的因数和f(n)就等于
f(n)=(1+a1+a1^2+……+a1^k1)*(1+a2+a2^2+……+a2^k2)*……*(1+ai+ai^2+……+ai^ki)
然后根据等比数列求和
f(n)=(a1^(k1+1)-1)/(a1-1)*(a2^(k2+1)-1)/(a2-1)*……*(ai^(ki+1)-1)/(ai-1)
(1)根据因子数的公式M=(e1+1)(e2+1)……*(en+1)得出x=pq或x=p^3;
(2)情况一:n =(p+1)*(q+1);
情况二:n = p^3+p^2+p+1;
#define maxn 100001 #define ll long long /*定义全局变量*/ bool f[maxn];//定义bool数组,标记是否为素数(以1代表非素) int primes[maxn];//记录所有素数 void ethPrime() { ll j; f[0] = f[1] = 1;//0和1当然是非素了 primes[0] = 0;//充当计数器作用 for(int i = 2;i < maxn;i++){ if(!f[i]){//从2开始,逻辑很完美 primes[++primes[0]] = i; for(j = (ll)i * i; j < maxn;j += i){//埃氏素数筛 f[j] = 1; } } } } bool isPrime(int x) { return !f[x]; } int sumFourDivisors(int* nums, int numsSize){ int p,q; int ans = 0; ethPrime(); for(int i = 0;i < numsSize;i++){//遍历数组每一个元素 for(int j = 1; j <= primes[0];j++){//prime[0]记录素数个数,遍历每一个素数 p = primes[j];//从第一个素数开始遍历 if(nums[i] % p == 0){ q = nums[i] / p; if(isPrime(q) && q != p){//q是素数以及pq不相等,那么就符合情况一 ans += (p+1)*(q+1); } if(q ==(ll) p * p){//因为q = nums[i] / p,所以符合情况二 ans += (p*p*p) + (p*p) + p + 1; } break; } } } return ans; }