【LOJ】#2587. 「APIO2018」铁人两项
题解
学习了圆方树!(其实是复习了Tarjan求点双)
我又双叒叕忘记了tarjan点双一个最重要,最重要的事情!
就是……假如low[v] >= dfn[u],我们就找到了一个点双,开始建立方点,但是,虽然这个点双包括点u,然而这个u啊,它很花心可能会在很多个点双里!首先u,不能被弹出去
其次呢,在栈里,u和这个点双其他的点,在栈里不一定是连续的一段,一般都是 u (一堆别的点) 点双里的点……,所以我们弹出到v,就结束这个点双,然后手动把u加进去
然后我们再来看这道题,我们枚举两个点,起点和终点,能当做中转点的点,一定是路上经过的点双里点的和
那么我们把所有点的值设成-1,方点的值设成点双里点的个数,然后就变成了对圆方树上所有路径统计路径长度,一个优秀做法就是枚举每个点看看会被多少条路径经过
代码
#include <iostream>
#include <cstdio>
#include <vector>
//#define ivorysi
#define pb push_back
#define MAXN 100005
#define space putchar(' ')
#define enter putchar('\n')
using namespace std;
typedef long long int64;
template<class T>
void read(T &res) {
res = 0;char c = getchar();T f = 1;
while(c < '0' || c > '9') {
if(c == '-') f = -1;
c = getchar();
}
while(c >= '0' && c <= '9') {
res = res * 10 + c - '0';
c = getchar();
}
res *= f;
}
template<class T>
void out(T x) {
if(x < 0) putchar('-');
if(x >= 10) {
out(x / 10);
}
putchar('0' + x % 10);
}
struct node {
int to,next;
}E[MAXN * 4];
int N,M,Cnt;
int head[MAXN],sumE,S;
int low[MAXN],dfn[MAXN],idx,sta[MAXN],top,tot,Val[MAXN * 4],siz[MAXN * 4];
int64 ans = 0;
vector<int> son[MAXN * 4];
void add(int u,int v) {
E[++sumE].to = v;
E[sumE].next = head[u];
head[u] = sumE;
}
void Tarjan(int u,int fa) {
dfn[u] = low[u] = ++idx;
sta[++top] = u;
Val[u] = -1;
siz[u] = 1;
for(int i = head[u] ; i ; i = E[i].next) {
int v = E[i].to;
if(dfn[v] && v != fa) {
low[u] = min(dfn[v],low[u]);
}
else if(!dfn[v]) {
Tarjan(v,u);
if(low[v] >= dfn[u]) {
++Cnt;
son[u].pb(Cnt);
while(1) {
int x = sta[top--];
Val[Cnt]++;
son[Cnt].pb(x);
siz[Cnt] += siz[x];
if(x == v) break;
}
Val[Cnt]++;
siz[u] += siz[Cnt];
}
else low[u] = min(low[v],low[u]);
}
}
}
void dfs(int u) {
if(Val[u] < 0) ans += (S - 1) * Val[u];
ans += 1LL * (S - siz[u]) * siz[u] * Val[u];
for(auto k : son[u]) {
ans += 1LL * siz[k] * (S - siz[k]) * Val[u];
}
for(auto k : son[u]) dfs(k);
}
void Init() {
read(N);read(M);
int u,v;
for(int i = 1 ; i <= M ; ++i) {
read(u);read(v);
add(u,v);add(v,u);
}
Cnt = N;
}
void Solve() {
for(int i = 1 ; i <= N ; ++i) {
if(!dfn[i]) {
Tarjan(i,0);
S = siz[i];
dfs(i);
}
}
printf("%lld\n",ans);
}
int main() {
#ifdef ivorysi
freopen("f1.in","r",stdin);
#endif
Init();
Solve();
return 0;
}
【LOJ】#2587. 「APIO2018」铁人两项的更多相关文章
- 【刷题】LOJ 2587 「APIO2018」铁人两项
题目描述 比特镇的路网由 \(m\) 条双向道路连接的 \(n\) 个交叉路口组成. 最近,比特镇获得了一场铁人两项锦标赛的主办权.这场比赛共有两段赛程:选手先完成一段长跑赛程,然后骑自行车完成第二段 ...
- LOJ #2587「APIO2018」铁人两项
是不是$ vector$存图非常慢啊...... 题意:求数对$(x,y,z)$的数量使得存在一条$x$到$z$的路径上经过$y$,要求$x,y,z$两两不同 LOJ #2587 $ Solutio ...
- LOJ 2587 「APIO2018」铁人两项——圆方树
题目:https://loj.ac/problem/2587 先写了 47 分暴力. 对于 n<=50 的部分, n3 枚举三个点,把图的圆方树建出来,合法条件是 c 是 s -> f 路 ...
- loj2587 「APIO2018」铁人两项[圆方树+树形DP]
主要卡在一个结论上..关于点双有一个常用结论,也经常作为在圆方树/简单路径上的良好性质,对于任意点双内互不相同的三点$s,c,t$,都存在简单路径$s\to c\to t$,证明不会.可以参见clz博 ...
- loj2587 「APIO2018」铁人两项
圆方树orz,参见猫的课件(apio和wc的)以及这里那里 #include <iostream> #include <cstdio> using namespace std; ...
- 【APIO2018】铁人两项
[APIO2018]铁人两项 题目描述 大意就是给定一张无向图,询问三元组\((s,c,f)\)中满足\(s\neq c\neq f\)且存在\((s\to c\to f)\)的简单路径(每个点最多经 ...
- 【APIO2018】铁人两项(圆方树,动态规划)
[APIO2018]铁人两项(圆方树,动态规划) 题面 UOJ 洛谷 BZOJ 题解 嘤嘤嘤,APIO的时候把一个组合数写成阶乘了,然后这题的70多分没拿到 首先一棵树是很容易做的,随意指定起点终点就 ...
- [APIO2018] Duathlon 铁人两项 圆方树,DP
[APIO2018] Duathlon 铁人两项 LG传送门 圆方树+简单DP. 不会圆方树的话可以看看我的另一篇文章. 考虑暴力怎么写,枚举两个点,答案加上两个点之间的点的个数. 看到题面中的一句话 ...
- LOJ #2585. 「APIO2018」新家
#2585. 「APIO2018」新家 https://loj.ac/problem/2585 分析: 线段树+二分. 首先看怎样数颜色,正常的时候,离线扫一遍右端点,每次只记录最右边的点,然后查询左 ...
随机推荐
- 两步建立 ssh 反向隧道
因为需要在寝室访问实验室的内部网络,刚好自己购买了阿里云,因此,可以远端干活了,mark下方法: 第一步:在内网的服务器上,使用ssh 命令建立反向隧道 publicUserName@publicIp ...
- 蓝桥杯 算法提高 学霸的迷宫 经典BFS问题
算法提高 学霸的迷宫 时间限制:1.0s 内存限制:256.0MB 问题描述 学霸抢走了大家的作业,班长为了帮同学们找回作业,决定去找学霸决斗.但学霸为了不要别人打扰,住在一个城 ...
- Django 2.0.1 官方文档翻译: 编写你的第一个 Django app,第五部分(Page 10)
编写你的第一个 Django app,第五部分(Page 10)转载请注明链接地址 我们继续建设我们的 Web-poll 应用,本节我们会为它创建一些自动测试. 介绍自动测试 什么是自动测试 测试是简 ...
- [整理]LumiSoft.Net 开源组件
http://www.lumisoft.ee/lsWWW/download/downloads/Net/info.txt SVN: https://svn.lumisoft.ee:8443/svn/L ...
- Java后台获取前端utf-8格式 ;空格,使用trim()消除不了的解决办法
byte bytes[] = {(byte) 0xC2,(byte) 0xA0}; String UTFSpace = new String(bytes,"utf-8"); htm ...
- 20155202 2016-2017-2 《Java程序设计》第7周学习总结
20155202 2016-2017-2 <Java程序设计>第7周学习总结 教材学习内容总结 世界协调时间:UTC 采用 闰秒修正 Epoch为某特定时代开始,时间轴上某一瞬间 Unix ...
- vue_列表渲染
vue列表渲染 <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <t ...
- Python基础入门(一)
1.在线教程 2.Python下载地址,安装步骤,就是next.next... 3.配置环境变量(win8) 电脑 --> 属性 --> 高级系统设置 --> 环境变量,找到系统变量 ...
- 单调栈(G - Sliding Window POJ - 2823 )
题目链接:https://cn.vjudge.net/contest/276251#problem/G 题目大意:给你n和m,然后问你对于(m,n)这中间的每一个数,(i-m+1,i)这个区间的最小值 ...
- 使用 script 命令记录用户操作行为
Script 命令可以帮助管理员记录用户的操作行为,包括用户查看文件中的哪些具体内容,写入了哪些文件,写了些什么都能看到,比较详细的记录了用户的操作行为. 本文对此进行简要说明. 1.添加日志记录 e ...