CH0805 防线(秦腾与教学评估)

CH0805 防线(秦腾与教学评估)

http://noi-test.zzstep.com/contest/0x08「基本算法」练习/0805 防线(秦腾与教学评估)

分析

题目中明确指出只有一个位置可能是奇数,很容易想到计算防具数目的前缀和,在防具数目为奇数的位置之前的前缀和均为偶数,在该位置及之后的前缀和均为奇数。前缀和满足>单调性<,故可以用二分答案的方法来进行验证。

但若直接暴力地计算每个位置的前缀和,显然会超时。我们可以在二分的时候再进行计算,而且只需要计算二分出来的位置的前缀和(扫描每一个防具段,然后将对前缀和的贡献累加),这样大大减少了运算量,时间复杂度为O(N),总时间复杂度为O(Nlog2E)

实现

//
//  main.cpp
//  daily
//
//  Created by 闫润邦 on 2021/8/27.
//  Copyright © 2021 闫润邦. All rights reserved.
//

#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
#define ll long long
using namespace std;

const int maxn = 2e5 + 10;

int T,n;

struct NODE
{
    int s , e , d;
}ord[maxn];


ll max(ll x, ll y)
{
    return x > y ? x : y;
}

ll min(ll x,ll y)
{
    return x < y ? x : y;
}

int main(int argc, const char * argv[])
{
    scanf("%d",&T);
    while(T--)
    {
        scanf("%d",&n);
        for(int i = 1; i <= n; i++)
            scanf("%d%d%d" , &ord[i].s , &ord[i].e , &ord[i].d);
        
        ll l = 1, r = 1ll<<31;
        while(l < r)
        {
            int cnt = 0;
            ll mid = (l + r) / 2;
            for(int i = 1; i <= n; i++)
                if(ord[i].s <= mid)
                    cnt += ( min(mid , ord[i].e) - ord[i].s ) / ord[i].d + 1;
            if(cnt & 1)
                r = mid;
            else
                l = mid + 1;
            
        }
        
        if(l == 1ll<<31)
            printf("There's no weakness.\n");
        else
        {
            int ans = 0;
            for(int i = 1; i <= n; i++)
                if(l >= ord[i].s && (l - ord[i].s) % ord[i].d == 0)
                    ans++;
            printf("%lld %d\n",l,ans);
        }
        
    }
    return 0;
}

总结

二分答案很好想到,本题难点在于计算前缀和的方法,在二分的过程中计算单点的前缀和,而不是常规的“先计算前缀和,再二分”。

转换思路很重要!

posted @   Franky0705  阅读(113)  评论(0编辑  收藏  举报
编辑推荐:
· AI与.NET技术实操系列:基于图像分类模型对图像进行分类
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
阅读排行:
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现
点击右上角即可分享
微信分享提示