[CP / Codefroces] B. A Balanced Problemset?(Div. 2)

B. A Balanced Problemset?

分析

本题考查 GCD(Greatest Common Divisor, 最大公约数) 的性质。
很惭愧,这道题我不会做,于是我看了 editorial,并学到了新知识:

GCD(a1,a2,a3,,an)=GCD(a1,a1+a2,a1+a2+a3,,a1+a2+a3++an)

证明:

da1,a2,a3,,an 的公约数,即有 d | ai 对于 1in 均成立,由整除的性质知 d |i=1kai 对于 1kn 成立,即 da1,a1+a2,a1+a2+a3,,a1+a2+a3++an 的约数。

反过来,若 d |i=1kai 对于 1kn 成立,因为 i=1kaii=1k1ai=ak, 2kn,所以 d | ai 对于 1in 均成立,即 da1,a2,a3,,an 的公约数。

综上,a1,a2,a3,,an 的约数和 a1,a1+a2,a1+a2+a3,,a1+a2+a3++an 完全相同,那么它们的最大公约数也相等了。

回到本题,由上面的结论知, x 无论如何被拆分,拆分出来的所有项的最大公约数一定是 x 的约数,这是一个必要条件,所以 “枚举所有的约数” 至少不会让我们漏掉答案。问题在于,这个约数和我们想要的最大公约数究竟有什么数学上的关系?仅仅求出约数还不足以得到最终答案!

x 的某个约数为 d,即 d | x,显然有 xd | x,或者说 xd 也是 x 的约数,所以 x 可以被分为 dxd 或者 xdd。我们的目标是:检查约数 dxd 是否可以作为拆分后的 n 个数的最大公约数。

结论是:当 dnxdn 时,另一方(xdd)可以作为拆分后的 n 个数的最大公约数,因为满足上述条件时,始终可以构造出形如 d,d,,x(n1)d 这样的序列,使得最大公约数为 d

代码

void solve()
{
int n, x;
std::cin >> x >> n;
int ans = 0;
for (int i = 1; i * i <= x; i++)
{
if (x % i == 0)
{
// two divisors: i and x / i
auto d2 = x / i;
if (i >= n)
ans = std::max(ans, d2);
if (d2 >= n)
ans = std::max(ans, i);
}
}
std::cout << ans << '\n';
}
posted @   ZXPrism  阅读(4)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· winform 绘制太阳,地球,月球 运作规律
· AI与.NET技术实操系列(五):向量存储与相似性搜索在 .NET 中的实现
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 上周热点回顾(3.3-3.9)
点击右上角即可分享
微信分享提示