zoukankan      html  css  js  c++  java
  • 【BZOJ1211】树的计数(Prufer编码)

    题意:一个有n个结点的树,设它的结点分别为v1, v2, …, vn,

    已知第i个结点vi的度数为di,问满足这样的条件的不同的树有多少棵。

    其中1<=n<=150,输入数据保证满足条件的树不超过10^17个。

    思路:

    Martix67:

    一个有趣的推广是,n个节点的度依次为D1, D2, …, Dn的无根树共有(n-2)! / [ (D1-1)!(D2-1)!..(Dn-1)! ]个,因为此时Prüfer编码中的数字i恰好出现Di-1次。

    POPOQQQ:

    注意此题无解需要输出0

    当n!=1&&d[i]==0时 输出0

    当Σ(d[i]-1)!=n-2时输出0

     1 var a,b,prime,cnt:array[0..1000]of longint;
     2     n,m,s,i:longint;
     3     ans:int64;
     4     flag:boolean;
     5 
     6 function mult(x,y:longint):int64;
     7 var tmp:int64;
     8 begin
     9  mult:=1; tmp:=x;
    10  while y>0 do
    11  begin
    12   if y and 1=1 then mult:=mult*tmp;
    13   tmp:=tmp*tmp;
    14   y:=y>>1;
    15  end;
    16 end;
    17 
    18 function ins(x,y:longint):longint;
    19 var i,k:longint;
    20 begin
    21  for i:=1 to m do
    22  begin
    23   k:=x;
    24   while k>0 do
    25   begin
    26    cnt[i]:=cnt[i]+k div prime[i]*y;
    27    k:=k div prime[i];
    28   end;
    29  end;
    30 end;
    31 
    32 function su(x:longint):boolean;
    33 var i:longint;
    34 begin
    35  if x=2 then exit(true);
    36  for i:=2 to trunc(sqrt(x)) do
    37   if x mod i=0 then exit(false);
    38  exit(true);
    39 end;
    40 
    41 begin
    42  assign(input,'bzoj1211.in'); reset(input);
    43 // assign(output,'bzoj1211.out'); rewrite(output);
    44  readln(n);
    45  for i:=2 to 150 do
    46   if su(i) then begin inc(m); prime[m]:=i; end;
    47  for i:=1 to n do
    48  begin
    49   read(a[i]);
    50   inc(b[a[i]]);
    51   s:=s+a[i]-1;
    52  end;
    53  if n-2<>s then
    54  begin
    55   writeln(0);
    56   exit;
    57  end;
    58  flag:=true;
    59  for i:=1 to n do
    60   if a[i]=0 then begin flag:=false; break; end;
    61  if (n>1)and( not flag) then
    62  begin
    63   writeln(0);
    64   exit;
    65  end;
    66 
    67  ins(n-2,1);
    68  for i:=1 to n do
    69   if b[i]-1>0 then ins(b[i]-1,-1);
    70  ans:=1;
    71  for i:=1 to m do ans:=ans*mult(prime[i],cnt[i]);
    72  writeln(ans);
    73 
    74  close(input);
    75  //close(output);
    76 end.
  • 相关阅读:
    表格标签
    图片标签
    超链接标签
    媒体标签
    实体标签
    html常用的标签
    头信息的作用
    【bzoj5017】[Snoi2017]炸弹 线段树优化建图+Tarjan+拓扑排序
    【bzoj3309】DZY Loves Math 莫比乌斯反演+线性筛
    【bzoj4010】[HNOI2015]菜肴制作 拓扑排序+堆
  • 原文地址:https://www.cnblogs.com/myx12345/p/6490745.html
Copyright © 2011-2022 走看看