• TopCoder[SRM513 DIV 1]:PerfectMemory(500)


    Problem Statement

         You might have played the game called Memoria. In this game, there is a board consisting of N rows containing M cells each. Each of the cells has a symbol on its back. Each symbol occurs on exactly two cells on the board. 



    A move means turning a pair of cells one by one to see the symbols behind them. When the symbols differ, both of the cells are turned on their faces, thus hiding the symbols again. The player should remember the symbols. If the symbols on the backs of the turned cells coincide, the cells stay that way, i.e., don't turn back again. As soon as after some move all the cells on the board are turned (such that all the symbols are simultaneously visible), the game ends. 



    Manao has a perfect memory, so when he sees the symbol behind some cell, he remembers it forever. Manao is trying to finish the game in the least expected number of moves. Find the expected number of moves he will need to accomplish this.

    Definition

        
    Class: PerfectMemory
    Method: getExpectation
    Parameters: int, int
    Returns: double
    Method signature: double getExpectation(int N, int M)
    (be sure your method is public)

    Limits

        
    Time limit (s): 2.000
    Memory limit (MB): 64

    Notes

    - The board Manao plays on is generated as follows. The same set of (N * M) / 2 symbols is used for each generation. The board contents are chosen uniformly among all valid N x M boards.
    - The returned value must have an absolute or relative error less than 1e-9.

    Constraints

    - N will be between 1 and 50, inclusive.
    - M will be between 1 and 50, inclusive.
    - N * M will be even.

    Examples

    0)  
        
    1
    2
    Returns: 1.0
    There are only two cells on the board, so the game always ends in one move.
    1)  
        
    2
    2
    Returns: 2.6666666666666665
    There are four cells. The game may flow in two possible scenarios:

    1) In the first move, Manao turns two cells with equal symbols. The game ends in two moves then and the probability of such a first move is 1/3.

    2) In the first move, Manao turns two cells with different symbols. Then he finishes the game in three moves and the probability of such a first move is 2/3.

    The overall expected number of moves is 1/3 * 2 + 2/3 * 3 = 8/3.
    2)  
        
    2
    3
    Returns: 4.333333333333334
     
    3)  
        
    4
    4
    Returns: 12.392984792984793
     

    题意:你有n*m张卡片,总共n*m/2种,每种有两张。每次操作时你可以翻开两张,若一样,则它们不再翻回去;否则,这两张卡面会向你展示后再翻回去(不改变位置),假设你记忆力很好,能够记住牌的种类。求出至少进行多少次操作,可以使所有牌都同时正面朝上。注意,一次操作翻牌是有先后的,即你可以先翻一张牌,看过其种类后,再决定翻第二张牌。

    题解:

    假设翻到一样的牌,它们就会被消掉。dp[i][j]表示场上还有i+j张牌未被消掉,已经翻开过其中i张牌(即知道其种类),剩下的j张牌还未被翻开过。

    每次操作一定会先翻一张未被翻过的牌,若其与i张牌中的一张对应,则第二张牌一定翻这张,把它们消掉。若是一张新的牌,则第二张牌一定也翻未被翻过的牌。

    计算每种情况出现的概率与期望,以j为阶段、i为状态,进行动态规划。

    代码:

     1 double dp[2502][2502];
     2 class PerfectMemory 
     3 {
     4     public:
     5     double getExpectation(int N, int M) 
     6     {
     7         //$CARETPOSITION$
     8         int n=N*M; dp[0][0]=0;
     9         for(int j=0;j<=n;j++)
    10         for(int i=0;i<=n;i++)
    11         {
    12             if((i==0)and(j==0))continue; dp[i][j]=10000000;
    13             if(i>j)continue; if(i+j>n)continue; if((j-i)%2==1)continue;
    14             dp[i][j]=0; double p,p2,a1;
    15             p=i; p=p/j; p2=1-p;
    16             if((j>0)and(i>0))
    17             {
    18                 dp[i][j]=dp[i][j]+p*(1+dp[i-1][j-1]);
    19             }
    20             double b,c,d;
    21             if(j>1)
    22             {
    23                 b=1; b=b/(j-1); c=j-2-i; c=c/(j-1); d=1-b-c;
    24                 a1=b*(1+dp[i][j-2])+c*(1+dp[i+2][j-2])+d*(2+dp[i][j-2]);
    25                 dp[i][j]=dp[i][j]+p2*a1;
    26             }
    27         }
    28         return dp[0][n];
    29         
    30     }
    31 };
    View Code
  • 相关阅读:
    python BUGGGGGGGGGG
    Golang channel底层原理及 select 和range 操作channel用法
    Go reflect包用法和理解
    Golang 之sync包应用
    Golang 之 sync.Pool揭秘
    深入理解字节码文件
    java中的回调,监听器,观察者
    范式
    BIO,NIO,AIO总结(二)
    anaconda命令行运行过程中出现的错误
  • 原文地址:https://www.cnblogs.com/GhostReach/p/6668558.html
Copyright © 2020-2023  润新知