POJ3071---Football

Football

Time Limit: 1000MS   Memory Limit: 65536K
Total Submissions: 3267   Accepted: 1668

Description

Consider a single-elimination football tournament involving 2n teams, denoted 1, 2, …, 2n. In each round of the tournament, all teams still in the tournament are placed in a list in order of increasing index. Then,
the first team in the list plays the second team, the third team plays the fourth team, etc. The winners of these matches advance to the next round, and the losers are eliminated. After
n rounds, only one team remains undefeated; this team is declared the winner.

Given a matrix P = [pij] such that pij is the probability that team
i will beat team j in a match determine which team is most likely to win the tournament.

Input

The input test file will contain multiple test cases. Each test case will begin with a single line containing
n (1 ≤ n ≤ 7). The next 2n lines each contain 2n values; here, the
jth value on the ith line represents pij. The matrix
P will satisfy the constraints that pij = 1.0 ?
pji
for all ij, and pii = 0.0 for all
i. The end-of-file is denoted by a single line containing the number ?1. Note that each of the matrix entries in this problem is given as a floating-point value. To avoid precision problems, make sure that you use either the
double data type instead of float.

Output

The output file should contain a single line for each test case indicating the number of the team most likely to win. To prevent floating-point precision issues, it is guaranteed that the difference in win probability for the top two teams will be at least
0.01.

Sample Input

2
0.0 0.1 0.2 0.3
0.9 0.0 0.4 0.5
0.8 0.6 0.0 0.6
0.7 0.5 0.4 0.0
-1

Sample Output

2

Hint

In the test case above, teams 1 and 2 and teams 3 and 4 play against each other in the first round; the winners of each match then play to determine the winner of the tournament. The probability that team 2 wins the tournament in this case is:

P(2 wins)  = P(2 beats 1)P(3 beats 4)P(2 beats 3) + P(2 beats 1)P(4 beats 3)P(2 beats 4)

= p21p34p23 + p21p43p24

= 0.9 · 0.6 · 0.4 + 0.9 · 0.4 · 0.5 = 0.396.

The next most likely team to win is team 3, with a 0.372 probability of winning the tournament.

Source

Stanford Local 2006

概率dp+规律,

令dp[i][j] 表示 第i个人赢到第j轮的概率

然后找到所有可能在第j轮和i相遇的队员(化二进制,找最高位不同)

/*************************************************************************
    > File Name: POJ3071.cpp
    > Author: ALex
    > Mail: [email protected]
    > Created Time: 2014年12月20日 星期六 13时20分58秒
 ************************************************************************/

#include <map>
#include <set>
#include <queue>
#include <stack>
#include <vector>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;

const int N = 200;
double dp[N][10];
double mat[N][N];
int n;

int diff(int a, int b)
{
    for (int i = n; i >= 0; i--)
    {
        if ((a & (1 << i)) != (b & (1 << i)))
        {
            return i;
        }
    }
}

int main()
{
    while (~scanf("%d", &n))
    {
        if (n == -1)
        {
            break;
        }
        for (int i = 1; i <= (1 << n); i++)
        {
            for (int j = 1; j <= (1 << n); j++)
            {
                scanf("%lf", &mat[i][j]);
            }
        }
        for (int i = 1; i <= (1 << n); i++)
        {
            for (int j = 1; j <=n; j++)
            {
                dp[i][j] = 0.0;
            }
        }
        for (int i = 1; i <= (1 << n); i++)
        {
            dp[i][0] = 1.0;
        }
        for (int i = 1; i <= n; i++)
        {
            for (int j = 1; j <= (1 << n); j++)
            {
                for (int k = 1; k <= (1 << n); k++)
                {
                    if (j == k)
                    {
                        continue;
                    }
                    int p = diff(j - 1, k - 1);
                    if (p != i - 1)
                    {
                        continue;
                    }
                    dp[j][i] += dp[j][i - 1] * dp[k][i - 1] * mat[j][k];
                }
            }
        }
        int cnt;
        double ans = 0;
        for (int i = 1; i <= (1 << n); i++)
        {
            if (ans < dp[i][n])
            {
                ans = dp[i][n];
                cnt = i;
            }
        }
        printf("%d\n", cnt);
    }
    return 0;
}
时间: 2024-08-08 05:38:55

POJ3071---Football的相关文章

POJ3071 Football 【概率dp】

题目 Consider a single-elimination football tournament involving 2n teams, denoted 1, 2, -, 2n. In each round of the tournament, all teams still in the tournament are placed in a list in order of increasing index. Then, the first team in the list plays

[poj3071]football概率dp

题意:n支队伍两两进行比赛,求最有可能获得冠军的队伍. 解题关键:概率dp,转移方程:$dp[i][j] +  = dp[i][j]*dp[i][k]*p[j][k]$表示第$i$回合$j$获胜的概率,原理为全概率公式. 如何判断相邻,通过位运算. 1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 #include<cstdlib> 5 #include<cmath> 6

POJ3071(Football)--概率DP

题目在这 题意:有(1<<n个足球队进行比赛,在经过多轮一对一淘汰赛后决出冠军队伍,问最后哪支队伍能够获胜,即输出获胜概率最大的那支队伍编号.给了你n*n的矩阵,用来表示每支队伍间的各自胜率.输入-1为表示结束 en....网上当然也后不少解题报告,但是很多直接给出状态转移方程和贴出代码,而少了其中重要的推断过程,我觉得不是很好.所以自己给写一个较为详细的过程 首先呢,以n==3为例子,即8支队伍参赛.一种比赛情形是这样的 由图可知,在题中给定n后,需要比赛n轮即可知道冠军队伍是谁,我这里多了

Holiday 8

今天是大年初一,但是我的心情并不怎么样.感觉过年了老家人也多了,人多了就不清净了.也不会浮躁,就是心里老是烦.这两天的学习效率远比不上之前,得赶紧调整. 今天结了概率一章的内容,最后的两道例题都没看懂,概率还需要继续学习积累沉淀. POJ3071 Football (http://poj.org/problem?id=3071) 与其说是DP,更像是递推,递推方程很好想,关键在于计算第i轮第k支球队可能碰到的对手,书上的计算方式看不懂,网上也找了不少博客,都大同小异.之后突然就茅塞顿开.首先很容

【POJ3071】Football - 状态压缩+期望 DP

Description Consider a single-elimination football tournament involving 2n teams, denoted 1, 2, …, 2n. In each round of the tournament, all teams still in the tournament are placed in a list in order of increasing index. Then, the first team in the l

POJ3071(Football)

Football Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 3469   Accepted: 1782 Description Consider a single-elimination football tournament involving 2n teams, denoted 1, 2, …, 2n. In each round of the tournament, all teams still in the

poj3071之概率DP

Football Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 2667   Accepted: 1361 Description Consider a single-elimination football tournament involving 2n teams, denoted 1, 2, -, 2n. In each round of the tournament, all teams still in the

Codeforces Round #281 (Div. 2) A. Vasya and Football 暴力

A. Vasya and Football Vasya has started watching football games. He has learned that for some fouls the players receive yellow cards, and for some fouls they receive red cards. A player who receives the second yellow card automatically receives a red

poj3071(概率DP)

题意:淘汰赛制,2^n(n<=7)个队员.给出相互PK的输赢概率矩阵.问谁最有可能赢到最后. 解法:ans[i][j]表示第i个队员第j轮胜出的概率.赢到最后需要进行n场比赛.算出每个人赢到最后的ans[i][n].写出序号的二进制发现一个规律,两个队员i.j如果碰到,那么一定是在第get(i,j)场比赛碰到的.get(i,j)计算的是i和j二进制不同的最高位,这个规律也比较明显. 代码: /****************************************************

POJ 3071 Football

Description Consider a single-elimination football tournament involving 2n teams, denoted 1, 2, -, 2n. In each round of the tournament, all teams still in the tournament are placed in a list in order of increasing index. Then, the first team in the l