【NOIP提高】通讯
来源:互联网 发布:如何在淘宝店发通告 编辑:程序博客网 时间:2024/05/22 15:45
Description
“这一切都是命运石之门的选择。”
试图研制时间机器的机关SERN截获了中二科学家伦太郎发往过去的一条短信,并由此得知了伦太郎制作出了电话微波炉(仮)。
为了掌握时间机器的技术,SERN总部必须尽快将这个消息通过地下秘密通讯网络,传达到所有分部。
SERN共有N个部门(总部编号为0),通讯网络有M条单向通讯线路,每条线路有一个固定的通讯花费Ci。
为了保密,消息的传递只能按照固定的方式进行:从一个已知消息的部门向另一个与它有线路的部门传递(可能存在多条通信线路)。我们定义总费用为所有部门传递消息的费用和。
幸运的是,如果两个部门可以直接或间接地相互传递消息(即能按照上述方法将信息由X传递到Y,同时能由Y传递到X),我们就可以忽略它们之间的花费。
由于资金问题(预算都花在粒子对撞机上了),SERN总部的工程师希望知道,达到目标的最小花费是多少。
Solution
tarjan缩点
互相到达的两个点,就是在同一个强连通分量里面的点的边权都没有用了。
那么明显可以用tarjan来缩点。
需要串上n个点
那么这个东西很像一个最小生成树,可惜不是。
那么我们另辟蹊径。
既然要保证每个点都在的出的图中,那么最优的方案就只有n-1条边,那么每个除了1号点只需要有一条边练过来就好了。那么肯定要保留最小的那条边。
注意
要清空数组TAT,由于一个数组忘记清空,只有80分。
Code
#include<iostream>#include<cstdio>#include<cstring>#include<algorithm>#include<cmath>#define fo(i,a,b) for(i=a;i<=b;i++)#define rep(i,a) for(i=first[a];i;i=next[i])using namespace std;typedef long long ll;const int maxn=200007;int i,j,k,l,t,n,m;int first[maxn*2],next[maxn*2],last[maxn*2],num,chang[maxn*2];int dfn[maxn],low[maxn],stack[maxn],df,tuan,shu[maxn],tou;bool az[maxn],bz[maxn];int xiao[maxn];ll ans;struct node{ int x,y,z;}a[maxn];void add(int x,int y,int z){ last[++num]=y;next[num]=first[x];first[x]=num;chang[num]=z;}void tarjan(int x){ low[x]=dfn[x]=++df; az[x]=bz[x]=1; stack[++stack[0]]=x; int i; rep(i,x){ if(!bz[last[i]]){ tarjan(last[i]); low[x]=min(low[x],low[last[i]]); } else if(az[last[i]]){ low[x]=min(low[x],dfn[last[i]]); } } if(dfn[x]==low[x]){ tuan++; while(stack[stack[0]+1]!=x){ az[stack[stack[0]]]=0; shu[stack[stack[0]]]=tuan; stack[0]--; } }}void dfs(int x,int y){ int i,j; rep(i,x){ int u=chang[i]; if(last[i]!=y){ bz[last[i]]=1; xiao[last[i]]=min(xiao[last[i]],u); dfs(last[i],x); } }}int main(){ while(1){ scanf("%d%d",&n,&m); if(!n&&!m)break; memset(first,0,sizeof(first));num=0; fo(i,1,m){ scanf("%d%d%d",&a[i].x,&a[i].y,&a[i].z);a[i].x++;a[i].y++; add(a[i].x,a[i].y,a[i].z); } memset(bz,0,sizeof(bz)); memset(stack,0,sizeof(stack)); tarjan(1); memset(first,0,sizeof(first));num=0; memset(bz,0,sizeof(bz)); tou=shu[1]; fo(i,1,m){ int u=shu[a[i].x],v=shu[a[i].y]; if(u==v)continue; add(u,v,a[i].z); } ans=0; memset(xiao,127,sizeof(xiao)); dfs(tou,0); fo(i,1,tuan)if(bz[i])ans+=xiao[i]; printf("%lld\n",ans); }}
1 0
- 【NOIP提高】通讯
- 2017.1.15【初中部 NOIP提高组】模拟赛B组 七天使的通讯(angelus) 题解
- 【NOIP提高】钱仓
- 【NOIP提高】种树
- 【NOIP提高】自然数
- 【NOIP提高】礼物
- 【NOIP提高】奇袭
- 【NOIP提高】Value
- 【NOIP提高】Binary
- NOIP提高模拟 Binary
- 【NOIP提高】公约数
- NOIP 提高 公约数
- 【NOIP提高】树上路径
- NOIP提高组 单峰
- NOIP提高组 积木
- 【NOIP提高】看电影
- NOIP提高组 看电影
- NOIP提高组 鼎纹
- Android开源项目推荐之「图片加载到底哪家强」
- 字符串输入小结
- hdu 5627 并查集
- HDU-5748-Bellovin【LIS】
- HDU 1556 Color the ball
- 【NOIP提高】通讯
- 浅谈Android中的PendingIntent
- java ----- 反射
- HUST 1352 Repetitions of Substrings
- poj2240——Arbitrage(Bellman-Ford算法)
- LCS和输出 hdu 1503(Advanced Fruits)
- vim without extern
- DataGuard主备之间解决gap的步骤
- 构造数据类型简单介绍