生活随笔
收集整理的這篇文章主要介紹了
Codeforces Round #617 (Div. 3) F. Berland Beauty 思维
小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
傳送門
文章目錄
題意:
給定一棵樹,再給定若干兩點(diǎn)最短路之間邊權(quán)的最小值,讓你給樹的邊權(quán)賦值,使得滿足給定的條件,如果不存在輸出?1-1?1。
思路:
觀察一個(gè)性質(zhì),加入經(jīng)過這條邊的路徑的最小邊權(quán)為w1,w2,..,wxw_1,w_2,..,w_xw1?,w2?,..,wx?,那么當(dāng)前這個(gè)邊的邊權(quán)wnow≥max(w1,w2,...,wx)w_{now}\ge max(w_1,w_2,...,w_x)wnow?≥max(w1?,w2?,...,wx?)。所以我們先按照邊權(quán)從小到大排序,讓后每次都直接將(a,b)(a,b)(a,b)之間的邊都賦值為wiw_iwi?,最后判斷一下是否合法即可。
nnn很小,暴力可過,這里用的lcalcalca來暴力的,個(gè)人感覺比較方便。
#include<cstdio>
#include<iostream>
#include<string>
#include<cstring>
#include<map>
#include<cmath>
#include<cctype>
#include<vector>
#include<set>
#include<queue>
#include<algorithm>
#include<sstream>
#include<ctime>
#include<cstdlib>
#define X first
#define Y second
#define L (u<<1)
#define R (u<<1|1)
#define pb push_back
#define mk make_pair
#define Mid (tr[u].l+tr[u].r>>1)
#define Len(u) (tr[u].r-tr[u].l+1)
#define random(a,b) ((a)+rand()%((b)-(a)+1))
#define db puts("---")
using namespace std
;
typedef long long LL
;
typedef unsigned long long ULL
;
typedef pair
<int,int> PII
;const int N
=5010,M
=N
*2,mod
=1e9+7,INF
=0x3f3f3f3f;
const double eps
=1e-6;int n
,m
;
PII p
[N
];
int e
[M
],ne
[M
],w
[M
],h
[N
],idx
;
int depth
[N
],fa
[N
][20];
int g
[N
][N
],flag
;
struct Node
{int a
,b
,w
;bool operator < (const Node
&W
) const {return w
<W
.w
;}
}q
[N
];void add(int a
,int b
)
{e
[idx
]=b
,ne
[idx
]=h
[a
],h
[a
]=idx
++;
}void dfs_dep(int u
,int f
)
{depth
[u
]=depth
[f
]+1;fa
[u
][0]=f
;for(int i
=1;i
<=16;i
++) fa
[u
][i
]=fa
[fa
[u
][i
-1]][i
-1];for(int i
=h
[u
];~i
;i
=ne
[i
]){int j
=e
[i
];if(j
==f
) continue;dfs_dep(j
,u
);}
}int lca(int a
,int b
)
{if(depth
[a
]<depth
[b
]) swap(a
,b
);for(int i
=16;i
>=0;i
--)if(depth
[fa
[a
][i
]]>=depth
[b
])a
=fa
[a
][i
];if(a
==b
) return a
;for(int i
=16;i
>=0;i
--)if(fa
[a
][i
]!=fa
[b
][i
])a
=fa
[a
][i
],b
=fa
[b
][i
];return fa
[a
][0];
}bool check()
{for(int i
=1;i
<=m
;i
++){int a
=q
[i
].a
,b
=q
[i
].b
,c
=q
[i
].w
;int f
=lca(a
,b
);int mi
=INF
;while(a
!=f
){if(g
[a
][fa
[a
][0]]) mi
=min(mi
,g
[a
][fa
[a
][0]]);a
=fa
[a
][0];}while(b
!=f
){if(g
[b
][fa
[b
][0]]) mi
=min(mi
,g
[b
][fa
[b
][0]]);b
=fa
[b
][0];}if(mi
!=c
) return false;}return true;
}int main()
{
memset(h
,-1,sizeof(h
));scanf("%d",&n
);for(int i
=1;i
<=n
-1;i
++) {int a
,b
; scanf("%d%d",&a
,&b
);add(a
,b
); add(b
,a
);p
[i
]={a
,b
};}dfs_dep(1,0);scanf("%d",&m
);for(int i
=1;i
<=m
;i
++){int a
,b
,c
; scanf("%d%d%d",&a
,&b
,&c
);q
[i
]={a
,b
,c
};}sort(q
+1,q
+1+m
);for(int i
=1;i
<=m
;i
++){int a
=q
[i
].a
,b
=q
[i
].b
,c
=q
[i
].w
;int f
=lca(a
,b
);while(a
!=f
){g
[a
][fa
[a
][0]]=c
;g
[fa
[a
][0]][a
]=c
;a
=fa
[a
][0];}while(b
!=f
){g
[b
][fa
[b
][0]]=c
;g
[fa
[b
][0]][b
]=c
;b
=fa
[b
][0];}}if(check()) for(int i
=1;i
<=n
-1;i
++) printf("%d ",g
[p
[i
].X
][p
[i
].Y
]==0? 1:g
[p
[i
].X
][p
[i
].Y
]);else puts("-1");return 0;
}
總結(jié)
以上是生活随笔為你收集整理的Codeforces Round #617 (Div. 3) F. Berland Beauty 思维的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。