zoukankan      html  css  js  c++  java
  • [HDU5955]Guessing the Dice Roll

    Problem Description
    There are N players playing a guessing game. Each player guesses a sequence consists of {1,2,3,4,5,6} with length L, then a dice will be rolled again and again and the roll out sequence will be recorded. The player whose guessing sequence first matches the last L rolls of the dice wins the game.
     
    Input
    The first line is the number of test cases. For each test case, the first line contains 2 integers N (1 ≤ N ≤ 10) and L (1 ≤ L ≤ 10). Each of the following N lines contains a guessing sequence with length L. It is guaranteed that the guessing sequences are consist of {1,2,3,4,5,6} and all the guessing sequences are distinct.
     
    Output
    For each test case, output a line containing the winning probability of each player with the precision of 6 digits.
     
    Sample Input
    3 5 1 1 2 3 4 5 6 2 1 1 2 1 3 1 4 1 5 1 6 1 4 3 1 2 3 2 3 4 3 4 5 4 5 6
     
    Sample Output
    0.200000 0.200000 0.200000 0.200000 0.200000 0.027778 0.194444 0.194444 0.194444 0.194444 0.194444 0.285337 0.237781 0.237781 0.239102
     

     
    对所有串建AC自动机,然后按照Trie图建立递推关系,转化成矩阵,用高斯消元解决带环的转移。
    写起来略恶心,反正我是不想调了。
     

     
    #include <iostream>
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    #include <queue>
    #include <cmath>
    using namespace std;
    #define reg register
    inline int read() {
        int res = 0;char ch=getchar();bool fu=0;
        while(!isdigit(ch))fu|=(ch=='-'),ch=getchar();
        while(isdigit(ch)) res=(res<<3)+(res<<1)+(ch^48),ch=getchar();
        return fu?-res:res;
    }
    
    int T;
    int n, L;
    int nxt[105][7], fail[105], danger[105], tot, who[105];
    inline void ins(int *s, int id) 
    {
        int now = 0;
        for (reg int i = 1 ; i <= L ; i ++)
            now = nxt[now][s[i]] ? nxt[now][s[i]] : nxt[now][s[i]] = ++tot;
        danger[now] = 1;
        who[now] = id;
    }
    
    inline void Build()
    {
        queue <int> q;
        for (reg int i = 1 ; i <= 6 ;i ++) if (nxt[0][i]) q.push(nxt[0][i]);
        while(!q.empty())
        {
            int x = q.front();q.pop();
            for (reg int i = 1 ; i <= 6 ; i ++)
                if (nxt[x][i]) fail[nxt[x][i]] = nxt[fail[x]][i], q.push(nxt[x][i]);
                else nxt[x][i] = nxt[fail[x]][i];
            danger[x] |= danger[fail[x]];
        }
    }
    
    long double a[105][105], ans[15];
    
    inline void Gauss()
    {
        for (reg int i = 0 ; i <= tot ; i ++)
        {
            int k = i;
            for (reg int j = i ; j <= tot ; j ++)
                if (fabs(a[j][i]) > fabs(a[k][i])) k = j;
            if (k != i) swap(a[k], a[i]);
            for (reg int j = 0 ; j <= tot ; j ++)
            {
                if (i == j) continue;
                long double r = a[j][i] / a[i][i];
                for (reg int k = i ; k <= tot + 1 ; k ++)
                    a[j][k] -= a[i][k] * r;
            }
        }
    }
    
    int main()
    {
        T = read();
        while(T--)
        {
            memset(nxt, 0, sizeof nxt);
            memset(fail, 0, sizeof fail);
            memset(danger, 0, sizeof danger);
            tot = 0;
            n = read(), L = read();
            int tmp[13];
            for (reg int i = 1 ; i <= n ; i ++)
            {
                for (reg int j = 1 ; j <= L ; j ++) tmp[j] = read();
                ins(tmp, i);
            }
            Build();
            memset(a, 0, sizeof a);
            for (reg int i = 0 ; i <= tot ; i ++)
            {
                a[i][i] -= 1.0;
                if (danger[i]) continue;
                for (reg int j = 1 ; j <= 6 ; j ++)
                    a[nxt[i][j]][i] += 1.0 / 6.0;
            }
            a[0][tot + 1] = -1.0;
    //        for(int i=0;i<=tot;i++,puts(""))
    //            for(int j=0;j<=tot+1;j++) printf("%.2Lf ",a[i][j]);
            Gauss();
            for (reg int i = 0 ; i <= tot ; i ++)
                if (danger[i]) ans[who[i]] = a[i][tot + 1] / a[i][i];
            for (reg int i = 1 ; i < n ; i ++) printf("%.6Lf ", ans[i]);
            printf("%.6Lf
    ", ans[n]);
        }
        return 0;
    }
  • 相关阅读:
    django从零开始-模板
    django从零开始-模型
    django从零开始-视图
    web基础
    django从零开始-入门
    Pycharm自动添加文件头注释
    django后台密码错误
    module 'sign.views' has no attribute 'search_name'
    TypeError: __init__() got an unexpected keyword argument 't_command'
    pycharm 中的 全局搜索(ctrl+shift+f) 功能无法使用的原因
  • 原文地址:https://www.cnblogs.com/BriMon/p/9842122.html
Copyright © 2011-2022 走看看