tarjan模板
tarjan
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <cstring>
#include <string>
#include <algorithm>
#include <set>
#include <map>
#include <queue>
#include <iostream>
using namespace std; #define ll long long const int maxn=1e4+;
const int inf=1e9;
const double eps=1e-; struct node
{
int d;
node *to;
}*e[maxn]; int id,dfn[maxn],low[maxn],tot_st,st[maxn],m,group[maxn];
bool vis[maxn],vis_st[maxn]; /**
id:编号 每增加一个点,++id
每增加一个点,加入栈中
low:点的编号
dfn:点以及后续点通过一条边能到的最小编号点的编号 同一个类 dfn[d]=low[d] 栈中,第x个数d到栈顶 任意点的low值为dfn[d]
st:栈 若点变为在一个类中时,从栈中弹出
vis_st : 当点还未标记到类中时,可以使用 m:类的个数
group:每个点所在的类
**/ void tarjan(int d)
{
int dd;
vis[d]=;
dfn[d]=low[d]=++id;
st[++tot_st]=d;
node *p=e[d];
while (p)
{
dd=p->d;
if (!vis[dd])
{
tarjan(dd);
low[d]=min(low[d],low[dd]);
}
else if (!vis_st[dd])
low[d]=min(low[d],dfn[dd]);
p=p->to;
}
if (dfn[d]==low[d])
{
m++;
int g=tot_st;
while (st[tot_st]!=d)
{
group[st[tot_st]]=m;
vis_st[st[tot_st]]=;
tot_st--;
}
group[st[tot_st]]=m;
vis_st[st[tot_st]]=;
tot_st--;
g-=tot_st; ///类的大小
}
} int main()
{
node *p;
int n,q,x,y,i;
scanf("%d%d",&n,&q);
while (q--)
{
scanf("%d%d",&x,&y);
///注意单边还是双边
p=new node();
p->d=y;
p->to=e[x];
e[x]=p;
}
for (i=;i<=n;i++)
if (!vis[i])
tarjan(i);
return ;
}
/* */
luogu P1726 上白泽慧音
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <cstring>
#include <string>
#include <algorithm>
#include <set>
#include <map>
#include <queue>
#include <iostream>
using namespace std; #define ll long long const int maxn=1e4+;
const int inf=1e9;
const double eps=1e-; struct node
{
int d;
node *to;
}*e[maxn]; int id,dfn[maxn],low[maxn],tot_st,st[maxn],m,group[maxn]; ///m:类的个数
bool vis[maxn],vis_st[maxn]; ///st:栈,存储未被'类‘标签的点 int ind,maxg=,md; void tarjan(int d)
{
int dd;
vis[d]=;
dfn[d]=low[d]=++id;
st[++tot_st]=d;
node *p=e[d];
while (p)
{
dd=p->d;
if (!vis[dd])
{
tarjan(dd);
low[d]=min(low[d],low[dd]);
}
else if (!vis_st[dd])
low[d]=min(low[d],dfn[dd]);
p=p->to;
}
if (dfn[d]==low[d])
{
m++;
int g=tot_st,mind=inf;
while (st[tot_st]!=d)
{
group[st[tot_st]]=m;
mind=min(mind,st[tot_st]);
vis_st[st[tot_st]]=;
tot_st--;
}
group[st[tot_st]]=m;
mind=min(mind,st[tot_st]);
vis_st[st[tot_st]]=;
tot_st--;
g-=tot_st;
if (maxg<g || (maxg==g && mind<md))
ind=m,maxg=g,md=mind;
}
} int main()
{
node *p;
int n,q,x,y,z,i;
scanf("%d%d",&n,&q);
while (q--)
{
scanf("%d%d%d",&x,&y,&z);
p=new node();
p->d=y;
p->to=e[x];
e[x]=p;
if (z==)
{
p=new node();
p->d=x;
p->to=e[y];
e[y]=p;
}
}
for (i=;i<=n;i++)
if (!vis[i])
tarjan(i);
printf("%d",maxg);
bool v=;
for (i=;i<=n;i++)
if (group[i]==ind)
{
if (!v)
printf("\n"),v=;
else
printf(" ");
printf("%d",i);
}
return ;
}
/* */
luogu P3387 【模板】缩点
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <cstring>
#include <string>
#include <algorithm>
#include <set>
#include <map>
#include <queue>
#include <iostream>
using namespace std; #define ll long long const int maxn=1e4+;
const int inf=1e9;
const double eps=1e-; /*
题目描述
给定一个n个点m条边有向图,每个点有一个权值,求一条路径,使路径经过的点权值之和最大。你只需要求出这个权值和。
允许多次经过一条边或者一个点,但是,重复经过的点,权值只计算一次。 第一行,n,m
第二行,n个整数,依次代表点权
第三至m+2行,每行两个整数u,v,表示u->v有一条有向边 共一行,最大的点权之和。 2 2
1 1
1 2
2 1 2
*/ struct node
{
int d;
node *to;
}*e[maxn],*gr[maxn]; int id,dfn[maxn],low[maxn],tot_st,st[maxn],m,group[maxn];
bool vis[maxn],vis_st[maxn];
int v[maxn],ans[maxn];/// /**
id:编号 每增加一个点,++id
每增加一个点,加入栈中
low:点的编号
dfn:点以及后续点通过一条边能到的最小编号点的编号 同一个类 dfn[d]=low[d] 栈中,第x个数d到栈顶 任意点的low值为dfn[d]
st:栈 若点变为在一个类中时,从栈中弹出
vis_st : 当点还未标记到类中时,可以使用 m:类的个数
group:每个点所在的类
**/ void tarjan(int d)
{
int dd;
vis[d]=;
dfn[d]=low[d]=++id;
st[++tot_st]=d;
node *p=e[d];
while (p)
{
dd=p->d;
if (!vis[dd])
{
tarjan(dd);
low[d]=min(low[d],low[dd]);
}
else if (!vis_st[dd])
low[d]=min(low[d],dfn[dd]);
p=p->to;
}
if (dfn[d]==low[d])
{
m++;
while (st[tot_st]!=d)
{
group[st[tot_st]]=m; ///
vis_st[st[tot_st]]=;
tot_st--;
}
group[st[tot_st]]=m; ///
vis_st[st[tot_st]]=;
tot_st--;
}
} void dfs(int d)
{
node *p=gr[d];
int dd,add=;
vis[d]=;
while (p)
{
dd=p->d;
if (!vis[dd])
dfs(dd);
add=max(add,ans[dd]); ///点d到达下一个点,最大的值 千万注意这个是放在外面的
p=p->to;
}
ans[d]+=add;
} int main()
{
node *p,*r;
int n,q,x,y,i,d;
scanf("%d%d",&n,&q); for (i=;i<=n;i++) ///点权
scanf("%d",&v[i]); while (q--)
{
scanf("%d%d",&x,&y);
///注意单边还是双边
p=new node();
p->d=y;
p->to=e[x];
e[x]=p;
}
for (i=;i<=n;i++)
if (!vis[i])
tarjan(i); for (i=;i<=n;i++)
{
ans[group[i]]+=v[i]; ///同一类,能互相访问所有的点
p=e[i];
while (p)
{
d=p->d;
if (group[i]!=group[d])
{
r=new node(); ///变量名要有区分
r->d=group[d];
r->to=gr[group[i]];
gr[group[i]]=r; // printf("%d %d\n",group[i],group[d]);
}
p=p->to;
}
} ///tarjan+缩点后无环
memset(vis,,sizeof(vis));
for (i=;i<=n;i++)
if (!vis[i])
dfs(i);
int maxa=;
for (i=;i<=n;i++)
maxa=max(maxa,ans[i]);
printf("%d",maxa);
return ;
}
/*
3 2
1 2 3
1 2
1 3
*/
luogu P3388 【模板】割点(割顶)
tarjan模板的更多相关文章
- 图论算法-Tarjan模板 【缩点;割顶;双连通分量】
图论算法-Tarjan模板 [缩点:割顶:双连通分量] 为小伙伴们总结的Tarjan三大算法 Tarjan缩点(求强连通分量) int n; int low[100010],dfn[100010]; ...
- UOJ #146. 【NOIP2015】信息传递 连通分量 tarjan模板题
http://uoj.ac/problem/146 题解:强连通分量 tarjan模板题.同时试了一下codeblock #include<bits/stdc++.h> using nam ...
- 学渣乱搞系列之Tarjan模板合集
学渣乱搞系列之Tarjan模板合集 by 狂徒归来 一.求强连通子图 #include <iostream> #include <cstdio> #include <cs ...
- 洛谷1726 上白泽慧音 tarjan模板
题目描述 在幻想乡,上白泽慧音是以知识渊博闻名的老师.春雪异变导致人间之里的很多道路都被大雪堵塞,使有的学生不能顺利地到达慧音所在的村庄.因此慧音决定换一个能够聚集最多人数的村庄作为新的教学地点.人间 ...
- 算法问题实战策略 MEETINGROOM 附一份tarjan模板
地址 https://algospot.com/judge/problem/read/MEETINGROOM 解答 2-sat 代码样例过了 没有ac. 我又没有正确代码对拍..... 已确认是输出 ...
- POJ 2186:Popular Cows Tarjan模板题
Popular Cows Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 25945 Accepted: 10612 De ...
- Tarjan 模板,高级并查集
第一个模板有误!!!! 请见谅!!! 要怪就怪HDU吧,竟然让我过了 第二个模板是正确的.请翻到下面看更新 HDU 1269 评论区居然有人说用并查集过了,其实回想一下 求无向图的连通分量,就是并查集 ...
- 强连通分量(Tarjan)模板
贴模板,备忘. 模板1: #include<iostream> #include<cstring> #include<cmath> #include<cstd ...
- HDU:1269-迷宫城堡(tarjan模板)
迷宫城堡 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) Problem Descri ...
随机推荐
- Network Policy - 每天5分钟玩转 Docker 容器技术(171)
Network Policy 是 Kubernetes 的一种资源.Network Policy 通过 Label 选择 Pod,并指定其他 Pod 或外界如何与这些 Pod 通信. 默认情况下,所有 ...
- java实现Windows记事本
给大家分享下我之前的作品: 源文件下载: 链接:https://pan.baidu.com/s/1N45VsS9aVgmvhvYjRLxBrA 提取码:b9fg 源码: JF_Notpad.jav ...
- FFmpeg AVPacket相关主要函数介绍
1.AVPacket相关函数介绍 操作AVPacket的函数大约有30个,主要分为:AVPacket的创建初始化,AVPacket中的data数据管理(clone,free,copy),AVPacke ...
- Git 生成SSH Key
背景:服务器是LINUX系统(centos7),使用GitLab管理git代码库.各个客户端通过sourcetree 工具,采用SSH获取.提交代码.使用SSH的方式需要公钥和私钥.下面介绍秘钥的生成 ...
- vue 路由元信息
官方文档:路由meta元信息 前言: 在设置面包屑导航还有菜单栏的时候,路由的meta字段可以自定义我们需要的信息,然后路由跳转的时候,提供我们判断条件 文档: 定义路由的时候可以配置 meta 字段 ...
- Redhat7.3更换CentOS7 yum源
Redhat yum源是收费的,没有注册的Redhat机器是不能使用yum源的. 1.当前系统环境: 系统版本:Red Hat Enterprise Linux Server release 7.3 ...
- centos7下kubernetes(12。kubernetes-service)
Service:定义了一个服务得访问入口地址,前端的应用通过这个入口地址访问其背后得一组由pod副本组成的集群实例: service与后端的pod副本集群之间则是通过label selector来实现 ...
- 011_Python中单线程、多线程和多进程的效率对比实验
Python是运行在解释器中的语言,查找资料知道,python中有一个全局锁(GIL),在使用多进程(Thread)的情况下,不能发挥多核的优势.而使用多进程(Multiprocess),则可以发挥多 ...
- NodeJS之异常处理
1. 为什么要处理异常? 如果我们不处理异常的话,直接会导致程序奔溃,用户体验比较差,因此我们要对异常进行处理,当出现异常的情况下,我们要给用户一个友好的提示,并且记录该异常,方便我们排查. 2. 在 ...
- [看图说话]在VMware Workstation 9中安装Mac OS X 10.8 Mountain Lion
本文环境: CPU:Intel Core i7 920: OS:Windows 7: 内存:8G: 玩Hackintosh各有各的理由,不管什么理由,利用虚拟机安装Mac OS X都是一个可行的办法. ...