首先明确purfer序列可以与一棵树一一对应,purfer序列构造方法为,先选取一个编号最小的度数为1的点,然后删去该点,并将改点所连出的边指向的点加入purfer序列,直到最后该图中剩下最后两个点,那么n个结点的树对应的purfer序列的长度为n-2。那么数有多少种就可以转换成这个序列有多少种。该序列的性质:原图中每个节点的度数为在该序列中出现的次数+1……
该题即转换成求purfer序列的个数。序列中非-1的节点位置的序列的个数可以由组合数算得,最后剩下的k个位置填num个-1的方案数即为k^num。
代码转载
import java.io.*;
import java.math.*;
import java.util.*;
public class Main
{
public static void main(String[] args){
Scanner cin = new Scanner(new BufferedInputStream(System.in));
int a[] = new int[1005];
int n = cin.nextInt(),s = 0;
for(int i = 1;i<=n;++i)a[i] = cin.nextInt();
if(n==1){
if(a[1]==0||a[1]==-1)System.out.println(1);
else System.out.println(0);
return;
}
int m = 0;
for(int i = 1;i<=n;++i)if(a[i]!=-1){
if(a[i]<1){System.out.println(0);return;}
a[i]--;s+=a[i];m++;
}
if(s>n-2){System.out.println(0);return;}
BigInteger f[] = new BigInteger[1005];
f[1] = BigInteger.ONE;f[0] = f[1];
for(int i = 2;i<=n;++i)
f[i] = f[i-1].multiply(BigInteger.valueOf(i));
BigInteger ans = f[n-2].divide(f[n-2-s]);
BigInteger x = BigInteger.valueOf(n-m);
for(int i = 1;i<=n;++i)if(a[i]!=-1)
ans = ans.divide(f[a[i]]);
for(int i = 1;i<=n-s-2;++i)ans = ans.multiply(x);
System.out.println(ans);
}
}