题解 | #K Yet Another Problem About Pi#

Yet Another Problem About Pi

https://ac.nowcoder.com/acm/contest/11259/K

K Yet Another Problem About Pi

  • 链接:K-Yet Another Problem About Pi_2021牛客暑期多校训练营8 (nowcoder.com)

  • 题意:平面上有无穷个长,宽为的矩形方格。你有一条长度为​的曲线可以任意弯折,起点任意,求曲线最多经过的方格数目(不计边界)

  • 先考虑最坏情况:对应时,我们不能越过任何一个方格,此时我们的最佳方案应该是以四个矩形方格的交点为起点,向周围走一圈,最小结果为4

图片说明

  • 如果我们能够越过方格,我们可以认为以下的所有情况都是有上方(结果为4)的情况推广而来,因为上述拿法是开局最佳。并且因为是无限循环小数,我们可以认为折线极其微小,但是真实存在,此时可以忽略折线的长度,我们有两种方案:

    • 走直线:取,走长度更小的一侧必然更优,此时每越过一个格子增加贡献为2
    • 走曲线:取,每越过一个格子增加贡献为3(即斜对角方格和其旁边紧挨两格)
  • 可见的是,我们要协调上述两种操作,使得最后的贡献最多。并且可以知道的是:在使用上述操作时,仅有边界情况会影响操作的选择是否需要改变(如走直线变成走曲线)。所以这种变换操作最多存在两次(可以类比回退一步求更优值),所以直接枚举上述两种操作的存在次数,对即可

#include <bits/stdc++.h>
#define endl '\n'
typedef long long ll;
typedef unsigned long long ull;
using namespace std;
const double PI = acos(-1);
signed main() {
    int t;
    scanf("%d", &t);
    while(t--) {
        double w, d, tmp, dis;
        ll ans = 0;
        scanf("%lf%lf", &w, &d);
        tmp = min(w, d);
        dis = sqrt(w * w + d * d);
        for(int i = 0; i <= 2; ++i) {
            //枚举直线数目
            if(i * tmp <= PI) ans = max(ans, (ll)(4 + 2 * i + floor((PI - tmp * i) / dis) * 3));
            // 枚举斜线数目
            if(i * dis <= PI) ans = max(ans, (ll)(4 + 3 * i + floor((PI - dis * i) / tmp) * 2));
        }printf("%lld\n", ans);
    }    
    return 0;
}
全部评论
大佬可以解释一下“如果我们能够越过方格,我们可以认为以下的所有情况都是有上方(结果为4)的情况推广而来”吗
点赞 回复 分享
发布于 2021-09-05 00:05
“考虑最坏情况……”min写成max了
点赞 回复 分享
发布于 2021-08-11 17:27
想问一下为什么“变换操作最多存在两次”?<(_ _)>
点赞 回复 分享
发布于 2021-08-11 10:53
大佬我想问一下,A题如果$a = m = n$那么不就无题可做了..是不是就不用去厕所了QAQ?
点赞 回复 分享
发布于 2021-08-09 19:52

相关推荐

不愿透露姓名的神秘牛友
今天 11:35
点赞 评论 收藏
分享
下北澤大天使:你是我见过最美的牛客女孩😍
点赞 评论 收藏
分享
评论
13
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务