https://ac.nowcoder.com/acm/problem/16564
题意:
已知每天可以借出去的教室数量a[i],根据先到先得原则,按顺序分配教室,共有m个订单,第i个订单需要[li,ri]区间内借xi个教室,问到第几个订单开始无法满足(教室不够了)

分析:
m次区间[li,ri]进行修改xi,边修改边查询是否满足题意,这不就是练习线段树的题目吗?
首先建一颗含最小值信息的线段树,模拟题意进行区间修改,修改完后判断一下整个区间最小值是否小于0,即minx[1]是否小于0,若发现一不符合的修改,直接return 0。
暴力即优雅,记得开longlong(不建议define int long long 费时费空间).

代码:

#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
#define int long long//补救措施开longlong
int n,m;
int a[1000005],lazy[4000005],minx[4000005];//懒标记数组和区间最小值数组
void build(int node,int l,int r){//建含最小值的线段树
    if(l==r){
        minx[node]=a[l];
        return ;
    }
    int mid=(l+r)>>1;
    build(node<<1,l,mid);
    build(node<<1|1,mid+1,r);
    minx[node]=min(minx[node<<1],minx[node<<1|1]);
}
void pushup(int node){//向下更新
    if(lazy[node]){
        minx[node<<1]+=lazy[node];
        minx[node<<1|1]+=lazy[node];
        lazy[node<<1]+=lazy[node];
        lazy[node<<1|1]+=lazy[node];
        lazy[node]=0;
    }
}
void update(int node,int l,int r,int start,int end,int num){//区间修改
    if(l>=start&&r<=end){
        minx[node]+=num;
        lazy[node]+=num;
        return ;
    }
    pushup(node);
    int mid=(l+r)>>1;
    if(start<=mid)update(node<<1,l,mid,start,end,num);
    if(end>mid)update(node<<1|1,mid+1,r,start,end,num);
    minx[node]=min(minx[node<<1],minx[node<<1|1]);
}
signed main()
{
    memset(minx,0x3f3f3f,sizeof(minx));//初始化最小值
    cin>>n>>m;
    for(int i=1;i<=n;i++) cin>>a[i];
    build(1,1,n);//建树
    for(int i=1;i<=m;i++){
        int d,s,tt;
        cin>>d>>s>>tt;
        update(1,1,n,s,tt,-d);
        //for(int i=1;i<=6;i++) cout<<t[i].minn<<" ";
        if(minx[1]<0){
            cout<<-1<<endl;
            cout<<i<<endl;
            return 0;
        }
    }
    cout<<0<<endl;
}