1 条题解
-
0
自动搬运
来自洛谷,原作者为

Great_Influence
**搬运于
2025-08-24 21:31:58,当前版本为作者最后更新于2017-12-10 19:51:17,作者可能在搬运后再次修改,您可在原文处查看最新版自动搬运只会搬运当前题目点赞数最高的题解,您可前往洛谷题解查看更多
以下是正文
高中数学题。
首先,对于固定的数字,可以得到关于划分块数的函数。然后开始求导。
对两边同时取对数,得
求导,得
所以
可以知道,当时,恒大于0
而为减函数
所以单调递减,在有极大值
而
所以当即时,取得极大值。
然而需要注意,为整数。所以,应该为或者
分别计算这两个点对应的函数值取max即可。
不好算?可以对原函数取对数,再比较对数即可。
然后便得到了。然后需要处理是否无限小数。
这个更简单。容易知道为有限小数当且仅当
所以直接强行把除掉所有的因子和因子就可以了。
注意提前除去。
代码:
#include<bits/stdc++.h> #include<cctype> #define For(i,a,b) for(i=(a),i##end=(b);i<=i##end;++i) #define Forward(i,a,b) for(i=(a),i##end=(b);i>=i##end;--i) #define Rep(i,a,b) for(register int i=(a),i##end=(b);i<=i##end;++i) #define Repe(i,a,b) for(register int i=(a),i##end=(b);i>=(b);--i) using namespace std; template<typename T>inline void read(T &x){ T s=0,f=1;char k=getchar(); while(!isdigit(k)&&k^'-')k=getchar(); if(!isdigit(k)){f=-1;k=getchar();} while(isdigit(k)){s=s*10+(k^48);k=getchar();} x=s*f; } void file(void){ #ifndef ONLINE_JUDGE freopen("water.in","r",stdin); freopen("water.out","w",stdout); #endif } const int MAXN=110001; static int n; const long double e=2.71828182845904523536; inline void init() { read(n); } inline long double calc(int f,int x) { return x*log((long double)f/x); } inline void solve() { static int ans1; static int ans=0; Rep(i,5,n) { ans1=floor(i/e); if(calc(i,ans1)<calc(i,ans1+1))++ans1; ans1/=__gcd(ans1,i); while(ans1%2==0)ans1/=2; while(ans1%5==0)ans1/=5; if(ans1!=1)ans+=i; else ans-=i; } printf("%d\n",ans); } int main(void){ file(); init(); solve(); return 0; }
- 1
信息
- ID
- 892
- 时间
- 1000ms
- 内存
- 125MiB
- 难度
- 5
- 标签
- 递交数
- 0
- 已通过
- 0
- 上传者