完结撒花!!!!!!!!!!!

最后一题填坑1A仙人掌WWWWWWW我真流弊

首先把环拆开,环中每一个点连向环的根,然后搞LCA,答案就是套路的d[x]+d[y]-d[lca]*2

然后就可以发现,其实只有当fx和fy在同一个环里面,才有可能通过不同的路线导致答案更小,特判之即可。

#include<cstdio>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<algorithm>
#include<cmath>
#include<vector>
using namespace std; struct node
{
int x,y,d,next;
}a[],e[];int len,last[],elen,elast[];
void ins(int x,int y,int d)
{
len++;
a[len].x=x;a[len].y=y;a[len].d=d;
a[len].next=last[x];last[x]=len;
}
void eins(int x,int y,int d)
{
elen++;
e[elen].x=x;e[elen].y=y;e[elen].d=d;
e[elen].next=elast[x];elast[x]=elen;
} bool edg[];int cnt,bel[],sum[],ts[];
int fa[],dep[],dis[];
int tp,id[],sdis[];
void DP(int rt,int bac)
{
tp=dep[bac]-dep[rt]+;
for(int i=;i<=tp;i++) id[tp-i+]=bac, bac=fa[bac]; sdis[]=;
for(int i=;i<=tp;i++)
{
sdis[i]=sdis[i-]+dis[id[i]];
ts[id[i]]=sdis[i];
}
cnt++;sum[cnt]=sdis[tp]+dis[rt]; for(int i=;i<=tp;i++)
{
ins(rt,id[i],min(sdis[i],sum[cnt]-sdis[i]));
edg[id[i]]=true;
bel[id[i]]=cnt;
}
}
int z,dfn[],low[];
void cactus(int x)
{
dfn[x]=low[x]=++z;
for(int k=elast[x];k;k=e[k].next)
{
int y=e[k].y;
if(dfn[y]==)
{
fa[y]=x;
dep[y]=dep[x]+;
dis[y]=e[k].d;
cactus(y);
low[x]=min(low[x],low[y]);
}
else if(y!=fa[x])
low[x]=min(low[x],dfn[y]);
} for(int k=elast[x];k;k=e[k].next)
{
int y=e[k].y;
if(fa[y]!=x&&dfn[x]<dfn[y])
{
int t=dis[x];
dis[x]=e[k].d;
DP(x,y);
dis[x]=t;
}
}
} //----------------------------------------- int Bin[];
int f[][];
void dfs(int x)
{
for(int i=;dep[x]>=Bin[i];i++)f[i][x]=f[i-][f[i-][x]]; for(int k=last[x];k;k=a[k].next)
{
int y=a[k].y;
if(y!=f[][x])
{
f[][y]=x;
dep[y]=dep[x]+;
dis[y]=dis[x]+a[k].d;
dfs(y);
}
}
}
int LCA(int x,int y,int &fx,int &fy)
{
int w=-;
if(dep[x]<dep[y]){swap(x,y);w=;}
for(int i=;i>=;i--)
if(dep[x]-dep[y]>=Bin[i])x=f[i][x];
if(x==y){fx=-;return x;}
for(int i=;i>=;i--)
if(dep[x]>=Bin[i]&&f[i][x]!=f[i][y])x=f[i][x],y=f[i][y];
if(w==-)fx=x,fy=y;
else fx=y,fy=x;
return f[][x];
} //--------------get_LCA---------------------------- int main()
{
int n,m,Q,x,y,dd;
scanf("%d%d%d",&n,&m,&Q);
len=;memset(last,,sizeof(last));
elen=;memset(elast,,sizeof(elast));
for(int i=;i<=m;i++)
{
scanf("%d%d%d",&x,&y,&dd);
eins(x,y,dd);eins(y,x,dd);
}
z=cnt=;
memset(dfn,,sizeof(dfn));
memset(low,,sizeof(low));
memset(edg,false,sizeof(edg));
fa[]=,dep[]=,cactus();
for(int i=;i<=n;i++)
if(edg[i]==false)
ins(fa[i],i,dis[i]); Bin[]=;for(int i=;i<=;i++)Bin[i]=Bin[i-]*;
f[][]=;dep[]=;dis[]=;dfs(); while(Q--)
{
scanf("%d%d",&x,&y);
int fx,fy,lca=LCA(x,y,fx,fy);
if(fx!=-&&bel[fx]!=&&bel[fx]==bel[fy])
{
dd=abs(ts[fx]-ts[fy]);
printf("%d\n",dis[x]-dis[fx]+dis[y]-dis[fy]+min(dd,sum[bel[fx]]-dd));
}
else
printf("%d\n",dis[x]+dis[y]-*dis[lca]);
}
return ;
}

bzoj3047:Freda的传呼机&&bzoj2125: 最短路的更多相关文章

  1. bzoj3047: Freda的传呼机 && 2125: 最短路

    Description 为了随时与rainbow快速交流,Freda制造了两部传呼机.Freda和rainbow所在的地方有N座房屋.M条双向光缆.每条光缆连接两座房屋,传呼机发出的信号只能沿着光缆传 ...

  2. [BZOJ2125]最短路(圆方树DP)

    题意:仙人掌图最短路. 算法:圆方树DP,$O(n\log n+Q\log n)$ 首先建出仙人掌圆方树(与点双圆方树的区别在于直接连割边,也就是存在圆圆边),然后考虑点u-v的最短路径,显然就是:在 ...

  3. bzoj2125 最短路

    Description 给一个N个点M条边的连通无向图,满足每条边最多属于一个环,有Q组询问,每次询问两点之间的最短路径. Input 输入的第一行包含三个整数,分别表示N和M和Q 下接M行,每行三个 ...

  4. BZOJ2125 最短路 圆方树、倍增

    传送门 对仙人掌建立圆方树,然后对边定权 对于圆点和圆点之间的边,是原来仙人掌上的桥,边权保持不变 对于圆点和方点之间的边,将圆方树看做以一个圆点为根的有根树之后,一个方点的父亲一定是一个圆点.对于这 ...

  5. 2018.07.25 bzoj2125: 最短路(圆方树+倍增)

    传送门 人生的第一道仙人掌. 这道题求是仙人掌上的最短路. 先建出圆方树,然后用倍增跑最短路,当lca" role="presentation" style=" ...

  6. BZOJ2125 最短路 【仙人掌最短路】

    题目 给一个N个点M条边的连通无向图,满足每条边最多属于一个环,有Q组询问,每次询问两点之间的最短路径. 输入格式 输入的第一行包含三个整数,分别表示N和M和Q 下接M行,每行三个整数v,u,w表示一 ...

  7. bzoj2125 最短路——仙人掌两点间距离

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=2125 仙人掌!模仿 lyd 的代码写的,也算是努力理解了: 主要分成 lca 在环上和不在环 ...

  8. [BZOJ2125]最短路[圆方树]

    题意 给定仙人掌,多次询问两点之间的最短路径. \(n\le 10000, Q\le 10000​\) 分析 建出圆方树,分路径 lca 是圆点还是方点讨论. 预处理出根圆点到每个圆点的最短距离 \( ...

  9. 【题解】Bzoj2125最短路

    处理仙人掌 ---> 首先建立出圆方树.则如果询问的两点 \(lca\) 为圆点,直接计算即可, 若 \(lca\) 为方点,则需要额外判断是走环的哪一侧(此时与两个点在环上的相对位置有关.) ...

随机推荐

  1. Java—将文件夹压缩为zip文件

    import java.io.BufferedInputStream; import java.io.File; import java.io.FileInputStream; import java ...

  2. 挂载硬盘,提示 mount: unknown filesystem type 'LVM2_member'的解决方案

    问题现象:由于重装linux,并且加了固态硬盘,直接将系统装在固态硬盘中.启动服务器的时候, 便看不到原来机械硬盘的挂载目录了,不知如何访问机械硬盘了.直接用命令 mount /dev/sda3 /s ...

  3. jQuery实现页面锚点滚动效果

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/ ...

  4. 移动web——bootstrap如何修改原组件

    基本介绍 1.bootstrap提供了丰富的组件,但是有时候我们不仅要删除不必要的标签,还需要修改里面的样式 2.我们建议若是修改样式那么最好将源样式从css中拷贝出来,名字换掉,然后修改具体样式,这 ...

  5. Windows2008 Server 常规设置及基本安全策略

    一.系统及程序 1.屏幕保护与电源 桌面右键--〉个性化--〉屏幕保护程序屏幕保护程序 选择无更改电源设置 选择高性能选择关闭显示器的时间 关闭显示器 选 从不 保存修改 2.安装IIS 管理工具-- ...

  6. TensorFlow:Windows下使用TensorFlow-Python版本

    原文链接:Win10X64下安装使用TensorFlow 安装TensorFlow 由于Google那帮人已经把 TensorFlow 打成了一个 pip 安装包,所以现在可以用正常安装包的方式安装 ...

  7. codeforces_731D_(前缀和)(树状数组)

    D. 80-th Level Archeology time limit per test 2 seconds memory limit per test 256 megabytes input st ...

  8. Objective-C在ARC下结合GCD的单例模式和宏模版

    单例模式在iOS开发过程中经常用到,苹果提供过objective c单例的比较官方的写法: static MyGizmoClass *sharedGizmoManager = nil; + (MyGi ...

  9. eclipse常用设置之项目分组查看

    1.打开‘NaviNavigator’ 视图,windows-->show views->NaviNavigator; 2.在NaviNavigator视图下选择select workin ...

  10. kvm virt-install 使用小结

    简介: virt-install 能够为KVM.Xen或其它支持libvrit API的hypervisor创建虚拟机并完成GuestOS安装. 此外,它能够基于串行控制台.VNC或SDL支持文本或图 ...