• bzoj1089 [SCOI2003]严格n元树


    1089: [SCOI2003]严格n元树

    Time Limit: 1 Sec  Memory Limit: 162 MB
    Submit: 803  Solved: 411
    [Submit][Status]

    Description

    如果一棵树的所有非叶节点都恰好有n个儿子,那么我们称它为严格n元树。如果该树中最底层的节点深度为d(根的深度为0),那么我们称它为一棵深度为d的严格n元树。例如,深度为2的严格2元树有三个,如下图:

    给出n, d,编程数出深度为d的n元树数目。

    Input

    仅包含两个整数n, d( 0   <   n   <   =   32,   0  < =   d  < = 16)

    Output

    仅包含一个数,即深度为d的n元树的数目。

    Sample Input

    【样例输入1】
    2 2

    【样例输入2】
    2 3

    【样例输入3】
    3 5

    Sample Output

    【样例输出1】
    3

    【样例输出2】
    21

    【样例输出2】
    58871587162270592645034001
     
    这题想了半天也没想出来还是orz了黄巨大才知道怎么做……好烦的dp啊
    f[i]=f[i-1]^n+1
    ans=f[d]-f[d-1]
    要高精的
    幸好有个东西叫模板
    我说……前面一大堆东西就不用认真看了吧
    不过……发现乘方^和加+的优先级有点混乱……只好分开来写
    #define mx 300
    #include<cstdio>
    #include<iostream>
    using namespace std;
    struct gaojing{
         int len;
         int a[mx+10];
    }zero,one,f[20];
    int n,d;
    inline void set0(gaojing &s)//¸ß¾«ÇåÁã 
    {
        s.len=1;
        for (int i=1;i<=mx+5;i++)s.a[i]=0;
    }
    inline void inputn(gaojing &a)//¸ß¾«ÊäÈë 
    {
        set0(a);
        char ch=getchar();
        while (ch<'0'||ch>'9')ch=getchar();  
        while (ch>='0'&&ch<='9')  
        {  
            a.a[a.len++]=ch-'0';
            ch=getchar();
        }
        a.len--;  
        int change[mx+15];
        for (int i=1;i<=a.len;i++)  
          change[i]=a.a[i];  
        for (int i=1;i<=a.len;i++)  
          a.a[i]=change[a.len-i+1];
        while (a.a[a.len]==0)a.len--;
    }  
    inline void put(gaojing a)//¸ß¾«Êä³ö 
    {
        for (int i=a.len;i>=1;i--)printf("%d",a.a[i]);
        printf("
    ");
    }
    inline bool operator < (const gaojing &a,const gaojing &b)//¸ß¾«< 
    {
        if (a.len<b.len)return 1;
        if (a.len>b.len)return 0;
        for (int i=a.len;i>=1;i--)
        {
            if (a.a[i]<b.a[i])return 1;
            if (a.a[i]>b.a[i])return 0;
        }
        return 0;
    }
    inline bool operator == (const gaojing &a,const gaojing &b)//¸ß¾«>
    {
        if (a.len!=b.len)return 0;
        for (int i=a.len;i>=1;i--)
        {
            if (a.a[i]!=b.a[i])return 0;
        }
        return 1;
    }
    inline gaojing max(const gaojing &a,const gaojing &b)//¸ß¾«max
    {
        if (a<b)return b;
        else return a;
    }
    inline gaojing min(const gaojing &a,const gaojing &b)//¸ß¾«min
    {
        if (a<b)return a;
        else return b;
    } 
    inline gaojing operator + (const gaojing &a,const gaojing &b)//¸ß¾«+
    {
        gaojing c;set0(c);  
        int maxlen=max(a.len,b.len);      
        for (int i=1;i<=maxlen;i++)      
        {      
            c.a[i]=c.a[i]+a.a[i]+b.a[i];      
            if (c.a[i]>=10)      
            {      
                c.a[i+1]+=c.a[i]/10;    
                c.a[i]%=10;    
            }    
        }      
        c.len=maxlen+4;      
        while (!c.a[c.len]&&c.len>1) c.len--;    
        return c;
    }
    inline gaojing operator - (const gaojing &a,const gaojing &b)//¸ß¾«-
    {
        gaojing c;set0(c);
        gaojing d;d=a;
        for (int i=1;i<=b.len;i++)  
          {  
            c.a[i]=d.a[i]-b.a[i];  
            if (c.a[i]<0)  
            {  
                c.a[i]+=10;  
                int now=i+1;  
                while (!d.a[now])  
                {  
                    d.a[now]=9;  
                    now++;  
                }  
                d.a[now]--;  
            }  
          }
        for (int i=b.len+1;i<=d.len;i++)c.a[i]=d.a[i];  
        c.len=d.len;  
        while (c.a[c.len]==0&&c.len>1)c.len--;
        return c;
    }  
    inline gaojing operator * (const gaojing &a,const gaojing &b)//¸ß¾«*
    {
        gaojing c;set0(c);
        for(int i=1;i<=a.len;i++)    
          for (int j=1;j<=b.len;j++)    
            c.a[i+j-1]+=a.a[i]*b.a[j];    
        c.len=a.len+b.len+5;  
        for (int i=1;i<=c.len;i++)    
          {    
            c.a[i+1]+=c.a[i]/10;    
            c.a[i]%=10;    
          }    
        while (!c.a[c.len]&&c.len>1)c.len--;
        return c;
    }
    inline void div_by_2(gaojing &a)
    {
        for (int i=a.len;i>=1;i--)
        {
            if (a.a[i]&1 && i!=1)a.a[i-1]+=10;
            a.a[i]/=2;
        }
        while (!a.a[a.len]&&a.len>1)a.len--;
    }
    inline gaojing operator / (gaojing a,const gaojing &b)//¸ß¾«/
    {
        gaojing l,r,ans;
        set0(l);l.len=1;
        set0(r);r=a;
        set0(ans);ans.len=1;
        while (l<r||l==r)
        {
            gaojing mid=l+r;
            div_by_2(mid);
            if(mid*b==a)return mid;
            if(mid*b<a){ans=mid;l=mid+one;}
            if(a<mid*b)r=mid-one;
        }
        return ans;
    }
    inline gaojing operator ^(const gaojing &a,int p)//¸ß¾«^ 
    {
    	gaojing ans=one,mult=a;
    	while (p)
    	{
    		if (p&1)ans=ans*mult;
    		mult=mult*mult;
    		p>>=1;
    	}
    	return ans;
    }
    inline void chushihua()//³õʼ»¯£¬¶Ô0¡¢1¸ß¾«¶È³£Êý¸³Öµ 
    {
        set0(zero); zero.len=1;
        set0(one);one.len=1;one.a[1]=1;
    }
    int main()
    {
    	chushihua();
    	scanf("%d%d",&n,&d);
    	f[0]=one;
    	for (int i=1;i<=d;i++)
    	{
    	  f[i]=f[i-1]^n;
    	  f[i]=f[i]+one;
    	}
    	put(f[d]-f[d-1]);
    }
    
    ——by zhber,转载请注明来源
  • 相关阅读:
    PHP分页类
    phpexcel 控制导出数据内容和行数
    phpexcel 导入 和 导出
    PHP无限极分类
    php 对查询结果集进行排序
    php 删除文件夹及文件夹内文件函数
    php 字符串截取函数
    php 获取用户登录的ip
    js layer页面层加载新网站
    分享到qq
  • 原文地址:https://www.cnblogs.com/zhber/p/4098407.html
Copyright © 2020-2023  润新知