51nod1766 樹上的最遠點對

2021-08-16 10:51:57 字數 2272 閱讀 2122

n個點被n-1條邊連線成了一顆樹,給出a~b和c~d兩個區間,表示點的標號請你求出兩個區間內各選一點之間的最大距離,即你需要求出max{dis(i,j) |a<=i<=b,c<=j<=d}

(ps 建議使用讀入優化)

第一行乙個數字 n n<=100000。

第二行到第n行每行三個數字描述路的情況, x,y,z (1<=x,y<=n,1<=z<=10000)表示x和y之間有一條長度為z的路。

第n+1行乙個數字m,表示詢問次數 m<=100000。

接下來m行,每行四個數a,b,c,d。

共m行,表示每次詢問的最遠距離

5 1 2 1

2 3 2

1 4 3

4 5 4

1 2 3 4 5

首先要有一些預備的姿勢

rmq求lca

做出每乙個點的尤拉序,用乙個陣列儲存乙個點第一次被訪問到的情況,記錄的fi陣列

對於兩個點x,y的lca

其實就是fi[x]—fi[y]這個區間內深度最小的點

樹的直徑的相關性質

到乙個點最遠的點一定在樹的直徑上

樹的直徑的兩端一定是葉子節點

兩棵樹合併,新的直徑的端點一定是原來兩條直徑中四個端點的兩個

(目前還不會證明)

因此我們按照第三條來做,用線段樹來維護某個區間內的樹的直徑

然後合併一下即可

code

#include 

#include

#include

#include

#define l rt<<1

#define r rt<<1|1

#define fo(i,a,b) for(i=a;iusing namespace std;

const int n=100005;

struct edge tr[n<<2];

intx,y,z,n,top,q,w,e,r,ans,t,i,m;

int nx[n<<1],he[n],b[n<<1],c[n<<1],dfn[n<<1];

int h[n],f[n<<1][19],fi[n],d[n],tot,j;

edge ans1,ans2;

intread()

while (c>='0'&&c<='9')

return sum*p;

}inline void add(int

x,int

y,int z)

inline void dfs(int

x,int fa)

}inline int lca(int

x,int

y)inline int dis(int

x,int

y)inline void merge(edge a,edge b,edge &c)

if (b.x==0)

int i,j,x,y,k,t=0;

int e[5];

e[1]=a.x,e[2]=a.y,e[3]=b.x,e[4]=b.y;

fo(i,1,3)

fo(j,i+1,4)

}c.x=x; c.y=y;

}inline void build(int rt,int l,int r)

int mid=(l+r)>>1;

build(l,l,mid);

build(r,mid+1,r);

merge(tr[l],tr[r],tr[rt]);

}inline void query(int rt,int l,int r,int

x,int

y) int mid=(l+r)>>1;

if (x

<=mid) query(l,l,mid,x,y);

if (y>mid) query(r,mid+1,r,x,y);

}int main()

dfs(1,0);

fo(i,1,top) f[i][0]=i;

fo(j,1,log(top)/log(2))

fo(i,1,top-(1

<1)

if (h[dfn[f[i][j-1]]]1

<<(j-1))][j-1]]])

f[i][j]=f[i][j-1]; else f[i][j]=f[i+(1

<<(j-1))][j-1];

build(1,1,n);

m=read();

while (m)

}

51NOD 1766 樹上的最遠點對

n 個點被n 1條邊連線成了一顆樹,邊有權值wi 有q 個詢問,給出 a b 和 c,d 兩個區間,表示點的標號請你求出兩個區間內各選一點之間的最大距離,即你需要求出 ma x 1 n,q 105,1 wi 104 可以發現最長路徑具有直徑的合併性質,即兩個區間選點的最長路徑端點一定是原本兩個區間最...

C 樹上的最遠點對

51nod 1766 vjudge n個點被n 1條邊連線成了一顆樹,給出 a b 和 c d 兩個區間,表示點的標號請你求出兩個區間內各選一點之間的最大距離,即你需要求出max dis i,j a i b,c j d ps 建議使用讀入優化 第一行乙個數字 n n 100000。第二行到第n行每行...

51nod 2602 樹的直徑 最遠點對

給出一顆 n 個節點的樹,求樹上最遠點對。用 d p i dp i dp i 維護以 i 為根的子樹的深度,dp i m ax d p i dp j 1 dp i max dp i dp j 1 dp i max dp i dp j 1 j 為 i 的兒子 求出任意節點 i 子樹深度之後,經過 i ...