• n!最末尾非0数


    最小周期串:
    如果s是ss的周期串,那么ss就可以表示成几个周期的s,
    如果s是ss的最小周期串,那么s就是ss的周期串中最小的一个.
    例,ZgxZgxZgxZgx的最小周期串是Zgx.
    {很好理解}

    给你一串数字ss,找出它的最小周期串n,求n!十进制表示的最末尾的非零数。ss的长度小于等于100。

     1 /*
     2 朴素版 
     3 */
     4 
     5 #include<iostream>
     6 #include<string>
     7 using namespace std;
     8 
     9 string s;
    10 int len=1,i;
    11 int sum2=0;
    12 int ans=1;
    13 int a[8]={1,3,1,9,9,7,9,1};
    14 
    15 
    16 //g(n)=1*3*5*7*9....*(2*n-1)
    17 int g(int n){
    18     if(n==1) return a[0];
    19     if(n==2) return a[1];
    20     sum2-=(n+2)/5;   //2的指数减去5的指数 
    21     
    22     return (g((n+2)/5)*a[(n-(n+2)/5-1)%8])%10;
    23     }
    24 
    25 
    26 //f(n)=n!
    27 int f(int n){
    28     if(n==1) return 1;
    29     sum2+=n/2;   //加上2的指数 
    30     
    31     return (f(n/2)*g(n-n/2))%10;  
    32     }
    33 
    34 
    35 int main()
    36 {
    37     cin>>s;
    38     for(len=1;len<=s.size();len++)
    39     if(s.size()%len==0)
    40     {
    41        for(i=0;i<s.size();++i)
    42        if(s[i%len]!=s[i]) break;
    43        if(i>=s.size()) break;        
    44                }
    45     
    46     
    47     int n=0;
    48     for(i=0;i<len;++i)
    49     n=n*10+s[i]-'0';
    50     
    51     ans=f(n);  
    52     while(sum2>0)
    53     {
    54       sum2--;
    55       ans*=2;
    56       ans%=10;
    57                  }
    58     while(sum2<0)
    59     {
    60       sum2++;
    61       ans*=5;
    62       ans%=10;
    63                  }
    64     
    65     
    66     cout<<ans<<endl;                
    67     
    68     
    69     
    70  //   system("pause");
    71 
    72     } 
      1 /*
      2 高精度版 
      3 */
      4 
      5 #include<iostream>
      6 #include<string>
      7 using namespace std;
      8 
      9 string s;
     10 int len=1,i;
     11 int sum2[105]={0};
     12 int num[105]={0};
     13 int ans=1;
     14 int a[8]={1,3,1,9,9,7,9,1};
     15 int b[4]={2,4,8,6};
     16 
     17 void print(int x[]){
     18      int i=100;
     19      for(i=100;i>=0;i--)
     20      if(x[i]!=0) break;
     21      cout<<endl;
     22      while(i>=0) cout<<x[i--];
     23      cout<<endl;
     24      
     25      }
     26 
     27 //return x==t
     28 bool Equal(int x[],int t){
     29      for(int i=100;i>0;i--)
     30      if(x[i]!=0) return false;
     31      if(x[0]==t) return true;
     32      return false;
     33      }
     34 
     35 //z=y+t
     36 void add(int z[],int y[],int t){
     37      for(int i=0;i<=100;++i)
     38      z[i]=y[i];
     39      z[0]+=t;
     40      int i=0;
     41      while(z[i]>=10)
     42      {
     43        z[i+1]+=z[i]/10;
     44        z[i]%=10;
     45        i++;
     46                    }
     47      return ;
     48      }
     49 
     50 //x=x-y
     51 void Sub(int x[],int y[]){
     52      for(int i=0;i<=100;++i)
     53      {
     54        x[i]=x[i]-y[i];
     55        if(x[i]<0) {x[i]+=10;x[i+1]-=1;}
     56              }
     57      return ;
     58      }
     59      
     60 //return (x-y-t)%m
     61 int SubAndMod(int x[],int y[],int t,int m){
     62     Sub(x,y);
     63     x[0]-=t;
     64     int i=0;
     65     while(x[i]<0)
     66     {
     67       x[i]+=10;
     68       x[i+1]-=1;
     69       i++;
     70                  }
     71     
     72     int tt=0;
     73     for(int i=100;i>=0;i--)
     74     {
     75        tt=tt*10;
     76        tt=(tt+x[i])%m;
     77             }
     78     return tt;
     79     }
     80 
     81 //y=x/k
     82 void Divide(int y[],int x[],int k){
     83      int t=0;
     84      for(int i=100;i>=0;i--)
     85      {
     86        y[i]=(t+x[i])/k;
     87        t=(t+x[i])%k;
     88        t*=10;
     89              }
     90      }
     91      
     92 //g(x)=1*3*5*7*9....*(2*x-1)
     93 int g(int x[]){
     94     if(Equal(x,1)) return a[0];
     95     if(Equal(x,2)) return a[1];
     96     int y[105]={0},z[105]={0};
     97     add(y,x,2);    //y=x+2
     98     Divide(z,y,5); //z=y/5  z为5的指数 
     99     Sub(sum2,z);   //2的指数减去5的指数 
    100     
    101     int t=SubAndMod(x,z,1,8);   //t=(x-(x+2)/5-1)%8
    102     return (g(z)*a[t])%10;
    103     }
    104 
    105 
    106 
    107 //y=y+x
    108 void Sum(int y[],int x[]){
    109      for(int i=0;i<=100;++i)
    110      {
    111        y[i]=y[i]+x[i];
    112        y[i+1]+=y[i]/10;
    113        y[i]%=10;
    114              }
    115      
    116      }
    117      
    118 //f(x)=x!     
    119 int f(int x[]){
    120     if(Equal(x,1)) return 1;
    121     int y[105]={0};
    122     Divide(y,x,2);   //y=x/2
    123     Sum(sum2,y);     //加上2的指数 
    124     if(x[0]%2==0) return (f(y)*g(y))%10;
    125     int z[105]={0};
    126     add(z,y,1);
    127     return (f(y)*g(z))%10;
    128     }
    129 
    130 
    131 int main()
    132 {
    133     cin>>s;
    134     for(len=1;len<=s.size();len++)
    135     if(s.size()%len==0)
    136     {
    137        for(i=0;i<s.size();++i)
    138        if(s[i%len]!=s[i]) break;
    139        if(i>=s.size()) break;        
    140                }
    141 
    142     for(i=0;i<len;++i)
    143     num[i]=s[len-i-1]-'0';
    144     ans=f(num);
    145     
    146     int z[105]={0};
    147     if(!Equal(sum2,0))
    148     ans=ans*b[SubAndMod(sum2,z,1,4)];
    149     
    150     ans%=10;
    151     cout<<ans<<endl;
    152   //  system("pause");
    153 
    154     } 
  • 相关阅读:
    消除共模干扰的方法
    C#模拟键盘事件
    获取本地IP V4 出现::1
    生成ssh密钥
    苹果应用商店DNS修改加快下载速度
    模算术 modular arithmetic
    有限域和质数的幂
    rere
    test
    图信号处理进行大数据分析
  • 原文地址:https://www.cnblogs.com/noip/p/7783512.html
Copyright © 2020-2023  润新知