poj1183 反正切函数
第一道poj的题更博,类似于博主这种英文水平,也就切一切这种中文题了吧!
题目大意:给你正整数a,求满足条件的 b 和 c,使得 $\frac {1}{a}=\frac {\frac {1}{b}+\frac{1}{c}}{1-\frac {1}{b\cdot c}}$,且 b + c 的和最小。
注释:1<=a<=60,000
想法:乍一看,数论啊!嘻嘻嘻嘻,好开心,但是没做出来。问了一下神犇CK蛤学长,掌握了一种极猛的处理数论变换的方法。由题目所给的式子可以得到
$b\cdot c-1=a\cdot b+a\cdot c$
$\mathrm {\Rightarrow {(b-a)}\cdot c=a\cdot b+1}$
$\mathrm {\Rightarrow c=\frac{a\cdot b+1}{b-a}}$
$\mathrm {\Rightarrow c=\frac{a\cdot {(b-a+a)}+1}{b-a}}$
$\mathrm {\Rightarrow b+c=b+a+\frac{a^2+1}{b-a}}$
$\mathrm {\Rightarrow b+c=b-a+2\cdot a+\frac{a^2+1}{b-a}}$
设b-a为t
$\mathrm {\Rightarrow b+c=t+2\cdot a+\frac{a^2+1}t}$
得出
$\mathrm {f(t)=t+2\cdot a+\frac{a^2+1}t}$
之后枚举$a^2+1$的所有不大于$\sqrt{a^2+1}$的所有约数,找到最小的,更新即可
最后,附上丑陋的代码......
#include <iostream>
#include <cstdio>
#include <cmath>
typedef long long ll;
using namespace std;
int main()
{
int a;
while(~scanf("%d",&a))
{
ll all=(ll)a*a+;
ll k=(ll)(sqrt(all*1.0));
ll ans=1ll<<;
for(ll i=;i<=k;i++)
{
if(all%i==) ans=min(ans,i+all/i+*a);
}
printf("%lld\n",ans);
}
return ;
}
小结:这东西,码出来就不该有错吧......
转载请注明:http://www.cnblogs.com/ShuraK/p/7880273.html——未经博主允许,严禁转载