zoukankan      html  css  js  c++  java
  • HDOJ 3547 DIY Cube 解题报告

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3547

    题目大意:求用$C$种颜色给立方体的8个顶点染色的本质不同的方法。两种方法本质不同即不能通过旋转立方体使得两个立方体的染色情况一致。

    简要题解:首先可以得到有24种组合旋转方式。根据Polya定理以及群论中的拉格朗日定理,然后再自己多想一想,就可以得到:$Ans=frac{x^8+Ax^4+Bx^2+Cx}{24}$,可知有3个未知数,然后样例正好有3组数据,所以可以解方程解得$A=17,B=6,C=0$。注意第三个数据是模了$10^{15}$次方的,但是显然$112^4$的四次方并不会超过$10^{15}$,所以也可以拿来使用。最后直接高精度就可以了。

      1 #include <cstdio>
      2 #include <cstring>
      3 #include <algorithm>
      4 using namespace std;
      5 #define K 10
      6 #define D 15
      7 
      8 const int T[5] = {0, 0, 6, 17, 1};
      9 int Case, n;
     10 
     11 struct Big
     12 {
     13     int len, num[101];
     14     Big () {len = 0; memset(num, 0, sizeof(num));}
     15     void init(int k)
     16     {
     17         len = 0;
     18         memset(num, 0, sizeof(num));
     19         for (; k; k /= K)
     20             num[++ len] = k % K;
     21         len = max(len, 1);
     22     }
     23     void Add(Big a)
     24     {
     25         len = max(len, a.len);
     26         for (int i = 1; i <= len; i ++)
     27             num[i] += a.num[i];
     28         for (int i = 1; i < len; i ++)
     29             if (num[i] >= K)
     30             {
     31                 num[i + 1] ++;
     32                 num[i] -= K;
     33             }
     34         if (num[len] >= K)
     35         {
     36             num[len + 1] = 1;
     37             num[len ++] -= K;
     38         }
     39     }
     40     void Times(Big a)
     41     {
     42         Big b;
     43         b.len = len + a.len - 1;
     44         for (int i = 1; i <= len; i ++)
     45             for (int j = 1; j <= a.len; j ++)
     46                 b.num[i + j - 1] += num[i] * a.num[j];
     47         for (int i = 1; i < b.len; i ++)
     48             if (b.num[i] >= K)
     49             {
     50                 b.num[i + 1] += b.num[i] / K;
     51                 b.num[i] %= K;
     52             }
     53         while (b.num[b.len] >= K)
     54         {
     55             b.num[b.len + 1] += b.num[b.len] / K;
     56             b.num[b.len ++] %= K;
     57         }
     58         len = b.len;
     59         for (int i = 1; i <= len; i ++)
     60             num[i] = b.num[i];
     61     }
     62     void Multi(int k)
     63     {
     64         for (int i = 1; i <= len; i ++)
     65             num[i] *= k;
     66         for (int i = 1; i < len; i ++)
     67             if (num[i] >= K)
     68             {
     69                 num[i + 1] += num[i] / K;
     70                 num[i] %= K;
     71             }
     72         while (num[len] >= K)
     73         {
     74             num[len + 1] += num[len] / K;
     75             num[len ++] %= K;
     76         }
     77     }
     78     void Divide(int k)
     79     {
     80         for (int i = len; i >= 1; i --)
     81         {
     82             if (i > 1) num[i - 1] += (num[i] % k) * K;
     83             num[i] /= k;
     84         }
     85         for (; !num[len] && len > 1; len --) ;
     86     }
     87     void out()
     88     {
     89         for (int i = min(D, len); i; i --)
     90             printf("%d", num[i]);
     91         puts("");
     92     }
     93 }A[5], Ans;
     94 
     95 int main()
     96 {
     97     scanf("%d", &Case);
     98     for (int Test = 1; Test <= Case; Test ++)
     99     {
    100         scanf("%d", &n);
    101         A[1].init(n), Ans.init(0);
    102         for (int i = 2; i <= 4; i ++)
    103         {
    104             A[i] = A[i - 1];
    105             A[i].Times(A[i - 1]);
    106             A[i].Multi(T[i]);
    107             Ans.Add(A[i]);
    108             A[i].Divide(T[i]);
    109         }
    110         Ans.Divide(24);
    111         printf("Case %d: ", Test);
    112         Ans.out();
    113     }
    114     return 0;
    115 }
    HDOJ 3547
      1 #include <cstdio>
      2 typedef long long LL;
      3 #define Mod 10000000000000000LL
      4 
      5 const int Base[4] = {0, 1, 2, 112};
      6 const LL Ans[4] = {0LL, 23LL, 296LL, 2675058176LL};
      7 
      8 struct Frac
      9 {
     10     LL fz, fm;
     11     Frac (LL _fz = 0LL, LL _fm = 0LL) {fz = _fz, fm = _fm;}
     12     LL Abs(LL x)
     13     {
     14         return x > 0 ? x : -x;
     15     }
     16     LL gcd(LL x, LL y)
     17     {
     18         return !y ? x : gcd(y, x % y);
     19     }
     20     void Simplify()
     21     {
     22         LL d = gcd(Abs(fz), Abs(fm));
     23         fz /= d, fm /= d;
     24         if (fm < 0) fm = -fm, fz = -fz;
     25     }
     26     Frac operator + (const Frac a)
     27     {
     28         Frac b;
     29         b.fz = fz * a.fm + fm * a.fz;
     30         b.fm = fm * a.fm;
     31         b.Simplify();
     32         return b;
     33     }
     34     Frac operator - (const Frac a)
     35     {
     36         Frac b;
     37         b.fz = fz * a.fm - fm * a.fz;
     38         b.fm = fm * a.fm;
     39         b.Simplify();
     40         return b;
     41     }
     42     Frac operator * (const Frac a)
     43     {
     44         Frac b;
     45         b.fz = fz * a.fz;
     46         b.fm = fm * a.fm;
     47         b.Simplify();
     48         return b;
     49     }
     50     Frac operator / (const Frac a)
     51     {
     52         Frac b;
     53         b.fz = fz * a.fm;
     54         b.fm = fm * a.fz;
     55         b.Simplify();
     56         return b;
     57     }
     58     void out()
     59     {
     60         printf("%lld/%lld
    ", fz, fm);
     61     }
     62 }X[5][5], Y[5];
     63 
     64 inline void Gauss()
     65 {
     66     for (int i = 1; i < 3; i ++)
     67         for (int j = i + 1; j <= 3; j ++)
     68         {
     69             Frac t = X[j][i] / X[i][i];
     70             for (int k = i; k <= 3; k ++)
     71                 X[j][k] = X[j][k] - X[i][k] * t;
     72             Y[j] = Y[j] - Y[i] * t;
     73         }
     74     for (int i = 3; i; i --)
     75     {
     76         Frac sum;
     77         sum.fz = 0LL, sum.fm = 1LL;
     78         for (int j = i + 1; j <= 3; j ++)
     79             sum = sum + X[i][j] * Y[j];
     80         Y[i] = (Y[i] - sum) / X[i][i];
     81     }
     82 }
     83 
     84 int main()
     85 {
     86     for (int i = 1; i <= 3; i ++)
     87     {
     88         for (int j = 3; j; j --)
     89         {
     90             if (j == 3) X[i][j].fz = Base[i];
     91                 else X[i][j].fz = X[i][j + 1].fz * X[i][j + 1].fz;
     92             X[i][j].fm = 1LL;
     93         }
     94         Y[i].fz = Ans[i], Y[i].fm = 1LL;
     95     }
     96     Gauss();
     97     for (int i = 1; i <= 3; i ++)
     98         Y[i].out();
     99     return 0;
    100 }
    HDOJ 3547 (Gauss)
  • 相关阅读:
    单链表反转
    C++面试题
    堆排序
    1链表:回文链表(leetcode 234)
    深信服社招linux岗面试记录
    腾讯后台开发社招记录(电话面试)
    小米社招ATE岗位记录
    诺基亚社招C++面试记录
    腾讯后台开发社招面试记录
    makefile笔记
  • 原文地址:https://www.cnblogs.com/gromah/p/5767013.html
Copyright © 2011-2022 走看看