题意很简单:1-n个钩子初始价值是1,然后题目给出Q个操作,x y z,将x->y的钩子价值改为z,最后输出n个钩子的总价值。
线段树功能:update:成段替换 (由于只query一次总区间,所以可以直接输出1结点的信息)
//3160 KB 624 ms #include<cstdio> #include<iostream> #include<cstring> #include<algorithm> #define M 100005 #define root 1,n,1 #define lson l,m,rt<<1 #define rson m+1,r,rt<<1|1 using namespace std; int sum[M<<2]; int col[M<<2]; void pushup(int rt) { sum[rt]=sum[rt<<1]+sum[rt<<1|1]; } void pushdown(int rt,int m) { if(!col[rt]) return; col[rt<<1]=col[rt<<1|1]=col[rt]; sum[rt<<1]=col[rt]*(m-(m>>1)); //m-m/2是左儿子的区间长度 sum[rt<<1|1]=col[rt]*(m>>1); //m/2 是右儿子的区间长度 /*可以化简成 这样简单表示左右儿子区间长度的方式,而且左儿子的区间长度>=右儿子的,这样记忆便可*/ col[rt]=0; } void build(int l,int r,int rt) { col[rt]=0; if(l==r){ sum[rt]=1; return ; } int m=(l+r) >>1; build(lson); build(rson); pushup(rt); } void update(int L,int R,int c,int l,int r,int rt) { if(L<=l&&r<=R){ sum[rt]=c*(r-l+1); col[rt]=c; return; } pushdown(rt,r-l+1); //pushdown lazytag int m=(l+r)>>1; if(L<=m) update(L,R,c,lson); if(R>m) update(L,R,c,rson); pushup(rt); } int main() { int cas,n,m; scanf("%d",&cas); for(int k=1;k<=cas;k++){ scanf("%d%d",&n,&m); build(root); for(int j=1;j<=m;j++){ int a,b,c; scanf("%d%d%d",&a,&b,&c); update(a,b,c,root); } printf("Case %d: The total value of the hook is %d.\n",k,sum[1]); } return 0; }