当前位置: 首页 > news >正文

北京seoqq群西安优化外包

北京seoqq群,西安优化外包,鞍山网络,免费制作简历DSU ON TREE DSU#xff1a;并查集 DSU ON TREE#xff1a;树上启发式合并 我也不知道为啥树上并查集就是树上启发式合并 启发式合并的思想是每次把小的往大的合并#xff0c;也就是最大化利用已有的答案#xff08;大的数组不用清空#xff0c;在原基础上加上小的即可并查集 DSU ON TREE树上启发式合并 我也不知道为啥树上并查集就是树上启发式合并 启发式合并的思想是每次把小的往大的合并也就是最大化利用已有的答案大的数组不用清空在原基础上加上小的即可。转移到树上“大”显然就是树的重心。 能解决什么样的问题需要统计子树信息但是子树的信息不好合并。比如权值是否出现桶。所以肯定要留下最大的也就是树链剖分的重儿子。 考虑两种合并方式以对子树做桶排序为例保留重儿子数组 遍历子树的桶对应相加即类似num[x][val]num[v][val]复杂度O(值域)遍历子树直接num[x][val[v]]复杂度O(子树大小) 显然第一种太大了。 同时显然不能对每个节点开一个桶表示“以x为根的子树的桶”空间无法接受所以桶只能留到一维这就涉及到清空因为在dfs另一个儿子时前一个子树的影响要清空。所以要尽可能少的减少清空在dfs时如果最后访问重儿子那就可以不清空最大的一部分。 void dfs2(int x,int fa,int save) {for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa || vmxson[x]) continue;dfs2(v,x,0);}if (mxson[x]) dfs2(mxson[x],x,1);if (!show[dis[x]]) show[dis[x]]deep[x];else show[dis[x]]min(show[dis[x]],deep[x]);int needk2*dis[x]-dis[x];if (show.count(need)){int mndepshow[need];int nowansmndepdeep[x]-2*deep[x]; ansmin(ans,nowans);}for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa || vmxson[x]) continue;calc_ans(v,x,x),add(v,x);}//if (!save) del(x,fa);if (!save) show.clear(); }大致这个样子save表示是否要清空桶。先跑轻儿子清空桶。再跑重儿子不清空桶那么这个桶里的东西再回溯到父亲节点时依然保留。同时注意为什么先calc_ans再add是为了避免有两个点在同一棵子树内的情况即 u → l c a → x → l c a → v u\rightarrow lca\rightarrow x\rightarrow lca\rightarrow v u→lca→x→lca→v的情况。在题目里往往这种情况不合法。 例题 洛谷P4149 [IOI2011] Race 题目链接 题目大意给一棵树每条边有权。求一条简单路径权值和等于k且边的数量最小。 思路问题转化为选择点对 ( u , v ) (u,v) (u,v)满足 d i s u d i s v − d i s l c a ( u , v ) k dis_udis_v-dis_{lca(u,v)}k disu​disv​−dislca(u,v)​k最小化 d e e p u d e e p v − d e e p l c a ( u , v ) deep_udeep_v-deep_{lca(u,v)} deepu​deepv​−deeplca(u,v)​考虑处理以 x x x为根的子树的答案不妨设 l c a ( u , v ) x lca(u,v)x lca(u,v)x在dfs到点u时只需要查找 k 2 ∗ d i s x − d i s u k2*dis_x-dis_u k2∗disx​−disu​的点都可以作为点 v v v移项可得此时考虑需要最小化的值 d e e p u deep_u deepu​和 d e e p x deep_x deepx​都是已知值所以只需要开一个桶map维护 m a p [ d ] map[d] map[d]表示 d i s d disd disd的点的 d e e p deep deep最小值。 解决了思路剩下的就是实现DSU ON TREE。注意先遍历子树求解再将该子树加入桶。 #includebits/stdc.h #define pa pairint,int #define INF 0x3f3f3f3f #define inf 0x3f #define fi first #define se second #define mp make_pair #define ll long long #define ull unsigned long long #define pb push_backusing namespace std;inline ll read() {ll f1,sum0;char cgetchar();while (!isdigit(c)) {if (c-) f-1;cgetchar();}while (isdigit(c)) {sumsum*10c-0;cgetchar();}return sum*f; } const int MAXN200010; struct edge{int next,to,val; }e[MAXN*2]; int head[MAXN],cnt; void addedge(int u,int v,int w) {e[cnt].nexthead[u];e[cnt].tov;e[cnt].valw;head[u]cnt; } int sz[MAXN],mxson[MAXN],mxsz[MAXN]; int deep[MAXN],ans,k; ll dis[MAXN]; void dfs1(int x,int fa) {sz[x]1;for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa) continue;dis[v]dis[x]e[i].val;deep[v]deep[x]1;dfs1(v,x);sz[x]sz[v];if (sz[v]mxsz[x]) mxson[x]v,mxsz[x]sz[v];} } map ll,int show; void del(int x,int fa) {show[dis[x]]0;for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa) continue;del(v,x);} } void add(int x,int fa) {if (!show.count(dis[x])) show[dis[x]]deep[x];else show[dis[x]]min(show[dis[x]],deep[x]);for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa) continue;add(v,x);} } void calc_ans(int x,int fa,int rt) {int needk2*dis[rt]-dis[x];if (show.count(need)){int mndepshow[need];int nowansmndepdeep[x]-2*deep[rt];ansmin(ans,nowans);}for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa) continue;calc_ans(v,x,rt);} } void dfs2(int x,int fa,int save) {for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa || vmxson[x]) continue;dfs2(v,x,0);}if (mxson[x]) dfs2(mxson[x],x,1);if (!show[dis[x]]) show[dis[x]]deep[x];else show[dis[x]]min(show[dis[x]],deep[x]);int needk2*dis[x]-dis[x];if (show.count(need)){int mndepshow[need];int nowansmndepdeep[x]-2*deep[x]; ansmin(ans,nowans);}for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa || vmxson[x]) continue;calc_ans(v,x,x),add(v,x);}//if (!save) del(x,fa);if (!save) show.clear(); } int main() {int nread(); kread();for (int i1;in;i){int uread()1,vread()1,wread();addedge(u,v,w);addedge(v,u,w);}deep[1]1;dfs1(1,0);//for (int i1;in;i) coutdeep[i] dis[i] mxson[i]endl;ansINF;dfs2(1,0,0);if (ansINF) cout-1endl;else coutansendl;return 0; }有一个小细节是要单独计算一下根的答案因为在后面的过程中并没有再次进入重儿子所以会漏掉重儿子到子树树根的这种答案。其他情况都已经在后面的不断加入中包含。 例题 CF 600E Lomsat gelral 题目链接 题目大意一棵树每个点有个颜色求以每个点为根的子树出现最多的颜色的编号之和。 思路朴素的DSU ON TREE开个桶记录就行众数用set维护当出现更大的清空set出现相等的插入set即可。 #includebits/stdc.h #define pa pairint,int #define INF 0x3f3f3f3f #define inf 0x3f #define fi first #define se second #define mp make_pair #define ll long long #define ull unsigned long long #define pb push_backusing namespace std;inline ll read() {ll f1,sum0;char cgetchar();while (!isdigit(c)) {if (c-) f-1;cgetchar();}while (isdigit(c)) {sumsum*10c-0;cgetchar();}return sum*f; } const int MAXN100010; struct edge{int next,to; }e[MAXN*2]; int head[MAXN],cnt; void addedge(int u,int v) {e[cnt].nexthead[u];e[cnt].tov;head[u]cnt; } int sz[MAXN],mxson[MAXN],mxsz[MAXN]; void pre_dfs(int x,int fa) {for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa) continue;pre_dfs(v,x);sz[x]sz[v];if (sz[v]mxsz[x]) mxson[x]v,mxsz[x]sz[v];}sz[x]; } set int s; int num[MAXN],nowmax,col[MAXN]; ll nowsum; void del(int x,int fa) {num[col[x]]--;for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa) continue;del(v,x);} } void add(int x,int fa) {num[col[x]];if (num[col[x]]nowmax){nowmax;s.clear();s.insert(col[x]);nowsumcol[x];}else if (num[col[x]]nowmax){nowsumcol[x];s.insert(col[x]);}for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa) continue;add(v,x);} } ll ans[MAXN]; void dfs(int x,int fa,int save) {for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa || vmxson[x]) continue;dfs(v,x,0);}if (mxson[x]) dfs(mxson[x],x,1);num[col[x]];if (num[col[x]]nowmax){nowmax;s.clear();s.insert(col[x]);nowsumcol[x];}else if (num[col[x]]nowmax){nowsumcol[x];s.insert(col[x]);}for (int ihead[x];i;ie[i].next){int ve[i].to;if (vfa || vmxson[x]) continue;add(v,x);}ans[x]nowsum;if (!save) del(x,fa),nowsum0,s.clear(),nowmax0; } int main() {int nread();for (int i1;in;i) col[i]read();for (int i1;in;i){int uread(),vread();addedge(u,v),addedge(v,u);}pre_dfs(1,0);dfs(1,0,0);for (int i1;in;i) coutans[i] ;coutendl;return 0; }
http://www.tj-hxxt.cn/news/138648.html

相关文章:

  • 专业型网站和个人网站长春商城网站开发
  • 视频网站VIP卡怎么做赠品wordpress电商模板下载
  • 网站开发电脑配置推荐百度关键字搜索量查询
  • 素材网站无水印深圳广告公司招聘
  • 网站开场动画怎么做网站怎么放404页面
  • 全网最低价查询网站娄底网站建设方案
  • 江西景德镇建设厅网站做外汇的网站
  • 网站微信二维码侧边栏漂浮框餐饮logo免费设计
  • 无锡网站排名优化费用2017年网站建设公司
  • 深圳建站的公司上海园区虚拟地址一览表
  • 张家港网站建设做网站徐州网站简介
  • 建工网官方网站wordpress防转载
  • 优化 网站访问速度益阳市网站建设
  • 免费合同模板网站网页设计与网站的关系
  • 河南第一火电建设公司网站一个人制作网站
  • 便利的龙岗网站设计建设和住房保障部 网站
  • 网站开发费 无形资产阿里云 win wordpress 伪静态
  • dedecms医院网站wap模板(橙色)4512345做销售如何在网站上搜集资料
  • 什么APP可以做网站ps软件电脑版
  • 全景网站如何建设重庆网站的建设
  • 网站做下子压缩文件的链接wordpress繁体中文
  • 郑州企业网站怎么优化广州网站优化指导
  • 网络营销公司策划方案网站怎样优化文章关键词
  • 免费网站建设培训班泰安刘明是怎么挨办的
  • 网站快照海陵区建设局网站
  • 徐州开发区中学网站西安 美院 网站建设
  • 哪些网站可以免费备案域名购买腾讯云
  • 北京网站设计制作教程网站开发一般有几个服务器
  • 汤姆叔叔官方网站建设wordpress+程序优化
  • 公众平台的微信网站开发关于做甜品的网站