社区讨论

线段树,已查3小时,至今不知道哪里错了

P3870[TJOI2009] 开关参与者 5已保存回复 8

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
8 条
当前快照
1 份
快照标识符
@mi869328
此快照首次捕获于
2025/11/21 09:18
4 个月前
此快照最后确认于
2025/11/21 09:18
4 个月前
查看原帖
我彻底绝望了
CPP
#include <iostream>

using namespace std;

#define MAXN 100001
#define lc (root*2)
#define rc (root*2+1)

struct Node
{
	int l,r;
	int data;
	bool sign;
} tree[MAXN<<2];

void build(int root,int l,int r);
void spread(int root);
void push_up(int root);
void change(int root,int l,int r);
int query(int root,int l,int r);

int n;

int main(void)
{
	int m,t1,t2,t3;
	cin>>n>>m;
	build(1,1,n);
	while(m--)
	{
		cin>>t1>>t2>>t3;
		if(t1)
		{
			cout<<query(1,t2,t3)<<endl;
		}
		else
		{
			change(1,t2,t3);
		}
	}
	return 0;
}

void build(int root,int l,int r)
{
	tree[root].l=l;
	tree[root].r=r;
	tree[root].data=0;
	tree[root].sign=false;
	if(l==r)
	{
		return;
	}
	int mid=(l+r)>>1;
	build(lc,l,mid);
	build(rc,mid+1,r);
	return;
}

void spread(int root)
{
	if(!tree[root].sign)
	{
		return;
	}
	tree[lc].data=tree[lc].r-tree[lc].l+1-tree[lc].data;
	tree[rc].data=tree[rc].r-tree[rc].l+1-tree[rc].data;
	tree[lc].sign=!tree[lc].sign;
	tree[rc].sign=!tree[rc].sign;
	tree[root].sign=false;
}

void push_up(int root)
{
	tree[root].data=tree[lc].data+tree[rc].data;
	return;
}

void change(int root,int l,int r)
{
	if(l<=tree[root].l&&r>=tree[root].r)
	{
		tree[root].data=tree[root].r-tree[root].l+1-tree[root].data;
		tree[lc].sign=!tree[lc].sign;
		tree[rc].sign=!tree[rc].sign;
		return;
	}
	spread(root);
	int mid=(tree[root].l+tree[root].r)>>1;
	if(l<=mid)
	{
		change(lc,l,r);
	}
	if(r>mid)
	{
		change(rc,l,r);
	}
	push_up(root);
	return;
}

int query(int root,int l,int r)
{
	if(l<=tree[root].l&&r>=tree[root].r)
	{
		return tree[root].data;
	}
	spread(root);
	int mid=(tree[root].l+tree[root].r)>>1,res=0;
	if(l<=mid)
	{
		res+=query(lc,l,r);
	}
	if(r>mid)
	{
		res+=query(rc,l,r);
	}
	return res;
}

回复

8 条回复,欢迎继续交流。

正在加载回复...