[NOIp2012] 国王游戏(排序 + 贪心 + 高精度)

题意

给你两个长为 n+1 的数组 a,b ,你需要定义一个顺序 pp0 永远为 0

能够最小化

maxi=1nj=0iapjbpi

1n1000,1a,b104

题解

开始把原来没做完的 NOIp 题都水掉qwq

类似这种题都需要有个巧妙的排序方法,使得答案最小,其实可以大力找规律或者猜结论发现按 ai×bi 排序是最优秀的。

我们尝试推导这个结论。

其实我们发现只需要考虑相邻两个数如何交换才是最优的,因为任意排列都可以由交换相邻两个数得到。

假设当前两个位置为 i,i+1 ,记 p=j=0i1aj

我们令 ans0 为交换前的最大值,ans1 为交换后的,那么有

{ans0=max{pbi,p×aibi+1}ans1=max{pbi+1,p×ai+1bi}

因为有

i,ai,bi1

不难发现有

{p×aibi+1pbi+1p×ai+1bipbi

所以当 ans1ans0 也就是交换后不会更优,当且仅当

p×ai+1bip×aibi+1ai+1×bi+1ai×bi

所以我们不难发现当 ai×bi 升序的时候是最优的。

然后答案需要用高精度存储,但是我不想写。。。(用 python 水过了2333)

考试时候应该还是会头铁写高精度的。。

总结

对于重排序列使得一些要求的东西最优的时候,可以考虑不等式推导。

然后也不需要考虑相隔很远的两个数,可以考虑相邻两个数,结论也是一样的,因为交换相邻两个数也可以使得序列排序。

代码

教你 17python3 代码水过2333

n = (int)(input()) a, b = map(int, input().split()) array = [[0] * 2] * n for i in range(0, n): array[i] = list(map(int, input().split())) def Cmp(elem): return elem[0] * elem[1] array.sort(key = Cmp) ans = 0 tot = a for i in range(0, n): ans = max(ans, tot // array[i][1]) tot = tot * array[i][0] print(ans)

__EOF__

本文作者zjp_shadow
本文链接https://www.cnblogs.com/zjp-shadow/p/9825225.html
关于博主:评论和私信会在第一时间回复。或者直接私信我。
版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!
声援博主:如果您觉得文章对您有帮助,可以点击文章右下角推荐一下。您的鼓励是博主的最大动力!
posted @   zjp_shadow  阅读(741)  评论(2编辑  收藏  举报
编辑推荐:
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
阅读排行:
· 地球OL攻略 —— 某应届生求职总结
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 提示词工程——AI应用必不可少的技术
· .NET周刊【3月第1期 2025-03-02】
点击右上角即可分享
微信分享提示