首页 > 其他分享 >雨天的尾巴

雨天的尾巴

时间:2024-05-11 19:19:06浏览次数:16  
标签:rt cnt int 尾巴 st 雨天 ra 救济粮

[Vani有约会] 雨天的尾巴 /【模板】线段树合并

题目背景

深绘里一直很讨厌雨天。

灼热的天气穿透了前半个夏天,后来一场大雨和随之而来的洪水,浇灭了一切。

虽然深绘里家乡的小村落对洪水有着顽固的抵抗力,但也倒了几座老房子,几棵老树被连根拔起,以及田地里的粮食被弄得一片狼藉。

无奈的深绘里和村民们只好等待救济粮来维生。

不过救济粮的发放方式很特别。

题目描述

首先村落里的一共有 \(n\) 座房屋,并形成一个树状结构。然后救济粮分 \(m\) 次发放,每次选择两个房屋 \((x, y)\),然后对于 \(x\) 到 \(y\) 的路径上(含 \(x\) 和 \(y\))每座房子里发放一袋 \(z\) 类型的救济粮。

然后深绘里想知道,当所有的救济粮发放完毕后,每座房子里存放的最多的是哪种救济粮。

输入格式

输入的第一行是两个用空格隔开的正整数,分别代表房屋的个数 \(n\) 和救济粮发放的次数 \(m\)。

第 \(2\) 到 第 \(n\) 行,每行有两个用空格隔开的整数 \(a, b\),代表存在一条连接房屋 \(a\) 和 \(b\) 的边。

第 \((n + 1)\) 到第 \((n + m)\) 行,每行有三个用空格隔开的整数 \(x, y, z\),代表一次救济粮的发放是从 \(x\) 到 \(y\) 路径上的每栋房子发放了一袋 \(z\) 类型的救济粮。

输出格式

输出 \(n\) 行,每行一个整数,第 \(i\) 行的整数代表 \(i\) 号房屋存放最多的救济粮的种类,如果有多种救济粮都是存放最多的,输出种类编号最小的一种。

如果某座房屋没有救济粮,则输出 \(0\)。

样例 #1

样例输入 #1

5 3
1 2
3 1
3 4
5 3
2 3 3
1 5 2
3 3 3

样例输出 #1

2
3
3
0
2

提示

  • 对于 \(20\%\) 的数据,保证 \(n, m \leq 100\)。
  • 对于 \(50\%\) 的数据,保证 \(n, m \leq 2 \times 10^3\)。
  • 对于 \(100\%\) 测试数据,保证 \(1 \leq n, m \leq 10^5\),\(1 \leq a,b,x,y \leq n\),\(1 \leq z \leq 10^5\)。

首先连边连成一个树,显然我们需要一个桶,记录pos位置下的值以及其次数,然后我们需要用树上差分以及LCA,
image
所以可用LCA找到x,y的最近公共祖先以及最近公共祖先的父亲,进行操作,合并过程用线段树合并O(nlogn)的复杂度显然是最优的,关于权值线段树的右边界,注意审题,只需1e5即可

点击查看代码
#include <bits/stdc++.h>
#define lid st[rt].l
#define rid st[rt].r
using namespace std;
int n,m,segtot;
const int N = 1e5+5,MAX=1e5;
vector <int> edge[N];
int root[N],d[N],f[N][33],ans[N];

struct tree
{
	int l,r,cnt,ans,t;
}st[N*80];
int read(){
    int s=0,f=1;char ch=getchar();
    for(;ch<'0'||ch>'9';ch=getchar()) if(ch=='-')f=-1;
    for(;ch>='0'&&ch<='9';ch=getchar()) s=s*10+(ch^48);
    return s*f;
}
void pushup(int rt)
{
	if(lid==0)
	{
		st[rt].cnt=st[rid].cnt;
		st[rt].t=st[rid].t;	
		return;
	}
	if(rid==0)
	{
		st[rt].cnt=st[lid].cnt;
		st[rt].t=st[lid].t;
		return;		
	}
	if(st[lid].cnt>=st[rid].cnt)
	{
		st[rt].cnt=st[lid].cnt;
		st[rt].t=st[lid].t;
	}else
	{
		st[rt].cnt=st[rid].cnt;
		st[rt].t=st[rid].t;		
	}
}
void dfslca(int x,int fa)
{
	d[x]=d[fa]+1;
	f[x][0]=fa;
	for(int j=1;j<=30;j++)
	{
		f[x][j]=f[f[x][j-1]][j-1];
	}
//	cout<<"&&"<<x<<" "<<d[x]<<endl;
	for(int i=0;i<edge[x].size();i++)
	{
		int to=edge[x][i];
		if(to==fa)continue;
		dfslca(to,x);
	}
}
void LCA_init()
{
//	for(int j=1;j<=25;j++)
//	{
//		for(int i=1;i<=n;i++)
//		{
//			f[i][j]=f[f[i][j-1]][j-1];
//		}
//	}
}
int lca(int x,int y)
{
	if(d[x]<d[y])swap(x,y);
	for(int i=30;i>=0;i--)
	{
		if(d[f[x][i]]>=d[y])x=f[x][i];
	}
	if(x==y)return x;
	for(int i=30;i>=0;i--)
	{
		if(f[x][i]!=f[y][i])
		{
			x=f[x][i];
			y=f[y][i];
		}
	}
	return f[x][0];
}
int segtree(int ra,int rb,int l,int r)
{
	if(!ra)return rb;
	if(!rb)return ra;
	if(l==r)
	{
		st[ra].cnt+=st[rb].cnt;
		return ra;
	}
	int mid=(l+r)>>1;
	st[ra].l=segtree(st[ra].l,st[rb].l,l,mid);
	st[ra].r=segtree(st[ra].r,st[rb].r,mid+1,r);
	pushup(ra);	
	return ra;
}
void update(int &rt,int l,int r,int pos,int val)
{
	if(!rt)rt=++segtot;
	if(l==r)
	{
		st[rt].cnt+=val;
		st[rt].t=pos;
		return;
	}
	int mid=(l+r)>>1;
	if(pos<=mid)update(lid,l,mid,pos,val);
	else update(rid,mid+1,r,pos,val);
	pushup(rt);
}
//int query(int rt,int l,int r,int L,int R)
//{
//	if(!rt)return 0;
//	
//}
void dfs(int x,int fa)
{
	for(int i=0;i<edge[x].size();i++)
	{
		int to=edge[x][i];
		if(to==fa)continue;
		dfs(to,x);
		root[x]=segtree(root[x],root[to],1,MAX);
	}
	ans[x]=st[root[x]].t;
	if(st[root[x]].cnt==0)ans[x]=0;
}
int main()
{
//	ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
//	freopen("a.out","r",stdin);
	cin>>n>>m;
	int a,b;
	for(int i=1;i<=n-1;i++)
	{
		a=read();b=read();
//		cin>>a>>b;
		edge[a].push_back(b);
		edge[b].push_back(a);
	}
	
	dfslca(1,0);
//	LCA_init();
	int x,y,z;
	for(int i=1;i<=m;i++)
	{
		x=read();y=read();z=read();
//		cin>>x>>y>>z;
		int q=lca(x,y);
//		cout<<"###"<<q<<endl;
		update(root[x],1,MAX,z,1);
		update(root[y],1,MAX,z,1);
		update(root[q],1,MAX,z,-1);
		if(f[q][0])update(root[f[q][0]],1,MAX,z,-1);
	}
	dfs(1,0);
	for(int i=1;i<=n;i++)
	{
		cout<<ans[i]<<endl;
	}
	return 0;
}

标签:rt,cnt,int,尾巴,st,雨天,ra,救济粮
From: https://www.cnblogs.com/wlesq/p/18187050

相关文章

  • 雨天的尾巴(P4556 [Vani有约会] 雨天的尾巴 /【模板】线段树合并)
    1.题意简化N个点,形成一个树状结构。有M次发放,每次选择两个点x,y对于x到y的路径上(含x,y)每个点发一袋Z类型的物品。完成所有发放后,每个点存放最多的是哪种物品。2.思路首先这道题肯定要用先建树,然后我们可以在树上的每个节点建一个权值线段树,考虑到空间问题(每个点都有1个权值......
  • 见鬼了!我家的 WiFi 只有下雨天才能正常使用...
    这是作者大学时期在家里遇到的一个非常奇怪的网络问题,作者的父亲是一名经验丰富的网络工程师,他们家里使用了一个复杂的网络设置,通过Wi-Fi桥接的方式,将父亲公司的高速商业网络连接到家中。但是有一天,作者发现家里的Wi-Fi只有在下雨时才能正常工作。。。事情发生在十多年前,那......
  • P4556 [Vani有约会] 雨天的尾巴 /【模板】线段树合并
    P4556[Vani有约会]雨天的尾巴/【模板】线段树合并在这题里面讲一下线段树合并。顾名思义就是把多个线段树合并成一个。显然完全二叉线段树(也就是普通线段树)是无法更高效的合并的,只能把所有节点加起来建个新树。但是在动态开点线段树中,有时候一个树只有几条链,这时候我们就是可......
  • 为何4G监控设备接入LiteCVR后,阴雨天气频繁出现播放卡顿现象?
    近年来,随着计算机、网络、图像处理以及传输技术的飞速发展,视频监控业务正在向其他领域加速渗透。LiteCVR视频融合平台基于云边端一体化架构,具有强大的数据接入、处理及分发能力,平台支持海量视频汇聚管理,可支持多协议、多类型的设备接入,属于性能稳定、高可靠、高可用的流媒体视频......
  • 题解 P4556 [Vani有约会]雨天的尾巴 /【模板】线段树合并
    传送门如题目所言,这就是个线段树合并的板子题。题目大意题目描述首先村落里的一共有\(n\)座房屋,并形成一个树状结构。然后救济粮分\(m\)次发放,每次选择两个房屋\((x,y)\),然后对于\(x\)到\(y\)的路径上(含\(x\)和\(y\))每座房子里发放一袋\(z\)类型的救济粮。然......
  • Luogu P4556 [Vani有约会]雨天的尾巴 /【模板】线段树合并
    [Vani有约会]雨天的尾巴/【模板】线段树合并题目背景深绘里一直很讨厌雨天。灼热的天气穿透了前半个夏天,后来一场大雨和随之而来的洪水,浇灭了一切。虽然深绘里家乡的小村落对洪水有着顽固的抵抗力,但也倒了几座老房子,几棵老树被连根拔起,以及田地里的粮食被弄得一片狼藉。无奈......
  • 连续下雨天,.net开发者如何预防流感
    最近连续下了3天雨,天气变化大,很容易引发感冒咳嗽等疾病。对于.NET技术开发人员来说,如何保持身体健康,保证工作效率是一个很重要的问题。首先,我们需要注意保持室内空气流通,避免长时间处于封闭的空间。在开发过程中,我们通常需要长时间坐在电脑前,容易导致眼睛疲劳和颈椎病等问题。因......
  • 我抓住了 小尾巴
    继上次:"我抓住了腾讯的小尾巴"再次发表此文章,眼见为实我估计是开发的人太忙了,有时候根本不管有没有评论...    ......
  • 仿QQ尾巴,让程序给记事本输入文字!:)
    效果截图如下:程序主要代码如下:voidCSendMessageNotepadDlg::OnBnClickedBtnsend()//发送按钮单击处理函数{HWNDhParent=NULL,hChild=NULL;hParent=::FindWindow(T......
  • 雨天与心情
    说到“雨天”,不自觉地将之与“交通拥堵”、“出行不便”、“湿了鞋子”、“阴冷潮湿”联想到了一起,对我来说,我还联想到“骑自行车湿了背包”。这样一想,不喜欢下雨......