RE求调
查看原帖
RE求调
793142
anmengxun楼主2023/7/19 11:13
#include <iostream>
#include <cstdio> 
#define Lc tree[now].lc
#define Rc tree[now].rc
#define Ls tree[now].lson
#define Rs tree[now].rson
#define V tree[now].v
#define MX 1000010
using namespace std;
int n,m;
int root[MX] = {1};//根节点坐标 
int yuan[MX];//原数据 
struct Node{
	int lson,rson;//左右儿子的坐标 
	int lc,rc;//所储存的范围 
	int v;//(叶子节点)所储存的值 
}tree[MX * 40];
int latest = 0;//树中最新的坐标 
int loc;//查询/修改目标坐标 
int k;//修改的值 
void maketree(int l,int r)
{
	int now = ++latest;//申请节点 
	Lc = l,Rc = r;
	if (Lc == Rc)//到达叶节点,储存实际值 
	{
		V = yuan[l];
		return;
	}
	int mid = (l + r) / 2;
	Ls = latest + 1;//记录左子节点坐标 
	maketree(l,mid);//构造左子节点 
	Rs = latest + 1;//记录右子节点坐标 
	maketree(mid + 1,r);//构造右子节点 
}
void edit(int old)//在ver版本的坐标 
{
	int now = ++latest;
	tree[now] = tree[old];//申请新的空间并且复制 
	if (Lc == Rc)//到达叶子节点,修改并返回 
	{
		V = k;
		return;
	}
	else//未到达叶子节点,继续递归 
	{
		if (loc <= tree[Ls].rc)//目标节点在左子节点 
		{
			Ls = latest + 1;//修改左子节点坐标 
			edit(tree[old].lson);//进入ver版本的左子节点 
		}
		else if (loc >= tree[Rs].lc)//目标节点在右子节点 
		{
			Rs = latest + 1;//修改右子节点坐标 
			edit(tree[old].rson);//进入ver版本的右子节点 
		}
	}
}
int querry(int now)//在查询(ver)版本的坐标 
{
	if (Lc == Rc)//到达目标叶子节点 
	{
		return V;
	}
	else
	{
		if (loc <= tree[Ls].rc)//目标节点在左子节点
		{
			querry(Ls);
		}
		else if (loc >= tree[Rs].lc)//目标节点在右子节点
		{
			querry(Rs);
		}
	}
}
int main()
{
	scanf("%d %d",&n,&m);//读入 
	for (int i = 1;i <= n;i++)
	{
		scanf("%d",&yuan[i]);
	}
	maketree(1,n);//建树 
	int opt,ver;
	for (int i = 1;i <= m;i++)
	{
		scanf("%d %d",&ver,&opt);
		if (opt == 1)
		{
			scanf("%d %d",&loc,&k);
			root[i] = latest + 1;//记录即将诞生的新根节点坐标 
			edit(root[ver]);//进入ver版本 
		}
		else
		{
			scanf("%d",&loc);
			root[i] = root[ver];//复制ver版本的树 
			printf("%d\n",querry(root[ver]));//进入ver版本 
		}
	}
	return 0;
}
2023/7/19 11:13
加载中...