The Shortest Statement,题解
题目链接
分析:
还是很明白的题意,直接分析问题,首先,这一题真的是给spfa用武之地,m比n大不超过20,但是这并不能使暴力不t,我们考虑一下如何改进一下,我们这样想,这个图只比它的生成树多最多21条边,而树上的最短路有是那么的容易(lca),我们可以先求出在树上两个点之间的最短路,可是非树边也很有可能通过啊,怎么办呢?我们可以这样想,通过至少一个非树边与只通过树边是对立的,也就是说除了只通过非树边的都通过树边,而只通过树边的很好求,下面我们来思考如何求通过至少一个非树边的路径。
如果通过至少一个非树边,那么一定通过这个边的两个顶点那么就好办了,最多一共有42个顶点在非树边两边,直接枚举通过每一个就好了(当然要提前处理出这些顶点的单元最短路)。
还有,这题spfa好像是比dij快(m-n<=20)。
代码(dij)
#include <cstdio>
#include <queue>
#include <cstring>
using namespace std;
const int maxn=1e5+;
struct E{
int to;
int next;
long long val;
int f;
E(){
f=;
}
}ed[maxn*];
int head[maxn];
int tot;
void J(int a,int b,long long c){
tot++;
ed[tot].to=b;
ed[tot].val=c;
ed[tot].next=head[a];
head[a]=tot;
}
int vis[maxn];
int t[maxn][];
long long va[maxn][];
int js;
int a[maxn];
int b[maxn];
long long c[maxn];
int de[maxn];
void Dfs(int x,int fa,int id){
de[x]=de[fa]+;
t[x][]=fa;
va[x][]=ed[id].val;
for(int i=;i<=;i++){
t[x][i]=t[t[x][i-]][i-];
va[x][i]=va[x][i-]+va[t[x][i-]][i-];
}
vis[x]=;
for(int i=head[x];i;i=ed[i].next){
if(ed[i].to==fa||ed[i].f)
continue;
if(vis[ed[i].to]){
ed[i].f=ed[i%?(i+):(i-)].f=;
js++;
a[js]=x;
b[js]=ed[i].to;
c[js]=ed[i].val;
continue;
}
Dfs(ed[i].to,x,i);
}
}
long long dis[][maxn];
int vis2[maxn];
int ha;
struct Node{
int x;
long long dis;
Node(){
}
Node(int a,long long b){
x=a;
dis=b;
}
friend bool operator < (Node a,Node b){
return a.dis>b.dis;
}
};
priority_queue<Node> q;
void dij(int s){
memset(vis2,,sizeof(vis2));
ha++;
dis[ha][s]=;
q.push(Node(s,));
while(!q.empty()){
Node js=q.top();
q.pop();
if(vis2[js.x])
continue;
vis2[js.x]=;
for(int i=head[js.x];i;i=ed[i].next)
if(dis[ha][ed[i].to]>dis[ha][js.x]+ed[i].val){
dis[ha][ed[i].to]=dis[ha][js.x]+ed[i].val;
q.push(Node(ed[i].to,dis[ha][ed[i].to]));
}
}
}
long long lca(int x,int y){
long long ans=;
if(de[x]<de[y])
swap(x,y);
int k=de[x]-de[y];
int ji=;
while(k){
if(k&){
ans+=va[x][ji];
x=t[x][ji];
}
k>>=;
ji++;
}
if(x==y)
return ans;
for(int i=;i>=;i--)
if(t[x][i]!=t[y][i]){
ans+=va[x][i];
ans+=va[y][i];
x=t[x][i];
y=t[y][i];
}
ans+=va[x][]+va[y][];
return ans;
}
long long Min(long long a,long long b){
return a>b?b:a;
}
int main(){
memset(dis,0x3f,sizeof(dis));
int n,m;
scanf("%d%d",&n,&m);
int js1,js2;
long long js3;
for(int i=;i<=m;i++){
scanf("%d%d%lld",&js1,&js2,&js3);
J(js1,js2,js3);
J(js2,js1,js3);
}
Dfs(,,);
for(int i=;i<=js;i++){
dij(a[i]);
dij(b[i]);
}
int q;
scanf("%d",&q);
for(int i=;i<=q;i++){
scanf("%d%d",&js1,&js2);
long long p=lca(js1,js2);
for(int j=;j<=*js;j++)
p=Min(dis[j][js1]+dis[j][js2],p);
printf("%lld\n",p);
}
return ;
}
The Shortest Statement,题解的更多相关文章
- CF1051F The Shortest Statement 题解
题目 You are given a weighed undirected connected graph, consisting of n vertices and m edges. You sho ...
- 【题解】Luogu CF1051F The Shortest Statement
原题传送门:CF1051F The Shortest Statement 题目大意,给你一个稀疏图,q次查询,查询两点之间距离 边数减点小于等于20 这不是弱智题吗,23forever dalao又开 ...
- Codeforces 1051E Vasya and Big Integers&1051F The Shortest Statement
1051E. Vasya and Big Integers 题意 给出三个大整数\(a,l,r\),定义\(a\)的一种合法的拆分为把\(a\)表示成若干个字符串首位相连,且每个字符串的大小在\(l, ...
- codeforces 1051F The Shortest Statement
题目链接:codeforces 1051F The Shortest Statement 题意:\(q\)组询问,求任意两点之间的最短路,图满足\(m-n\leq 20\) 分析:一开始看这道题:fl ...
- The Shortest Statement CodeForces - 1051F(待测试)
#include <iostream> #include <cstdio> #include <sstream> #include <cstring> ...
- Educational Codeforces Round 51 (Rated for Div. 2) F - The Shortest Statement 倍增LCA + 最短路
F - The Shortest Statement emmm, 比赛的时候没有想到如何利用非树边. 其实感觉很简单.. 对于一个询问答案分为两部分求: 第一部分:只经过树边,用倍增就能求出来啦. 第 ...
- CF 1051 F. The Shortest Statement
F. The Shortest Statement http://codeforces.com/contest/1051/problem/F 题意: n个点,m条边的无向图,每次询问两点之间的最短路. ...
- Educational Codeforces Round 51 (Rated for Div. 2) The Shortest Statement
题目链接:The Shortest Statement 今天又在群里看到一个同学问$n$个$n$条边,怎么查询两点直接最短路.看来这种题还挺常见的. 为什么最终答案要从42个点的最短路(到$x,y$) ...
- CF_Edu.#51_Div.2_1051F_The Shortest Statement
F. The Shortest Statement time limit per test:4 seconds memory limit per test:256 megabytes input:st ...
- 题解 CF1051F 【The Shortest Statement】
这道题思路比较有意思,第一次做完全没想到点子上... 看到题目第一反应是一道最短路裸题,但是数据范围1e5说明完全不可能. 这个时候可以观察到题目给出了一个很有意思的条件,就是说边最多比点多20. 这 ...
随机推荐
- 在树莓派3b or 3a or 4a or 4b上搭建OpenWebRX
OpenWebRx OpenWebRX 项目提供了搭建WebSDR的解决方案,该项目基于 Python 编写,除了完全开源外,官方还提供了完备的技术文档.您只需要一台电脑或是树莓派,一个SDR设备和网 ...
- 聊一聊高并发高可用那些事 - Kafka篇
目录 为什么需要消息队列 1.异步 :一个下单流程,你需要扣积分,扣优惠卷,发短信等,有些耗时又不需要立即处理的事,可以丢到队列里异步处理. 2.削峰 :按平常的流量,服务器刚好可以正常负载.偶尔推出 ...
- Canvas绘制圆点线段
最近一个小伙遇到一个需求,客户需要绘制圆点样式的线条. 大致效果是这样的: 思路一:计算并使用arc填充 他自己实现了一种思路,然后咨询我有没有更好的思路. 先看看他的思路是如何实现的,大致代码如下: ...
- vue无法选择上传相同文件
使用h5自带的input type=file时,使用change触发上传事件 <input class="exportss" type="file" id ...
- SpringBoot爬坑系列
1.日志篇 现象 由于日志配置采用原来SpringMVC项目中的log4j.properties 文件,日志采用springboot自带的jar包会出现打印不出日志的情况. 解决 引入原日志包 < ...
- [转载]java内存工具VisualVM的简单使用以及与Idea集成
本文来源https://blog.csdn.net/KingBoyWorld/article/details/75579606 一.idea集成 1.打开设置 windows File->Set ...
- 数值格式化 NumberFormat、 DecimalFormat、 RoundingMode
NumberFormat [简介] java.text.NumberFormat extends java.text.Format extends java.lang.Object 实现的接口:Ser ...
- Water Testing【皮克定理,多边形面积,线段上点的数目】
Water Testing 传送门:链接 来源:UPC 9656 题目描述 You just bought a large piece of agricultural land, but you n ...
- Linux中tomcat的部署
红帽7如何配置tomcat 1.下载tomcat9.0和java-1.8 tomcat的下载地址: https://tomcat.apache.org/ java1.8是radhat7自带: [roo ...
- 数据湖&数据仓库,别再傻傻分不清了
摘要:什么是数据湖?它有什么作用?今天将由华为云技术专家从理论出发,将问题抽丝剥茧,从技术维度娓娓道来. 什么是数据湖 如果需要给数据湖下一个定义,可以定义为这样:数据湖是一个存储企业的各种各样原始数 ...