题解:AtCoder abc420 G

AtCoder abc420 G 题解

题意

给定整数 \(X\),找出所有的 \(n\) 使得 \(\sqrt {n^2+n+X}\) 是一个整数

数据规模与约定

  • \(-10^{14} \le X \le 10^{14}\)

  • 输入的 \(X\) 为整数

需要的算法

数论

题意

转化题意:求出所有的 \(k\),使得 \(n^2+n+X=k^2\)

对等式 \(n^2+n+X=k^2\) 配方和变形:

\[\begin{align*} n^{2}+n + X&=k^{2}\\ 4n^{2}+4n + 4X&=4k^{2}\\ 4n^{2}+4n + 1-1 + 4X&=4k^{2}\\ (2n + 1)^{2}-1 + 4X&=4k^{2}\\ (2n + 1)^{2}-4k^{2}&=1 - 4X \end{align*} \]

根据平方差公式 \(a^2 - b^2 = (a-b)(a+b)\),则有:

\[(2n+1-2k)(2n+1+2k)=1-4X \]

\(1-4X\) 记作 \(C\)

\(a=2n+1-2k,b=2n+1+2k\),则有:

\[a+b=(2n-1-2k)+(2n-1+2k)=4n+2 \]

移项得:

\[4n=a+b-2 \]

最后得:

\[n=\frac{a+b-2}{4} \]

这时,问题被转化为:

寻找所有的因数对 \((a,b)\),使得 \(a \times b = C\) 并且 \((a+b-2) \mod 4 = 0\)

Code

#include <bits/stdc++.h>
using namespace std;
/*====================*/
typedef long long ll;
/*====================*/
#define endl '\n'
/*====================*/
void Solve(void)
{
    ll x;cin>>x;
    ll d_1=1-4*x;
    ll d_2=abs(d_1);
    set<ll> fact;
    for(ll d=1;d*d<=d_2;d++)
    {
        if(d_2%d==0)
        {
            fact.insert(d);
            fact.insert(d_2/d);
            fact.insert(-d);
            fact.insert(-d_2/d);
        }
    }
    set<ll> ans;
    for(auto a:fact)
    {
        ll b=d_1/a;
        ll c=a+b;
        if((c-2)%4==0)
        {
            ll n=(c-2)/4;
            ans.insert(n);
        }
    }
    cout<<ans.size()<<endl;
    for(auto it=ans.begin();it!=ans.end();it++)cout<<*it<<" ";
    cout<<endl;
}
/*====================*/
int main()
{
#ifndef ONLINE_JUDGE
    freopen("IN.txt","r+",stdin);
#endif
    ios::sync_with_stdio(false);
    cin.tie(nullptr),cout.tie(nullptr);
    int T=1;//cin>>T;
    while(T--)Solve();
    return 0;
}

posted @ 2025-08-24 22:36  yufh  阅读(27)  评论(0)    收藏  举报
浏览器标题切换
浏览器标题切换end