多少个约数

简介: 多少个约数

问题描述


给定正整数 a, b, c,请问有多少个正整数,是其中至少两个数的约数。


输入格式


输入一行包含三个正整数 a, b, c。


输出格式


输出一行包含一个整数,表示答案。


样例输入


30 70 35


样例输出


6


样例说明


1、2、5、7、10、35满足条件。


评测用例规模与约定


对于 50% 的评测用例,1 <= a, b, c <= 1000000。

对于所有评测用例,a, b, c 不超过 10**12(10的12次方)。


大致思路


首先进行分解质因数,存入map中。然后利用容斥原理,可以得到如下表达式(Q a . . b 表示a…b的公约数数量)


image.png

可求出答案数。

#include <iostream>
#include <string>
#include <stack>
#include <vector>
#include <queue>
#include <map>
#include <set>
#include <algorithm>
#include <cmath>
typedef long long ll;
using namespace std;
int main() {
    ll a, b, c;
    cin >> a >> b >> c;
    map<ll, ll> sa, sb, sc;
    for (int i = 2; i <= a && a != 1; i++) {
        while (a % i == 0) {
            sa[i]++;
            a = a / i;
        }
    }
    for (int i = 2; i <= b && b != 1; i++) {
        while (b % i == 0) {
            sb[i]++;
            b = b / i;
        }
    }
    for (int i = 2; i <= c && c != 1; i++) {
        while (c % i == 0) {
            sc[i]++;
            c = c / i;
        }
    }
    ll cab = 0, cbc = 0, cac = 0, cabc = 0;
    for (map<ll, ll>::iterator it = sa.begin(); it != sa.end(); it++) {
        cab += min(it->second, sb[it->first]);
        cac += min(it->second, sc[it->first]);
        cabc += min(min(it->second, sc[it->first]), sb[it->first]);
    }
    for (map<ll, ll>::iterator it = sb.begin(); it != sb.end(); it++) {
        cbc += min(it->second, sc[it->first]);
    }
    cout << pow(2, cab) + pow(2, cac) + pow(2, cbc) - 2 * pow(2, cabc) << endl;
    return 0;
}
相关文章
|
3月前
|
移动开发 算法
求其最大公约数和最小公倍数
求其最大公约数和最小公倍数。
81 5
|
6月前
|
移动开发 算法
最大公约数和最小公倍数
【6月更文挑战第8天】最大公约数和最小公倍数。
69 9
|
6月前
每日一数——最大公约数与最小公倍数
每日一数——最大公约数与最小公倍数
|
7月前
|
算法
详解最大公约数和最小公倍数
详解最大公约数和最小公倍数
|
算法 C语言 C++
【数论】最大公约数、约数的个数与约数之和定理
先来科普下什么是约数:当a能被b整除,我们就说b为a的约数,b的倍数为a
135 0
|
人工智能 BI
求最大公约数和最小公倍数
求最大公约数和最小公倍数
92 0
求最大公约数最小公倍数
求最大公约数最小公倍数
120 0
AcWing 724. 约数
AcWing 724. 约数
81 0
AcWing 724. 约数