UOJ第558位。ドラゴンボール

トピックの背景

コーチの強制の下では、他のこんにゃくは、実際に私の話題です!論外!(私はあまりにも多くの水データqwqを見つけることができません)

良い、JLは良いタイトルが100速いをもたらしたと述べました

タイトル説明

スーパーサイヤ人Kakaluote非常に好戦的なので、全体のアラブはA2、宇宙a1に行く...そして最終的に宇宙に行くために、つまり(彼に一定の順序を与えたので、彼は、強い探して他の宇宙から学びますユニバースAN)は、パスを介してn個の宇宙の合計行く、ワイス彼は双AIユニバースことがユニバースから、当然のことながら、AI、BI宇宙に到達する宇宙から、すなわち、N-1チャンネル宇宙のために確立しました。宇宙通じKakaluoteそれぞれは、いくつかの強力な宇宙に挑戦しようとしている各、(もちろん、これは強力な挑戦を前に持っていたではないです)強い挑戦します。Kakaluoteがプレーしていないので、Kakaluote毎日とベジータは、演奏のKakaluoteので、すでに疲れて、地球を襲ったので、宇宙の最後には、地球です。

入力形式

最初の整数n行が2行目は、N個の整数のユニバースの数を表し、順次説明A1-AN

次に、二つの整数xのN-1株は、yは、二つの基準空間のxとyとの間に接続された通路を発現しました。

出力フォーマット

n行の合計は、宇宙のI番号i行目の出力が強い課題の少なくとも数であろう。

サンプル入力と出力

入力#1

5
1 4 5 3 2
1 2
2 4
2 3
4 5

出力#1

1
2
1
2
1

説明/ヒント

30%2 <= N <= 300

100%2 <= N <= 300000

アイデア(コードを参照してください):

#include <cstdioを> 
する#include <アルゴリズム> 
の#include <CStringの> 
する#include <cstdlib> 
使用して名前空間std。
構造体パス{ 
    INT次、終了します。
    魏int型; 
} pH値[600020]。
int型のPTA [300010]、FA [40] [300010]、D [300010]、S [300010]、E。
int型CNT [300010]。
BOOL VIS [300010]。
ボイドDFS(INT P、INT DPT){//倍增LCA的初始化
    VIS [P]が真=。
    D [P] = DPT。
    以下のために(; I; int型I = PTA [P] IでpH = [I] .next){ 
        IF(VIS [pHは[I] .ENDS])続けます。
        FA [0] [pHは[i]は.ENDS] = P。
        DFS(PH [I] .ENDS、DPT + 1)。
    } 
} 
ボイドmakep(INT U、V INT){//建边 
    のpH【++ E] .ENDS = V。
    pHは[E] .next = PTA [U]。
    PTA [U] = E。
    pH値[++ E] .ENDS = U。
    pHは[E] .next = PTA [V]。
    PTA [V] = E。
} 
int型LCA(int型のx、int型のY){//求LCA 
    場合(D [X] <D [Y])スワップ(X、Y)
    INT DIF = D [X] - D [Y]。
    以下のために(私は30 = int型; I> = 0; --I)
        IF(1 << I <= DIF)
        DIF - = 1 << I、
        X = FA [i]が[X]。
    もし(x == y)は戻りX。
    以下のために(30 = I int型; I> = 0; - I)
        IF(!FA [I] [X] = FA [i]を[Y])
        X = FA [I] [X]、Y = FA [I ] [Y]。
    もし(x == y)は戻りX。
    他のFAを返す[0] [X]; 
} 
INT dfs_ans(INT P){//还原答案
    INT ANS = CNT [P]。//加上自身权值
    VIS [P] = trueの。 
    ため(INT I = PTA [P]; I; I = pHを[I] .next){ 
        IF(VIS [pHは[I] .ENDS])続けます。
        ANS +でpH = [I] .wei =のdfs_ans(PH [i]は.ENDS); // 右サブツリーが右辺の値であり、I 
    } 
    のための(INT I = PTA [P]; I; I = pHが[ I] .next){ 
        IF(pH値[I] == .ENDS FA [0] [P])pHは[I] = .wei ANS、I = 0; 
        //父の側は無向エッジとして(有向検索2有向辺)として格納されている
    } 
    ;戻りANS 
} 
int型のmain(){ 
    int型N-; 
    scanfの( "%のD"、およびN-)を、
    ため(INT I = 1; I <= N; ++ I)
        scanfの( "%のD"、S + I)
    のために(INT I = 1; I <N-; ++ I){ 
        int型A、B、
        scanfの( "%のDの%のD"、&A、&B); 
        MAKEP(A、B ); 
    } 
    FA [0] [S [1]] =のS [1]; DFS(Sの,. 1)[1];  
    のための(INT I = 1; I << 1 <= N;++ I)//乗算前処理ステップ
    のための(INT 1 = J; J <= N; J ++)
        FA [I] [ J] = FA [I-1 ] [FA [I-1]〜[J]。 
    のための(INT I = 1; I <N - 、I ++)は、各処理ステップのための// 
        のCNT [S [I] ++ 、CNTの[S [ 1 + I] ++、
        CNTは[LCA(S [I]、S [I + 1]。)] - = 2; 
    のmemset(VIS、0、はsizeof(VIS)); 
    dfs_ans;(Sの[1]。)
    のために(INT 1 = I; I <= N - 、Iは++){ 
        int型ANS = 0; 
        のため(PTA J = INT [I]; J; J = pHは[J] .next)
            ANSでpH = + [J]。魏; 
        IF(I == S [N-])ANS - ;重量際終わりが//増加する必要はありません
        のprintf( "%d個の\ n"は 、(ANS + 1)>> 1); //は切り上げ
    } 
    の戻り0; 
} //コードSRJ兄

 

#include <cmath> 
の#include <cstdioを> 
する#include <CStringの> 
する#include <iostreamの> 
する#include <アルゴリズム> 
名前空間STDを使用して、

const int型N = 300010; 

VIS [N] BOOL。
int型、E、N、A、B、CNT [N]。
int型[40] Fヘッド[N]、[N]、D [N]、S [N]。

構造体なし{ 
	int型NXT編、W。
}マップ[N * 2]。

ボイドDFS(INT P、INT DPT){ 
	VIS [P]が真=。
	D [P] = DPT。
	(; I; I =マップ[i]は.nxt int型I =ヘッド[P]){ための
		IF(VIS [マップ[i]は.ED])
			続けます。
		F [0] = P [i]は.ED [MAP]。
		DFS(マップ[i]は.ED、DPT + 1)。
	} 
} 

ボイドmakep(INT U、V INT){ 
	マップ[++ E] .ED = V。
	地図[E] .nxt =頭部[U]。
	ヘッド[U] = E。
	地図【++ E] .ED = U。
	地図[E] .nxt =頭部[V]。
	ヘッド[V] = E。
} 

int型LCA(int型のx、int型のY){ 
	IF(D [X] <D [Y])
		スワップ(X、Y)
	INT DIF = D [X] -d [Y]。
	以下のために(私は30 = int型; I> = 0; i--)
		IF(1 << I <= DIF)
			dif- = 1 << I、
			     X = F [i]が[X]。
	(x == y)の場合は
		リターンX。
	以下のために(私は30 = int型; I> = 0; --I)
		IF(!F [i]が[X] = F [i]を[Y])
			X = F [i]が[X]は、YはF [Iを= ] [Y]。
	(x == y)の場合は
		リターンX。
		; F [0] [x]はリターン 
} 

int型(int型P){解決
	INT ANS = CNT [P]を。
	VIS [P] = trueの。
	用(INT I =ヘッド[P]; I; I =マップ[i]が.nxt){ 
		IF(VIS [マップ[i]は.ED]) 
			続けます。
		ANS + =マップ[i]は.W =([I]マッピング解決します。編); 
	}
	用(; I; int型I =ヘッド[P] I =マップ[i]が.nxt){ 
		IF(マップ[i]が.ED == F [0] [P]){ 
			マップ[i]は.W = ANS。
			I = 0; 
		} 
	} 
	戻りANS。
} 

int型のmain(){ 
	scanf関数( "%のD"、&N); 
	(; iが<= N I ++は、I = 1 INT)のため
		のscanf( "%dの"、&S [I])。
	{ため(; iがn <I ++はI = 1 INT)
		のscanf( "%d個の%のD"、&、&B)。
		makep(B)
	} 
	F [0] [S [1] = sの[1]。
	DFS(S [1]、1)。
	以下のために(; 1 << iがn = <I ++ i = 1 INT)
		のために(INT J = 1; J <= N; J ++)
			F [i]は[J] = F [I-1]を[1- [F 1]〜[J]。
	以下のために(; iがn <; I = int型1 ++ I){ 
		CNT [S [I]] ++; 
		CNT [S [I + 1] ++; 
		CNT [LCA(S [i]は、S [I + 1)] - = 2。
	memsetの(VIS、0、はsizeof(VIS))。
	ための式(I = 1 int型、iが<= N; iは++){ 
		int型ANS = 0。
		(; J J =マップ[J] .nxt INT J =頭部[i])とするための
			ANS + =マップ[J] .W。
		IF(I == S [N])
			ans--。
		printf( "%d個の\ n"、(ANS + 1)>> 1)。
	} 
	0を返します。
} //本蒟蒻的代码

 

おすすめ

転載: www.cnblogs.com/mysh/p/11355456.html