1 条题解

  • 0
    @ 2026-2-1 16:04:53
    #include<bits/stdc++.h>
    using namespace std;
    
    // 存储每个居民的种树需求:l-区间左端点,r-区间右端点,t-该区间最少需要种的树数量
    struct node{
        int l,r,t;
    }arr[6000]; 
    
    // 比较函数:按区间右端点r升序排序,r相同时按左端点l升序
    // 贪心策略:优先处理右端点小的区间,方便后续区间复用已种的树
    bool cmp(node x,node y){
        if(x.r == y.r) 
            return x.l < y.l;
        else 
            return x.r < y.r;
    }
    
    int main(){
        long long n,h;
        cin >> n >> h; // [1] 输入区域总数n和居民户数h
        bool flag[40000] = {false}; // 标记数组,记录每个位置是否已种树,初始为未种
        
        // [2] 输入每个居民的种树需求
        for(int i = 0; i < h; i++){
            cin >> arr[i].l >> arr[i].r >> arr[i].t;
        }
        
        sort(arr, arr + h, cmp); // [3] 按区间右端点升序排序,为贪心处理做准备
        
        long long sum = 0; // 记录最少需要种的树的总数
        // [4] 遍历每个居民的需求区间
        for(int i = 0; i < h; i++){   
            // 先统计当前区间内已种的树,减少需要新增的数量
            for(int j = arr[i].l; j <= arr[i].r && arr[i].t > 0; j++){
                if(flag[j])
                    arr[i].t--; 
            }
            if(arr[i].t <= 0) 
                continue; // 已种的树已满足需求,跳过当前区间
            
            // 贪心策略:从区间右端往左种新树,让后续区间尽可能复用这些树
            for(int j = arr[i].r; j >= arr[i].l && arr[i].t > 0; j--){
                if(flag[j] == false){
                    sum++;
                    arr[i].t--;
                    flag[j] = true; // 标记该位置已种树
                }
            }
        }
        cout << sum; // [5] 输出最少需要种的树的总数
        return 0;
    }
    
    • 1

    信息

    ID
    1037
    时间
    1000ms
    内存
    256MiB
    难度
    2
    标签
    递交数
    3
    已通过
    1
    上传者