题解:P17070 [ICPC 2017 Shenyang R] Heron and His Triangle
前置知识
题目大意
一个三角形的三条边长分别为三个连续整数 \(t-1\)、\(t\)、\(t+1\),且其面积为整数,对于给定的 \(n\),你需要找出满足 \(t \ge n\) 的最小 \(t\) 所对应的且其面积为整数的三角形。
思路
先根据海伦公式求出这个三角形的面积:
\[S=\sqrt{p(p-t)(p-t-1)(p-t+1)}
\]
然后 \(p=\frac{(t-1)+t+(t+1)}{2}=\frac{3t}{2}\),
\[\begin{aligned}
\therefore S&=\sqrt{\frac{3t}{2}\times\frac{t}{2}\times(\frac{t}{2}+1)\times(\frac{t}{2}-1)}\\
&=\sqrt{\frac{3t^2}{4} \times (\frac{t^2}{4}-1)}\\
&=\frac{t}{4}\times\sqrt{3(t^2-4)}\\
\end{aligned}\]
所以 \(3(t^2-4)\) 为整数。
设 \(3(t^2-4)=9y^2\),则有:\(t^2-3y^2=12\)。
这是一个佩尔方程,可以知道 \(t_n=4t_{n-1}-t_{n-2}\)。
初始化为:\(t_1=4\),\(t_2=14\),往后递推即可。
我们注意到 \(t\) 一定是一个偶数,所以 \(4 \mid 3(t^2-4)\),因此 \(S\) 一定是一个整数。
代码就很简单了:
#include <bits/stdc++.h>
using namespace std;
int t;
__int128 n,ma=1;
vector<__int128>v;
__int128 read(){
__int128 a=0;
char c=getchar();
while(c<'0'||c>'9')c=getchar();
while(c>='0'&&c<='9'){
a=a*10+c-48;
c=getchar();
}
return a;
}
void write(__int128 a){
if(a>9)write(a/10);
putchar(a%10+48);
}
int main(){
for(int i=0;i<30;++i)ma*=10;
v.push_back(4);
v.push_back(14);
while(v[v.size()-1]<=ma){
int sz=v.size()-1;
v.push_back(4*v[sz]-v[sz-1]);
}
cin>>t;
while(t--){
n=read();
int l=0,r=v.size();
while (l<r){//二分查找出第一个满足条件的数
int mid=l+r>>1;
if (v[mid]>=n)r=mid;
else l=mid+1;
}
if(v[l]>=n){
write(v[l]);
putchar('\n');
}else puts("-1");
}
return 0;
}

浙公网安备 33010602011771号