zoukankan      html  css  js  c++  java
  • HDU 2604 Queuing 矩阵高速幂

    Queuing

    Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
    Total Submission(s): 2483    Accepted Submission(s): 1169


    Problem Description
    Queues and Priority Queues are data structures which are known to most computer scientists. The Queue occurs often in our daily life. There are many people lined up at the lunch time. 
      Now we define that ‘f’ is short for female and ‘m’ is short for male. If the queue’s length is L, then there are 2L numbers of queues. For example, if L = 2, then they are ff, mm, fm, mf . If there exists a subqueue as fmf or fff, we call it O-queue else it is a E-queue.
    Your task is to calculate the number of E-queues mod M with length L by writing a program.
     

    Input
    Input a length L (0 <= L <= 10 6) and M.
     

    Output
    Output K mod M(1 <= M <= 30) where K is the number of E-queues with length L.
     

    Sample Input
    3 8 4 7 4 8
     

    Sample Output
    6 2 1
     

    Author
    WhereIsHeroFrom
     

    Source
     


    题解

    突然发现这类题目又是有一个小技巧的。先说题意,一个字符串,由f和m两种字符构成。如今的问题是,当中的子串,不出现“fff”和"fmf"的长度为L的串有多少个。

    相同的,我们考虑一个充分长的串,确定他的最后两位之后,看看倒数第三位的字符是什么:


    这里的x代表的是倒数第三位,能够看到,事实上这个是有规律可循的。我们仅仅要把生成fff和fmf的那种情况规避掉即可了。所以整个矩阵就是:


    最后把矩阵中的所有的值所有加起来取模就可以。

    代码演示样例

    /****
    	*@author    Shen
    	*@title     HDU 2604
    	*/
    #include <cstdio>
    #include <string>
    #include <cstring>
    #include <iostream>
    #include <algorithm>
    using namespace std;
    typedef long long int64;
    
    const int MAXN = 4;
    const int MAXM = 4;
    const int Mod = 1000000007;
    
    struct Matrax{
        int n, m;
        int64 mat[MAXN][MAXM];
        Matrax(): n(-1), m(-1){}
        Matrax(int _n, int _m): n(_n), m(_m){
            memset(mat, 0, sizeof(mat));
        }
        void Unit(int _s){
            n = _s; m = _s;
            for (int i = 0; i < n; i++){
                for (int j = 0; j < n; j++){
                    mat[i][j] = (i == j)? 1: 0;
                }
            }
        }
        void print(){
            printf("n = %d, m =  %d
    ", n, m);
            for (int i = 0; i < n; i++){
                for (int j = 0; j < m; j++)
                    printf("%16d", mat[i][j]);
                printf("
    ");
            }
        }
    };
    
    Matrax add_mod(const Matrax& a,const Matrax& b,const int64 mod){
        Matrax ans(a.n, a.m);
        for (int i = 0; i < a.n; i++){
            for (int j = 0; j < a.m; j++){
                ans.mat[i][j] = (a.mat[i][j] + b.mat[i][j]) % mod;
            }
        }
        return ans;
    }
    
    Matrax mul(const Matrax& a,const Matrax& b){
        Matrax ans(a.n, b.m);
        for (int i = 0; i < a.n; i++){
            for (int j = 0; j < b.m; j++){
                int64 tmp = 0;
                for (int k = 0; k < a.m; k++){
                    tmp += a.mat[i][k] * b.mat[k][j];
                }
                ans.mat[i][j] = tmp;
            }
        }
        return ans;
    }
    
    Matrax mul_mod(const Matrax& a, const Matrax& b, const int mod){
        Matrax ans(a.n, b.m);
        for (int i = 0; i < a.n; i++){
            for (int j = 0; j < b.m; j++){
                int64 tmp = 0;
                for (int k = 0; k < a.m; k++){
                    tmp += (a.mat[i][k] * b.mat[k][j]) % mod;
                }
                ans.mat[i][j] = tmp % mod;
            }
        }
        return ans;
    }
    
    Matrax pow_mod(const Matrax& a, int64 k, const int mod){
        Matrax p(a.n, a.m), ans(a.n, a.m);
        p = a; ans.Unit(a.n);
        if (k == 0) return ans;
        else if (k == 1) return a;
        else {
            while (k){
                if (k & 1){
                    ans = mul_mod(ans, p, mod);
                    k--;
                }
                else {
                    k /= 2;
                    p = mul_mod(p, p, mod);
                }
            }
            return ans;
        }
    }
    
    int  l, m;
    
    void solve(){
        if (l <= 2)
        {
            int root = 1;
            for (int i = 0; i < l; i++)
                root *= 2;
            cout << root % m << endl;
            return;
        }
    
        Matrax ans(1, 1);
    
        //tmp = cef ^ (l - 2);
        //ans = vct * tmp;
        //ans = ans * beg;
        //res = ans.mat[0][0] % m;
    
        Matrax cef(4, 4), tmp(4, 4);
        cef.mat[0][0] = 1; cef.mat[0][3] = 1;
        cef.mat[1][2] = 1;
        cef.mat[2][0] = 1;
        cef.mat[3][1] = 1; cef.mat[3][2] = 1;
        //cef.print();
    
        Matrax beg(4, 1), vct(1, 4);
        for (int i = 0; i < 4; i++)
            beg.mat[i][0] = vct.mat[0][i] = 1;
    
        tmp = pow_mod(cef, l - 2, m);
        //tmp.print();
    
        vct = mul_mod(vct, tmp, m);
        ans = mul_mod(vct, beg, m);
        //ans.print();
    
        int res = ans.mat[0][0];
        cout << res % m << endl;
    }
    
    int main(){
        while (cin >> l >> m) solve();
        return 0;
    }
  • 相关阅读:
    python连接SMTP的TLS(587端口)发邮件python发邮件(带认证,587端口)202010
    JAVA抓取通过JS渲染的网站(动态)网页数据
    moviepy音视频剪辑:与大小相关的视频变换函数详解
    区块链知识博文1: 共识算法之争(PBFT,Raft,PoW,PoS,DPoS,Ripple)
    MoviePy v2.0.0.dev1尚不成熟,不建议大家使用
    区块链学习2:一些概念性的基础知识笔记
    老猿学5G:3GPP 5G规范中的URI资源概念
    区块链学习1:Merkle树(默克尔树)和Merkle根
    老猿Python博客文章目录索引
    老猿学5G:融合计费场景的Nchf_ConvergedCharging_Create、Update和Release融合计费消息交互过程
  • 原文地址:https://www.cnblogs.com/zfyouxi/p/3774402.html
Copyright © 2011-2022 走看看