[Luogu 2169] 正则表达式

<题目链接>


感谢 0xis 推题。

记忆中很久没有过一遍写过一题了…

别被题目名称蒙骗!这不是正则表达式题目!和字符(串)处理一点关系都没有!这是个图论题啊喂!

题都没急,Capella 你急啥?

由题意得,能够本地传输的机子们处于同一强连通分量,于是 Tarjan 一遍,缩点。缩的过程中,对于两个 SCC 之间的边,选短的加。

我这里用一个 map,记录边(pair<int, int>)到边权(int)的映射,然后用 map 判断是否加边就好了。

最短路,跑一个 Dijkstra 即可(珍爱生命,远离某死亡算法不解释)。

输出 1 所在的 SCC 到 n 所在的 SCC 的路径。

#include <algorithm>
#include <cstdio>
#include <cstring>
#include <map>
#include <queue>
#include <stack> #define nullptr NULL const int MAXN = 200010; int n, m; namespace SCC
{
bool exist[MAXN], vis[MAXN];
int num, sum, DFN[MAXN], low[MAXN], SCC[MAXN], dist[MAXN];
std :: stack<int> S;
struct Node
{
int index, dist;
Node(int index, int dist): index(index), dist(dist) {}
bool operator <(const Node& rhs) const
{
return dist > rhs.dist;
}
};
struct Graph
{
struct Edge
{
int to, w;
Edge *next;
Edge(int to, int w, Edge* next): to(to), w(w), next(next) {}
~Edge(void)
{
if(next != nullptr)
delete next;
}
}*head[MAXN];
Graph(int n)
{
std :: fill(head + 1, head + n + 1, (Edge*)nullptr);
}
~Graph(void)
{
for(int i = 1; i <= n; ++i)
delete head[i];
}
void AddEdge(int u, int v, int w)
{
head[u] = new Edge(v, w, head[u]);
}
}*G, *Gnew;
void Tarjan(int u)
{
S.push(u);
exist[u] = true;
DFN[u] = low[u] = ++num;
int v;
for(Graph :: Edge *i = G -> head[u]; i != nullptr; i = i -> next)
if(!DFN[v = i -> to])
{
Tarjan(v);
low[u] = std :: min(low[u], low[v]);
}
else if(exist[v])
low[u] = std :: min(low[u], DFN[v]);
if(DFN[u] == low[u])
{
++sum;
do
{
exist[v = S.top()] = false;
S.pop();
SCC[v] = sum;
}
while(u ^ v);
}
}
void Shrink(void)
{
std :: map<std :: pair<int, int>, int> QAQ;
std :: pair<int, int> t;
Gnew = new Graph(sum);
for(int u = 1, v; u <= n; ++u)
for(Graph :: Edge *i = G -> head[u]; i != nullptr; i = i -> next)
if(!QAQ.count(t = std :: make_pair(SCC[u], SCC[v = i -> to])) || i -> w < QAQ[t])
{
Gnew -> AddEdge(SCC[u], SCC[v], i -> w);
QAQ[t] = i -> w;
}
}
void Dijkstra(int S)
{
std :: priority_queue<Node> Q;
memset(dist, 0x3f, sizeof dist);
Q.push(Node(S, dist[S] = 0));
while(!Q.empty())
{
int u = Q.top().index, v;
Q.pop();
if(!vis[u])
{
vis[u] = true;
for(Graph :: Edge *i = Gnew -> head[u]; i != nullptr; i = i -> next)
if(dist[v = i -> to] > dist[u] + i -> w)
Q.push(Node(v, dist[v] = dist[u] + i -> w));
}
}
}
void Solve(void)
{
for(int i = 1; i <= n; ++i)
if(!DFN[i])
Tarjan(i);
Shrink();
Dijkstra(SCC[1]);
printf("%d\n", dist[SCC[n]]);
}
} int main(void)
{
scanf("%d %d", &n, &m);
SCC :: G = new SCC :: Graph(n);
for(int i = 1, u, v, w; i <= m; ++i)
{
scanf("%d %d %d", &u, &v, &w);
SCC :: G -> AddEdge(u, v, w);
}
SCC :: Solve();
return 0;
}

谢谢阅读。

[Luogu 2169] 正则表达式的更多相关文章

  1. 【luogu P2169 正则表达式】 题解

    题目链接:https://www.luogu.org/problemnew/show/P2169 tarjan缩点 + SPFA 缩完点之后加边注意别写错. 也可以不用建两个图,可以在一张图上判断是否 ...

  2. JS正则表达式常用总结

    正则表达式的创建 JS正则表达式的创建有两种方式: new RegExp() 和 直接字面量. //使用RegExp对象创建 var regObj = new RegExp("(^\\s+) ...

  3. Python高手之路【五】python基础之正则表达式

    下图列出了Python支持的正则表达式元字符和语法: 字符点:匹配任意一个字符 import re st = 'python' result = re.findall('p.t',st) print( ...

  4. C# 正则表达式大全

    文章导读 正则表达式的本质是使用一系列特殊字符模式,来表示某一类字符串.正则表达式无疑是处理文本最有力的工具,而.NET提供的Regex类实现了验证正则表达式的方法.Regex 类表示不可变(只读)的 ...

  5. C#基础篇 - 正则表达式入门

    1.基本概念 正则表达式(Regular Expression)就是用事先定义好的一些特定字符(元字符)或普通字符.及这些字符的组合,组成一个“规则字符串”,这个“规则字符串”用来判断我们给定的字符串 ...

  6. JavaScript正则表达式,你真的知道?

    一.前言 粗浅的编写正则表达式,是造成性能瓶颈的主要原因.如下: var reg1 = /(A+A+)+B/; var reg2 = /AA+B/; 上述两个正则表达式,匹配效果是一样的,但是,效率就 ...

  7. Python 正则表达式入门(中级篇)

    Python 正则表达式入门(中级篇) 初级篇链接:http://www.cnblogs.com/chuxiuhong/p/5885073.html 上一篇我们说在这一篇里,我们会介绍子表达式,向前向 ...

  8. 【JS基础】正则表达式

    正则表达式的() [] {}有不同的意思. () 是为了提取匹配的字符串.表达式中有几个()就有几个相应的匹配字符串. (\s*)表示连续空格的字符串. []是定义匹配的字符范围.比如 [a-zA-Z ...

  9. JavaScript 正则表达式语法

    定义 JavaScript定义正则表达式有两种方法. 1.RegExp构造函数 var pattern = new RegExp("[bc]at","i"); ...

随机推荐

  1. 【CS231N】4、神经网络

    一.疑问 二.常用激活函数 1. Sigmoid ​ sigmoid将输入实数值"挤压"到0到1范围内.更具体地说,很大的负数变成0,很大的正数变成1.它对于神经元的激活频率有良好 ...

  2. vmdk->vhdx

    https://cloudbase.it/qemu-img-windows/ Usage examplesConvert a QCOW2, RAW, VMDK or VDI image to VHDX ...

  3. [转帖]超能课堂 CPU制作过程

    http://www.expreview.com/50814.html 一般来说,我们对IC芯片的了解仅限于它概念,但是对于已经应用到各式各样的数码产品中IC芯片是怎么来的?大家可能只知道制作IC芯片 ...

  4. Ubuntu16.04中MySQL之中文不能插入问题

    转自:http://blog.csdn.net/fr555wlj/article/details/55668476 今天下午在学习MySQL时,向表中插入一条数据含有中文,结果报错如下, ERROR ...

  5. IE下Userdata本地化存储

    这两天看了下Discuz x2发帖的实时保存机制,涉及到本地化存储,所以上网查了下,Firefox等支持HTML5的浏览器使用window.localStorage或window.sessionSto ...

  6. Multiple Instance Learning

    ///////////////////////////////////////////推荐学习组////////////////////////////// http://www.robots.ox. ...

  7. 【题解】JSOI2009球队收益 / 球队预算

    为什么大家都不写把输的场次增加的呢?我一定要让大家知道,这并没有什么关系~所以 \(C[i] <= D[i]\) 的条件就是来卖萌哒?? #include <bits/stdc++.h&g ...

  8. 【BZOJ3609】人人尽说江南好(博弈论)

    [BZOJ3609]人人尽说江南好(博弈论) 题面 BZOJ 洛谷 题解 昨天考试的时候,毒瘤出题人出了一个\(noip\)博弈十合一然后他就被阿鲁巴了,因为画面残忍,就不再展开. 这题是他的十合一中 ...

  9. 树状数组+二分答案查询第k大的数 (团体程序设计天梯赛 L3-002. 堆栈)

    前提是数的范围较小 1 数据范围:O(n) 2 查第k大的数i:log(n)(树状数组查询小于等于i的数目)*log(n)(二分找到i) 3 添加:log(n) (树状数组) 4 删除:log(n) ...

  10. Python 爬虫入门(一)

    毕设是做爬虫相关的,本来想的是用java写,也写了几个爬虫,其中一个是爬网易云音乐的用户信息,爬了大概100多万,效果不是太满意.之前听说Python这方面比较强,就想用Python试试,之前也没用过 ...