题目来源:acm.hdu.edu.cn/showproblem.php?pid=1698
代码注释:
#include<iostream>//线段树区间更新
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<algorithm>
#include<vector>
#include<queue>
#define MAX_len 400040
using namespace std;
typedef long long ll;
struct A {
int l,r,add,sum;
}tree[MAX_len];
void build(int p,int l,int r)//建树
{
tree[p].l=l;
tree[p].r=r;
tree[p].add=0;
tree[p].sum=1;
if(l==r)
return ;
int mid=(l+r)>>1;
build(p<<1,l,mid);
build(p<<1|1,mid+1,r);
}
void pushdown(int p)
{
int m=(tree[p].r-tree[p].l+1);
if(tree[p].add)//存在标记的子区间才进行更新节约时间
{
tree[p<<1].add=tree[p].add;
tree[p<<1|1].add=tree[p].add;
tree[p<<1].sum=(m-(m>>1))*tree[p].add;
tree[p<<1|1].sum=(m>>1)*tree[p].add;//右节点直接除以2(奇数偶数都适应)
tree[p].add=0;
}
}
void update(int p,int l,int r,int val)//更新区间
{
if(l<=tree[p].l && r>=tree[p].r)
{
tree[p].add=val;//也是用于标记
tree[p].sum=(tree[p].r-tree[p].l+1)*val;//区间长度乘以改变的价值
return ;
}
pushdown(p);//继续向下更新子区间
int mid=(tree[p].l+tree[p].r)>>1;
if(r<=mid)
update(p<<1,l,r,val);
else if(l>mid)
update(p<<1|1,l,r,val);
else
{
update(p<<1,l,mid,val);
update(p<<1|1,mid+1,r,val);
}
tree[p].sum=tree[p<<1].sum+tree[p<<1|1].sum;//相加回去
}
int main()
{
int T;
int kk=1;
scanf("%d",&T);
while(T--)
{
int n,i,j,q;
scanf("%d",&n);
scanf("%d",&q);
int x,y,z;
build(1,1,n);
while(q--)
{
scanf("%d %d %d",&x,&y,&z);
update(1,x,y,z);
}
printf("Case %d: The total value of the hook is %d.\n",kk++,tree[1].sum);
}
return 0;
}