惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

The GitHub Blog
The GitHub Blog
博客园 - 三生石上(FineUI控件)
V
V2EX
博客园 - 司徒正美
小众软件
小众软件
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
T
Tailwind CSS Blog
Last Week in AI
Last Week in AI
雷峰网
雷峰网
月光博客
月光博客
钛媒体:引领未来商业与生活新知
钛媒体:引领未来商业与生活新知
Apple Machine Learning Research
Apple Machine Learning Research
让小产品的独立变现更简单 - ezindie.com
让小产品的独立变现更简单 - ezindie.com
S
SegmentFault 最新的问题
美团技术团队
Hugging Face - Blog
Hugging Face - Blog
WordPress大学
WordPress大学
宝玉的分享
宝玉的分享
爱范儿
爱范儿
博客园 - 聂微东
量子位
J
Java Code Geeks
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
Vercel News
Vercel News

博客园 - ZefengYao

Markdown 入门与 Word 使用指南 关于崩溃报告的日志以及dump文件 hdu 6223 Infinite Fraction Path ACM-ICPC 2018 南京赛区网络预赛 Sum c语言几个字符串处理函数的简单实现 各种类型排序的实现及比较 随机洗牌算法Knuth Shuffle和错排公式 两个栈实现队列 面试杂题 面试题——栈的压入、弹出顺序 C++ 智能指针的简单实现 openGL初学函数解释汇总 foj Problem 2107 Hua Rong Dao foj Problem 2282 Wand UVA-1400 Ray, Pass me the dishes! 《挑战程序设计竞赛》 利用后缀数组求最长回文串 Uva 11174 Stand in a Line UVA 11375 Matches poj 3729 Facer’s string
2017南宁现场赛E The Champion
ZefengYao · 2018-10-09 · via 博客园 - ZefengYao

Bob is attending a chess competition. Now the competition is in the knockout phase. There are 2^r2r players now, and they will play over rr rounds.

In each knockout round, the remaining players would be divided into pairs, and the winner of each pair would advance to the next knockout round. Finally only one player would remain and be declared the champion.

Bob has already assigned all players in an order while he assigned himself to the k-th site. A better player is located at a site with a smaller number indicating a higher order. The probability that a player with higher order wins a player with lower order is p (0 \le p \le 1)p(0p1).

Bob notices that arrangement of matches is crucial for the final result.

For example, if there are 44 players and Bob is the second best player (he is the second site), and p = 0.9p=0.9. In the first round, if Bob meets the best player, he will have only 0.1 \times 0.9 = 0.090.1×0.9=0.09 probability to become the champion. However if he does not meet the best player in the first round, he will have 0.9 \times (0.9 \times 0.1 + 0.1 \times 0.9) = 0.1620.9×(0.9×0.1+0.1×0.9)=0.162 probability to become the champion. Now Bob wants to know, what is the winning probability for him in the best arrangement of matches.

Input

The first line in the input contains an integer t (1 \le t \le 63000)t(1t63000) which is the number of test cases.

For each case, there is only one line containing two integers rr and k(1 \le r < 64,1 \le k \le 2^r)(1r<64,1k2r) and a float-point number p (0 \le p \le 1)p(0p1) as described above.

Output

For each case, calculate the winning probability for Bob in the best arrangement. Output the probability with the precision of 66 digits.

样例输出

0.800000
0.162000

题意:2^r个人打比赛,一共比r伦决出冠军,主角的实力排在第k位,并且对于所有人,打败比他弱的人概率是p,打败比他强的人概率是(1-p);主角要尽可能的提高获胜的概率,求这个概率即可
思路:如果当前这一轮还有比主角弱的人,主角选择和弱的人对决,若只剩比主角强的人,就只能和强的人比赛。dfs记得记忆化搜索。。
AC代码:

#define _CRT_SECURE_NO_DEPRECATE
#include<iostream>
#include<algorithm>
#include<cmath>
#include<vector>
#include<cstring>
#include<map>
using namespace std;
#define INF 0x3f3f3f3f
#define EPS 1e-7
typedef unsigned long long ll;
const int N_MAX = 10000+10;
const int MOD = 1e10+7;
int r;
ll k, qiang, ruo, num;
map<pair<ll, ll>, double>mp;//记忆化搜素
double p;

double dfs(ll qiang,ll ruo) {
    if (qiang == 0 && ruo == 0)return 1;
    if (mp[make_pair(qiang, ruo)] != 0)return mp[make_pair(qiang, ruo)];
    ll nxt_qiang = qiang >> 1, nxt_ruo = ruo >> 1;
    if (ruo & 1) {//弱的为奇数个,说明强的为偶数个,只要主角和一个弱的打就行了
        return mp[make_pair(qiang, ruo)] =p*dfs(nxt_qiang, nxt_ruo);
    }
    else {//否则弱的是偶数个,强的奇数个
        if (ruo != 0) {//弱的个数不为0,此时主角还是选择和弱的打,但是总会有一个强的会多出来和弱的打,所以这两者谁赢谁输就要分两种情况
            return mp[make_pair(qiang, ruo)] = p*(p*dfs(nxt_qiang + 1, nxt_ruo - 1) + (1 - p)*dfs(nxt_qiang, nxt_ruo));
        }
        else {//没有弱的选手了,主角只能和强的打
            return mp[make_pair(qiang, 0)] = (1 - p)*dfs(nxt_qiang, 0);
        }
    }
}

int main() {
    int t; scanf("%d",&t);
    while (t--) {
        scanf("%d%lld%lf",&r,&k,&p);
        mp.clear();
        num = 1LL << r;
        qiang = k - 1, ruo = num - k;
        double res=dfs(qiang, ruo);
        printf("%.6f\n",res);
    }
    return 0;
}