diff --git a/GESP/Level5/GESP202506/T2.cpp b/GESP/Level5/GESP202506/T2.cpp index 59e4ec3..51e8feb 100644 --- a/GESP/Level5/GESP202506/T2.cpp +++ b/GESP/Level5/GESP202506/T2.cpp @@ -1,26 +1,50 @@ -#include -#include +#include using namespace std; -const int N = 1e5 + 5; -int n, q, a[N], g; +const int N = 1e5 + 5; // 数组最大长度,根据题目数据范围设定 +int n, q; // n:整数个数,q:查询次数 +int a[N]; // 存储输入的n个整数 +int g; // 存储差分数组的最大公约数 +/** + * 计算两个数的最大公约数 + * @param a 第一个整数 + * @param b 第二个整数 + * @return a和b的最大公约数 + * @note 特殊处理:如果其中一个数为0,返回两数之和(即非零数本身) + */ int gcd(int a, int b) { if (a == 0 || b == 0) - return a + b; - return gcd(b, a % b); + return a + b; // 处理0的情况:gcd(0, x) = x + return gcd(b, a % b); // 递归实现欧几里得算法 +} + +// 最大公约数,辗转相除法 +int gcd(int a, int b) { + return b ? gcd(b, a % b) : a; } int main() { - scanf("%d%d", &n, &q); + // 读取整数个数n和查询次数q + cin >> n >> q; + + // 读取n个整数到数组a中 for (int i = 1; i <= n; i++) - scanf("%d", &a[i]); + cin >> a[i]; + + // 对数组进行排序,便于后续计算差分数组 sort(a + 1, a + n + 1); + + // 计算差分数组的最大公约数 + // 数学原理:gcd(a1+x, a2+x, ..., an+x) = gcd(gcd(a2-a1, a3-a1, ..., an-a1), a1+x) for (int i = 2; i <= n; i++) - g = gcd(g, a[i] - a[i - 1]); + g = gcd(g, a[i] - a[i - 1]); // 递推计算相邻元素差的最大公约数 + + // 处理q次查询 for (int i = 1; i <= q; i++) { - int x; - scanf("%d", &x); + int x; // 查询的参数x + cin >> x; + // 计算并输出gcd(g, a[1]+x),即为所求的所有数加x后的最大公约数 printf("%d\n", gcd(g, a[1] + x)); } return 0;