一开始用sb方法,时间没超然而内存爆了,之后又换了操作,启发式合并可证明最坏情况是合并的复杂度一共是nlognlogn的复杂度。map还是好容易在dfs里面炸内存啊。然而他swap两个map和swap两个map的下标最后的时间差别只有一点点。据说swap(map[1],map[2])是只交换指针的,不用遍历整个map[1],map[2]种的元素,神奇。
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<set>
#include<map>
#define maxl 100010
using namespace std;
int n,cnt;
int col[maxl],ehead[maxl];
int dy[maxl];
long long ans[maxl];
struct ed{int to,nxt;} e[maxl<<1];
map <int,int> mp[maxl];
map <int,long long> sum[maxl];
map <int,int> :: iterator it1,it2;
inline int read()
{
int x=0;char ch=getchar();
while(ch<'0' || ch>'9') ch=getchar();
while(ch>='0' && ch<='9') x=x*10+ch-'0',ch=getchar();
return x;
}
void prework()
{
/* memset(ehead,0,sizeof(ehead));
for(int i=1;i<=n;i++)
mp[i].clear();*/
for(int i=1;i<=n;i++)
col[i]=read(),dy[i]=i,mp[i][col[i]]=1,sum[i][1]=col[i];
int u,v;cnt=0;
for(int i=1;i<=n-1;i++)
{
u=read();v=read();
e[++cnt].to=v;e[cnt].nxt=ehead[u];ehead[u]=cnt;
e[++cnt].to=u;e[cnt].nxt=ehead[v];ehead[v]=cnt;
}
}
void dfs(int u,int fa)
{
int v;
for(int i=ehead[u];i;i=e[i].nxt)
{
v=e[i].to;
if(v!=fa)
{
dfs(v,u);
if(mp[dy[u]].size()<mp[dy[v]].size())
swap(dy[u],dy[v]);
for(it1=mp[dy[v]].begin();it1!=mp[dy[v]].end();++it1)
{
sum[dy[u]][mp[dy[u]][(*it1).first]]-=(*it1).first;
mp[dy[u]][(*it1).first]+=(*it1).second;
sum[dy[u]][mp[dy[u]][(*it1).first]]+=(*it1).first;
}
}
}
ans[u]=(*sum[dy[u]].rbegin()).second;
}
void mainwork()
{
dfs(1,0);
}
void print()
{
for(int i=1;i<=n;i++)
printf("%I64d ",ans[i]);
printf("\n");
}
int main()
{
while(~scanf("%d",&n))
{
prework();
mainwork();
print();
}
return 0;
}