題目概述:
給出乙個公司所有員工的上下級關係(資料保證是一棵樹),現在想解雇一些員工,而他們的位置由他們的手下裡能力值比他大而且忠誠度最高的人來替代,給出m個詢問,求輸出替代他們的人的編號。
大致思路:
學習了一下dfs序的用法,附學習的部落格:
簡單的說dfs序就是將一棵樹變成線性結構的演算法,並且保證點i的子樹都在i的後面。
根據dfs序首先將員工之間的關係轉化成陣列,然後對於員工的資料a按照能力值降序排列,並且將所有的詢問q也按對應的能力值降序排列。
排完序之後依次插入a中的元素進入線段樹中,比較當前插入的ai與未處理的q中能力值最高的比較,如果ai的能力值比較小,則處理這個詢問,否則繼續插入。
**:
1 #include 2 #include 3 #include 4 #include 5 #include 6 #include 7 #include 8 #include 9 #include 10 #include 11 #include 12using
namespace
std;
1314
#define sacnf scanf
15#define scnaf scanf
16#define maxn 50010
17#define maxm 26
18#define inf 1061109567
19#define eps 0.00001
20const
double pi=acos(-1.0
);21
#define mod 7
22#define maxnum 10000
23void swap(int &a,int &b)
24int abs(int x)
25 typedef long
long
ll;26 typedef unsigned int
uint;27
28struct
node
2936
} a[maxn];
3738
struct
node1
39 q[maxn];
4243 vectorg[maxn];
44int
tme;
45int
st[maxn],ed[maxn];
46int
tabi[maxn],tloy[maxn];
47int
ans[maxn];
48int tree[maxn*4]; ///
loy最大的點的編號
4950
bool
cmp(node1 a,node1 b)
5154
55void dfs(int u,int
fa)56
64 ed[u]=tme;65}
6667
void build_tree(int l,int r,int
dir)
6874
int m=(l+r)>>1
;75 build_tree(l,m,dir<<1
);76 build_tree(m+1,r,dir<<1|1
);77 tree[dir]=1;78
}7980void add(int l,int r,int dir,int pos,int
val)
8187
int m=(l+r)>>1;88
if(pos<=m) add(l,m,dir*2
,pos,val);
89else add(m+1,r,dir*2+1
,pos,val);
90 tree[dir]=(tloy[tree[dir*2]]2+1]])?tree[dir*2+1]:tree[dir*2
];91}92
93int query(int l,int r,int dir,int ql,int
qr)94
103104
intmain()
105125
126 tme=0
;127 dfs(1,-1
);128 build_tree(1,n,1
);129
130 sort(a+1,a+1+n); ///
按ability降序排列 a-->第i個人的資料
131132
for(int i=1;i<=m;i++) ///
q-->第i個詢問的序號及詢問編號
133137 sort(q+1,q+1+m,cmp); ///
按ability降序排列
138139
int i=1,j=1
;140
while(i<=m)
141149
else
if(j150153
}154
for(i=1;i<=m;i++) printf("
%d\n
",(ans[i]==0)?-1
:ans[i]);
155}
156//
clock_t ed=clock();
157//
printf("\n\ntime used : %.5lf ms.\n",(double)(ed-st)/clocks_per_sec);
158return0;
159 }
HDOJ3639解題報告 縮點 dfs
題目概述 題面有點翻譯不來 可以用chrome自帶的那個翻譯。大致思路 如果跑bfs或者dfs遇到環的話就會出問題,所以先跑一遍tarjan求強連通分量,把環的情況去掉,在剩下的圖上做。這個時候發現樣例1裡2這個節點指向的兩個節點都是答案,所以反向建圖,用dfs求出所有入度為0的點的子樹大小,最大數...
hdoj1181解題報告,DFS,標記用過的的方法
給一堆字串,判斷能否從某個字母做開頭,首尾相連,到某個字母的結尾 要注意,每一種變換只能使用一次,例如b t,只能用一次。否則無限迴圈。include include includeusing namespace std char s 2000 int m 30 30 vis 30 30 int x...
HDOJ5692解題報告 dfs序 線段樹
題目概述 中文題面就不贅述了。大致思路 這個題給出的是一棵樹,我們可以使用dfs序將這棵樹處理成一條鏈,然後對這條鏈來進行資訊維護和查詢。有兩種操作,0 x是詢問從0出發 題目保證0為樹根 經過x的路徑中的最大權值,1 x y是將點x的權值修改成y,這時我們用線段樹來維護乙個d i 表示點i到0點的...