AcWing 398. 交通实时查询系统
大型补档计划
只有割点是必行点。
在任意一个点双中,都有分叉没有点交集的两条路径。
所以 v-DCC 缩点。
但是他问的是路径走到另一条路径的必行点。我蒙蔽了,发现自己对无向图双联通分量理解不够。因为一条边必然属于且只属于一个点双联通分量,为什么呢?因为就选这条边的两个点就构成了一个点双联通分量,所以必然存在包含的,并且由于极大性,只属于一个也显然。
缩点后变成一颗树。然后就变成了:在一颗树中,任意两点间有多少个特殊的点(割点?),用 LCA + 树上差分即可。
upd1:顺便提一句,这道题不一定保证联通,可能是森林,所以要多次dfs,但是第一次写我没多次也过了,说明数据较水。
upd2:为啥我uva WA了。
#include <cstdio>
#include <iostream>
#include <vector>
#include <cstring>
using namespace std;
const int N = 20005, M = 200005, L = 15;
int n, m, Q, num, newId[N];
int dfn[N], low[N], dfncnt, s[N], c[N], top, cnt, id[M], d[N];
bool vis[N];
int fa[N][L], dep[N];
vector<int> dcc[N], g[N];
bool cut[N];
int head[N], numE = 1;
struct E{
int next, v;
} e[M];
void inline add(int u, int v) {
e[++numE] = (E) { head[u], v };
head[u] = numE;
}
void tarjan(int u, int rt) {
dfn[u] = low[u] = ++dfncnt;
s[++top] = u;
if (u == rt && !head[u]) {
dcc[++cnt].push_back(u);
return;
}
int flag = 0;
for (int i = head[u]; i; i = e[i].next) {
int v = e[i].v;
if (!dfn[v]) {
tarjan(v, rt); low[u] = min(low[u], low[v]);
if (low[v] >= dfn[u]) {
flag++;
if (u != rt || flag > 1) cut[u] = true;
int y; ++cnt;
do {
y = s[top--];
dcc[cnt].push_back(y);
} while (y != v);
dcc[cnt].push_back(u);
}
} else low[u] = min(low[u], dfn[v]);
}
}
void dfs(int u) {
vis[u] = true;
for (int i = 1; i < L && fa[u][i - 1]; i++)
fa[u][i] = fa[fa[u][i - 1]][i - 1];
if (u > cnt) d[u]++;
for (int i = 0; i < g[u].size(); i++) {
int v = g[u][i];
if (v == fa[u][0]) continue;
fa[v][0] = u, dep[v] = dep[u] + 1, d[v] = d[u];
dfs(v);
}
}
int lca(int x, int y) {
if (dep[x] < dep[y]) swap(x, y);
for (int i = L - 1; ~i; i--)
if (dep[x] - (1 << i) >= dep[y]) x = fa[x][i];
if (x == y) return x;
for (int i = L - 1; ~i; i--)
if (fa[x][i] != fa[y][i]) x = fa[x][i], y = fa[y][i];
return fa[x][0];
}
int main() {
while (scanf("%d%d", &n, &m), n || m) {
for (int i = 1, x, y; i <= m; i++) {
scanf("%d%d", &x, &y);
add(x, y); add(y, x);
}
for (int i = 1; i <= n; i++) if (!dfn[i]) tarjan(i, i);
num = cnt;
for (int i = 1; i <= n; i++) if (cut[i]) newId[i] = ++num;
for (int i = 1; i <= cnt; i++) {
for (int j = 0; j < dcc[i].size(); j++) {
int x = dcc[i][j];
if (cut[x]){
g[newId[x]].push_back(i);
g[i].push_back(newId[x]);
}
c[x] = i;
}
for (int j = 0; j < dcc[i].size(); j++) {
int x = dcc[i][j];
for (int k = head[x]; k; k = e[k].next) {
int v = e[k].v;
if (c[v] == i) id[k >> 1] = i;
}
}
}
for (int i = 1; i <= num; i++) if (!vis[i]) dfs(i);
scanf("%d", &Q);
while (Q--) {
int a, b; scanf("%d%d", &a, &b);
a = id[a], b = id[b];
int p = lca(a, b);
printf("%d\n", d[fa[a][0]] - d[fa[p][0]] + d[fa[b][0]] - d[p]);
}
numE = 1;
memset(cut, false, sizeof cut);
memset(newId, 0, sizeof newId);
memset(c, 0, sizeof c);
memset(head, 0, sizeof head);
memset(dfn, 0, sizeof dfn);
memset(vis, false, sizeof vis);
memset(id, 0, sizeof id);
memset(fa, 0, sizeof fa);
for (int i = 1; i <= num; i++) g[i].clear();
for (int i = 1; i <= cnt; i++) dcc[i].clear();
dfncnt = cnt = 0;
}
return 0;
}
AcWing 398. 交通实时查询系统的更多相关文章
- 实时查询系统架构:spark流式处理+HBase+solr/ES查询
最近要做一个实时查询系统,初步协商后系统的框架 1.流式计算:数据都给spark 计算后放回HBase 2.查询:查询采用HBase+Solr/ES
- Windows系统CPU和内存状态实时查询(Java)
一.背景 需要查询Windows服务器的CPU和内存状态. Linux系统查询CPU和内存状态很简单,一个top命令搞定,Windows就稍微麻烦一些了. 经过资料查找,发现jdk目前不能直接查询系统 ...
- 转: 透过CAT,来看分布式实时监控系统的设计与实现
评注: 开源的分布式监控系统 转:http://www.infoq.com/cn/articles/distributed-real-time-monitoring-and-control-syste ...
- 基于三星ARM9(S3C2410)的交通违章抓拍系统的开发
ARM9的交通违章抓拍系统的开发 ARM9的交通违章抓拍系统的开发 智能交通系统(ITS)将先进的信息技术.数据通讯传输技术.电子控制技术.计算机处理技术等应用于交通运输行业,从而实现各种运输方式 ...
- 透过CAT,来看分布式实时监控系统的设计与实现
2011年底,我加入大众点评网,出于很偶然的机会,决定开发CAT,为各个业务线打造分布式实时监控系统,CAT的核心概念源自eBay闭源系统CAL----eBay的几大法宝之一. 在当今互联网时代,业务 ...
- 基于Impala平台打造交互查询系统
本文来自网易云社区 原创: 蒋鸿翔 DataFunTalk 本文根据网易大数据蒋鸿翔老师DataFun Talk--"大数据从底层处理到数据驱动业务"中分享的<基于Impal ...
- 实时查询引擎 - Facebook Presto 介绍与应用
1. Presto 是什么 Facebook presto是什么,继Facebook创建了HIVE神器后的又一以SQL语言作为接口的分布式实时查询引擎,可以对PB级的数据进行快速的交互式查询.它支 ...
- Druid:一个用于大数据实时处理的开源分布式系统——大数据实时查询和分析的高容错、高性能开源分布式系统
转自:http://www.36dsj.com/archives/28590 Druid 是一个用于大数据实时查询和分析的高容错.高性能开源分布式系统,旨在快速处理大规模的数据,并能够实现快速查询和分 ...
- PB级数据实时查询,滴滴Elasticsearch多集群架构实践
PB级数据实时查询,滴滴Elasticsearch多集群架构实践 mp.weixin.qq.com 点击上方"IT牧场",选择"设为星标"技术干货每日送达 点 ...
随机推荐
- sk_buff结构--转载
套接字缓存之sk_buff结构 https://www.cnblogs.com/wanpengcoder/p/7529486.html 来此此处 sk_buff结构用来描述已接收或者待发送的数据报文信 ...
- Socket 套接字的系统调用
socket 结构 /** * struct socket - general BSD socket * @state: socket state (%SS_CONNECTED, etc) * @ty ...
- 315. Count of Smaller Numbers After Self(二分或者算法导论中的归并求逆序数对)
You are given an integer array nums and you have to return a new counts array. The counts array has ...
- dp背包 面试题 08.11. 硬币
https://leetcode-cn.com/problems/coin-lcci/ 硬币.给定数量不限的硬币,币值为25分.10分.5分和1分,编写代码计算n分有几种表示法.(结果可能会很大,你需 ...
- 03、MyBatis 映射文件
1.XML映射器 2.select Select元素来定义查询操作 Id:唯一标识符 - 用来引用这条语句,需要和接口的方法名一致 parameterType:参数类型 - 可以不传,MyBatis会 ...
- Environment Cubemap
要创建一个Cubemap(将您的环境捕获到一个Cubemap中),您需要去Unity Documentation复制RenderCubemapWizard.cs脚本! 然后在"Project ...
- 利用代理IP池(proxy pool)搭建免费ip代理和api
先看这里!!!---->转载:Python爬虫代理IP池(proxy pool) WIIN10安装中遇到的问题: 一.先安装Microsoft Visual C++ Compiler for P ...
- kali 系列学习05 - Nessus 安装及配置
Nessus 安装 1.https://www.tenable.com/products/nessus/select-your-operating-system 点此下载nessus选择适合自己 ...
- Sound Forge常规功能详解
Sound Forge是一款有口皆碑的音频编辑软件,专为录音.母带处理和音频编辑开发.但是该如何使用Sound Forge呢,Sound Forge经常用到的功能有哪些呢?今天小编通过该文章给大家进行 ...
- 从本质上学会基于HarmonyOS开发Hi3861(主要讲授方法)
引言:花半秒钟就看透事物本质的人,和花一辈子都看不透事物本质的人,注定是截然不同的命运 做开发也一样,如果您能看透开发的整个过程,就不会出现"学会了某个RTOS的开发,同样的RTOS开发换一 ...