bzoj2048[2009国家集训队]书堆 数论
Posted GXZlegend
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了bzoj2048[2009国家集训队]书堆 数论相关的知识,希望对你有一定的参考价值。
题目描述
输入
第一行正整数 N M
输出
一行(有换行符),L,表示水平延伸最远的整数距离 (不大于答案的最大整数)
样例
#1
Input: 1 100
Output: 49
#2
Input: 2 100
Output: 74
题解
数论
一个结论:桌面上摆$n$本长度为$l$的书,不掉出桌面,能够伸出桌面的最大长度为$\frac 12l*H_n$,其中$H_n=\sum\limits_{i=1}^n\frac 1i$。
证明:设i本书按该条件摆放,它们的重心距离最下面的书的边缘的距离为$\frac12l*f(i)$,那么首先有$f(1)=1$,而考虑$i$本书的情况,上面的$i-1$本的重心一定是在第$i$本的边缘上。那么由杠杆原理,$(i-1)*f(i)=1*(1-f(i))$可知,故$f(i)=\frac 1i$。而每次都是重心落在边缘,所以伸出长度即为每次的重心与边缘的距离之和$H_n$。
但是$n$有$10^18$之大,直接暴力肯定使不可取的。考虑调和级数的近似值:$H_n\approx ln(n+1)+\gamma$,其中$\gamma$为欧拉常数,它约为0.57721566490153286060651209。
这个公式当$n$较小时误差较大,所以当$n$较小时考虑暴力求解,$n$较大时套用公式。
#include <cmath> #include <cstdio> typedef long long ll; int main() { ll n , m , i; double ans = 0; scanf("%lld%lld" , &n , &m); if(n <= 1000000) for(i = 1 ; i <= n ; i ++ ) ans += 0.5 / i; else ans = 0.5 * (log(n + 1) + 0.5772156649); ans *= m; printf("%d\n" , (int)(ans - 1e-9)); return 0; }
以上是关于bzoj2048[2009国家集训队]书堆 数论的主要内容,如果未能解决你的问题,请参考以下文章
BZOJ 2257: [Jsoi2009]瓶子和燃料数论:裴蜀定理
bzoj 2257[Jsoi2009]瓶子和燃料 数论/裴蜀定理
BZOJ 2039: [2009国家集训队]employ人员雇佣