7.18每日一题题解

树上求和

涉及知识点:

  • 二分
  • 思维

solution:

  • 二分出答案
  • 假设答案是x的话,判断我们至少删除几个可以到达x
  • 如果我们需要删除的数量大于m的话,那么此时答案一定是比小的(right = mid - 1)
  • 否则x就有可能是答案(left = mid)

std:

#include <iostream>
#include <vector>
#include <algorithm>
#include <cstring>
using namespace std;
int n,m,l;
const int N = 5e4 + 10;
int a[N];

bool check(int x)
{
    int last = l;
    int cnt = 0;
    for(int i = n; i >= 0;i --)
    {
        if(last - a[i] < x){
            cnt ++; // 如果此时的距离比x小的话,那么这个就可以被删除
        }
        else{
            last = a[i]; // 更新最后一个石头
        }
    }
    
    if(cnt > m)return false;
    else return true;
    
}

int main()
{
    cin >> l >> n >> m;
    
    for(int i = 1;i <= n;i ++)
    {
        cin >> a[i];
    }
    
    int left = 0,right = l;
    
    while(left < right)
    {
        int mid = left + right + 1 >> 1;
        if(check(mid)){
            left = mid;
        }
        else{
            right = mid - 1;
        }
    }
    
    cout << left << endl;
    
    return 0;
}
posted @ 2020-07-18 18:12  QFNU-ACM  阅读(80)  评论(0编辑  收藏  举报