zoukankan      html  css  js  c++  java
  • 【SCOI 2003】 严格n元树

    【题目链接】

               点击打开链接

    【算法】

              f[i]表示深度小于等于i的严格n元树

              显然,一棵深度小于等于i的严格n元树,就是一个根节点,下面有n棵子树,这n棵子树都是深度小于等于i-1的严格n元树,每棵子树有f[i-1]种形态,根据乘法原理,

              可知f[i] = f[i-1] ^ n + 1

              那么最后f[d] - f[d-1]就是答案

              注意要用高精度计算

    【代码】

              

    #include<bits/stdc++.h>
    using namespace std;
    #define MAXN 35
    #define MAXL 400
     
    int i,n,d;
    struct INT
    {
            int len;
            int num[MAXL];
    } ans,f[MAXN];
     
    inline INT add(INT x)
    {
            int i;
            reverse(x.num,x.num+x.len); 
            x.num[0]++;
            for (i = 0; i < x.len; i++)
            {
                    if (x.num[i] >= 10)
                    {
                            x.num[i+1]++;
                            x.num[i] %= 10;
                    }
            }
            while (x.num[x.len]) x.len++;
            reverse(x.num,x.num+x.len);
            return x;
    }
    inline void multipy(INT &a,INT b)
    {
            int i,j;
            static INT res;
            memset(res.num,0,sizeof(res.num));
            reverse(a.num,a.num+a.len);
            reverse(b.num,b.num+b.len);
            for (i = 0; i < a.len; i++)
            {
                    for (j = 0; j < b.len; j++)
                    {
                            res.num[i+j] += a.num[i] * b.num[j];     
                    }    
            }    
            res.len = a.len + b.len - 1;
            while (!res.num[res.len-1]) res.len--;
            for (i = 0; i < res.len; i++)
            {
                    if (res.num[i] >= 10) 
                    {
                            res.num[i+1] += res.num[i] / 10;
                            res.num[i] %= 10; 
                    }
            }
            if (res.num[res.len]) res.len++;
            reverse(res.num,res.num+res.len);
            a = res;
    }
    inline INT _minus(INT a,INT b)
    {
            static INT res;
            memset(res.num,0,sizeof(res.num));
            reverse(a.num,a.num+a.len);
            reverse(b.num,b.num+b.len);
            for (i = 0; i < a.len; i++)
            {
                    if (a.num[i] >= b.num[i]) res.num[i] = a.num[i] - b.num[i];
                    else
                    {
                            a.num[i+1]--;
                            res.num[i] = a.num[i] + 10 - b.num[i];    
                    } 
            }
            res.len = a.len;
            while (!res.num[res.len-1]) res.len--;
            reverse(res.num,res.num+res.len);
            return res;
    }
    inline INT power(INT a,int n)
    {
            INT res;
            if (!n) return (INT){1,{1}};
            if (n == 1) return a;
            res = power(a,n>>1);
            multipy(res,res);
            if (n & 1) multipy(res,a);
            return res;    
    }
    inline void output(INT x)
    {
            int i;
            for (i = 0; i < x.len; i++) printf("%d",x.num[i]);
            puts("");    
    }
    
    int main()
    {
            
            scanf("%d%d",&n,&d);
            f[0] = (INT){1,{1}};
            for (i = 1; i <= d; i++) f[i] = add(power(f[i-1],n));
            ans = _minus(f[d],f[d-1]);
            output(ans);
        
            return 0;
    }
        


  • 相关阅读:
    WSAAsyncSelect模型的小i例子
    网络编程之Winsock2
    网络编程系列之Winsock
    网络编程系列之前言
    winpcap 编程及环境配置
    inno setup 一款强大的安装包制作工具
    创建windows服务程序
    python模块之logging
    ABOUT ME
    [省选联考 2020 A 卷] 树
  • 原文地址:https://www.cnblogs.com/evenbao/p/9196328.html
Copyright © 2011-2022 走看看