1. 程式人生 > >Fast Arrangement (線段樹 維護區間最大值 lazy標記)

Fast Arrangement (線段樹 維護區間最大值 lazy標記)

Fast Arrangement

題意:

有一列火車同一時刻只能承載K個人,然後有Q個人要買票(給出Q組區間表示要買票的區間),(注意: 火車行駛區間為a-b的範圍),問那個人可以成功買到票(先到先得)。

AC程式碼:

#include <iostream>
#include <stdio.h>
#define ll long long
#define lson l, mid, rt << 1
#define rson mid + 1, r, rt << 1 | 1
#define il inline
using namespace std;
const
ll MAXN = 1e6 + 10; struct Tree {//定義結構 ll lazy; ll maxn; } t[MAXN<<2]; il void push_up(ll rt) { //向上更新 t[rt].maxn = max(t[rt << 1].maxn ,t[rt << 1 | 1].maxn); } il void push_down(ll rt, ll m) {//pushdown函式 if(t[rt].lazy) { //若有標記,則將標記向下移動一層 t[rt << 1].lazy +=
t[rt].lazy; t[rt << 1 | 1].lazy += t[rt].lazy; t[rt << 1].maxn += t[rt].lazy; t[rt << 1 | 1].maxn+= t[rt].lazy; t[rt].lazy = 0;//取消本層標記 } } il void build(ll l,ll r, ll rt) { //建樹 t[rt].lazy = 0; if(l == r) { t[rt].maxn=0; return
; } ll mid = (l + r) >> 1; build(lson); build(rson); push_up(rt);//向上更新 } il void update(ll L,ll R, ll l,ll r, ll rt) { //區間更新 if(L <= l && R >= r) { t[rt].maxn+=1; t[rt].lazy+=1; return; } push_down(rt, r - l + 1);//向下更新 long long int mid = (l + r) >> 1; if(L <= mid) update(L, R,lson); if(R > mid) update(L, R,rson); push_up(rt);//向上更新 } il ll query_max(ll L, ll R, ll l, ll r,ll rt) { //區間求最大值 if(L <= l && R >= r) return t[rt].maxn; push_down(rt, r - l + 1);//向下更新 ll mid = (l + r) >> 1; ll ans = 0; if(L <= mid) ans = max(ans,query_max(L, R, lson)); if(R > mid) ans = max(ans,query_max(L, R, rson)); return ans; } int main() { ll k,l,r,v,m; char a; int t; cin>>t; for(ll i=1; i<=t; i++) { printf("Case %lld:\n",i); build(1,1000000, 1); scanf("%lld %lld", &k,&m); for(ll j=1;j<=m;j++) { scanf("%lld %lld", &l,&r); if(query_max(l,r-1,1,1000000,1)<k){ printf("%lld ",j); update(l,r-1,1,1000000,1); } } printf("\n\n"); } return 0; }