無題,需要多次複習的

(一)求一顆樹所有直徑上的所有點。

設f[i][0] 表示子樹第一長,f[i][1]表示子樹第二長,f[i][2]表示父節點到他的最長路徑,son[x]表示子樹最長路徑的兒子。

核心代碼:

void dp(int x,int fa)
{
	p[x]=fa;
	for(int i=first[x];i;i=e[i].next)
	{
		int w=e[i].to;
		if(w==fa) continue;
		dp(w,x);
		if(f[w][0]+1>f[x][0])
		{
			f[x][1]=f[x][0];
			f[x][0]=f[w][0]+1;
			son[x]=w;
		}
		else f[x][1]=max(f[x][1],f[w][0]+1);
	}
}

void dfs(int x,int fa)
{
	if(x!=0)
	{
		f[x][2]=f[p[x]][2];
		if(son[p[x]]==x) f[x][2]=max(f[x][2],f[p[x]][1]);
		else f[x][2]=max(f[x][2],f[p[x]][0]);
		f[x][2]++;
	}
	for(int i=first[x];i;i=e[i].next)
	{
		int w=e[i].to;
		if(w==fa) continue;
		dfs(w,x);
	}
}
(二)錯排公式

f[i]=(n-1)*(f[n-2]+f[n-1]);

f[1]=0,f[2]=1;

證明:

設f[i]表示i個元素滿足錯排的方案數,

對於一個新元素 n,他一定不能放在n位置。

1.我們可以將n放在前面的任意一個位置k,即有(n-1)種方案。

2.既然n放在了一個位置k,那麼該位置原來的元素就要換一個位置。

如果他在n位置,那麼就是n個元素,除了k位置的n&n位置的k,還有n-2個元素要求滿足錯排,即f[n-2]

如果不在n位置,那麼就是n個元素,除了k位置的n,還有n-1個元素要求滿足錯排,即f[n-1]

整理的出公式:f[i]=(i-1)*(f[i-1]+f[i-2])

然後邊界條件手算一下就好了(1和2)。
(三)  編號小的元素在答案排列中儘量靠前==倒過來字典序最大

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章