[bzoj1005]明明的烦恼
根据purfer序列的原理,每一个purfer序列都一一对应了一棵树,每一个点在purfer序列中出现的次数就是它的度数,那么直接用组合数去计算即可,注意要加高精度
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
1 #include<cstdio> 2 #include<cstring> 3 using namespace std; 4 struct ji{ 5 int len,a[10001]; 6 }a; 7 int n,m,k,d[1001],vis[1001]; 8 void cheng(int b){ 9 a.a[1]*=b; 10 for(int i=2;i<=a.len;i++){ 11 a.a[i]=a.a[i]*b+a.a[i-1]/10; 12 a.a[i-1]%=10; 13 } 14 while (a.a[a.len]>9){ 15 a.a[a.len+1]=a.a[a.len]/10; 16 a.a[a.len++]%=10; 17 } 18 } 19 void calc(int k,int p){ 20 for(int i=2;i*i<=k;i++) 21 while (k%i==0){ 22 vis[i]+=p; 23 k/=i; 24 } 25 if (k>1)vis[k]+=p; 26 } 27 void c(int a,int b){ 28 for(int i=b+1;i<=a;i++)calc(i,1); 29 for(int i=1;i<=a-b;i++)calc(i,-1); 30 } 31 int main(){ 32 scanf("%d",&n); 33 m=n-2; 34 k=n; 35 for(int i=1;i<=n;i++)scanf("%d",&d[i]); 36 a.len=a.a[1]=1; 37 for(int i=1;i<=n;i++) 38 if (d[i]!=-1){ 39 c(m,d[i]-1); 40 m-=d[i]-1; 41 k--; 42 } 43 for(int i=1;i<=m;i++)calc(k,1); 44 for(int i=1;i<=1000;i++) 45 for(int j=1;j<=vis[i];j++)cheng(i); 46 for(int i=a.len;i;i--)printf("%d",a.a[i]); 47 }