Codeforces 678E. Another Sith Tournament

题意:

n(n<=18)个人打擂台赛,给定任意两人对决的胜负概率,比赛规则:可指定一人作为最开始的擂主,每次可指定台下的人替代失败的人上去对决,失败的人出局。问在最优决策下,第一个人留到最后的概率。

思路:

首先要观察到这一性质:一号玩家要想取得最终胜利的概率尽可能大,一定要把他安排在最后上场,只打一次。获胜概率与当前擂主以及台下的人有关,所以这个是状态,容易想到需要用二进制表示来压缩状态。

然而想到这些还是不好做,因为如果顺着逻辑正向DP是很困难的,因为每次有输和赢两种走向。因此需要倒着DP。

那么,定义dp[i][sta]:当前存活状态为sta,擂主为i的情况下,一号玩家获胜的最大概率。那么就有了这般转移式:

dp[i][sta] = max{ dp[i][sta], p[i][j] * dp[i][sta^(1<<j)] + p[j][i] * dp[j][sta^(1<<i)] }

这个转移式不是很好理解,想了比较久,觉得这样理解比较好:

对于擂主为i,存活人状态为sta的情况,枚举下一个上台的人j,对于确定的j,状态就有两种走向,i打败j或j打败i。

因此如果我们的决策是指定j上台攻擂,那么上述状态下一号玩家获胜的概率就会等于

pij(i赢j的概率) * dp[i]sta^(1<<j) + pji(i输给j的概率) * dp[j]sta^(1<<i)


因此DP转移的顺序应该是倒着的,对于确定的存活状态,再枚举擂主以及攻擂的人,来贪心出怎么转移过去一号玩家获胜概率最大,那么倒着推到n个人都活着的时候,对擂主i枚举,即可贪出最大概率。

代码:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<iomanip>
#include<vector>
#include<map>
#include<set>
#include<queue>
#include<cstring>
#include<cmath>
#include<functional>
#include<string>
#define dd(x) cout<<#x<<" = "<<x<<" "
#define de(x) cout<<#x<<" = "<<x<<"\n"
#define pb push_back
#define mp make_pair
#define fi first
#define se second
using namespace std;
typedef long long ll;
typedef long double ld;
typedef pair<int,int> P;
typedef priority_queue<int> BQ;
typedef priority_queue<int,vector<int>,greater<int> > SQ;
const int maxn=6e5+10,mod=1e9+7,INF=0x3f3f3f3f;
ld p[20][20];
ld dp[20][maxn];
int main()
{
int n;
cin>>n;
for (int i=0;i<n;++i)
for (int j=0;j<n;++j)
cin>>p[i][j];
dp[0][1]=1;
for (int sta=1;sta<(1<<n);++sta)
{
for (int i=0;i<n;++i)
{
if (!(sta&(1<<i)))
continue;
for (int j=0;j<n;++j)
{
if (i==j||!(sta&(1<<j)))
continue;
dp[i][sta]=max(dp[i][sta], p[i][j]*dp[i][sta^(1<<j)]+p[j][i]*dp[j][sta^(1<<i)]);
}
}
}
ld ans=-1;
for (int i=0;i<n;++i)
ans=max(ans,dp[i][(1<<n)-1]);
cout<<setprecision(10)<<ans;
return 0;
}

Codeforces 678E. Another Sith Tournament(概率DP,状压)的更多相关文章

  1. Educational Codeforces Round 13 E. Another Sith Tournament 概率dp+状压

    题目链接: 题目 E. Another Sith Tournament time limit per test2.5 seconds memory limit per test256 megabyte ...

  2. codeforces 678E Another Sith Tournament 概率dp

    奉上官方题解 然后直接写的记忆化搜索 #include <cstdio> #include <iostream> #include <ctime> #include ...

  3. 20190716NOIP模拟赛T1 礼物(概率dp+状压)

    题目描述 夏川的生日就要到了.作为夏川形式上的男朋友,季堂打算给夏川买一些生 日礼物. 商店里一共有种礼物.夏川每得到一种礼物,就会获得相应喜悦值Wi(每种 礼物的喜悦值不能重复获得). 每次,店员会 ...

  4. Codeforces 678E Another Sith Tournament 状压DP

    题意: 有\(n(n \leq 18)\)个人打擂台赛,编号从\(1\)到\(n\),主角是\(1\)号. 一开始主角先选一个擂主,和一个打擂的人. 两个人之中胜的人留下来当擂主等主角决定下一个人打擂 ...

  5. Codeforces 678E(Another Sith Tournament)

    题目链接:传送门 题目大意:有n个人决斗(n<=18),每两个人之间都有一定几率杀死对方,一次进行一次决斗,胜利者成为擂主继续接受决斗直到只剩下一个人,你是一号,问你最大有多大几率存活到最后. ...

  6. hdu 4336 概率dp + 状压

    hdu 4336 小吃包装袋里面有随机赠送一些有趣的卡片,如今你想收集齐 N 张卡片.每张卡片在食品包装袋里出现的概率是p[i] ( Σp[i] <= 1 ), 问你收集全部卡片所需购买的食品数 ...

  7. HDU4336 Card Collector (概率dp+状压dp)

    http://acm.hdu.edu.cn/showproblem.php?pid=4336 题意:有n种卡片,一个包里会包含至多一张卡片,第i种卡片在某个包中出现的次数为pi,问将所有种类的卡片集齐 ...

  8. SCUT - 254 - 欧洲爆破 - 概率dp - 状压dp

    https://scut.online/p/254 思路很清晰,写起来很恶心. #include<bits/stdc++.h> using namespace std; #define l ...

  9. 【HDU】4352 XHXJ's LIS(数位dp+状压)

    题目 传送门:QWQ 分析 数位dp 状压一下现在的$ O(nlogn) $的$ LIS $的二分数组 数据小,所以更新时直接暴力不用二分了. 代码 #include <bits/stdc++. ...

随机推荐

  1. 转载博客(Django2.0集成xadmin管理后台遇到的错误)

    转载博客地址:https://blog.csdn.net/yuezhuo_752/article/details/87916995 django默认是有一个admin的后台管理模块,但是丑,功能也不齐 ...

  2. 调用打码平台api获取验证码 (C#版)

    一.打码平台很多,这里选择两个:联众和斐斐 联众开发文档: https://www.jsdati.com/docs/guide 斐斐开发文档: http://docs.fateadm.com/web/ ...

  3. js之数据类型(对象类型——单体内置对象——Math)

    Math是一个内置对象,它具有数学常数和函数的属性和方法.Math对象用于执行数学任务,和其它对象不同,Math只是一个静态对象并没有Math()构造函数,实际上,Math()只是一个由js设置的对象 ...

  4. vue中的绑定class和微信小程序中的绑定class的区别

    微信小程序 小程序里面的class与style绑定,遵循HTML特性绑定,有关于HTML绑定.在进行class与style绑定时,可以直接绑定,也可以带上逻辑与,或者三元运算进行条件控制 JS dat ...

  5. C++ STL 之 string

    #include <iostream> #include <string> using namespace std; // 初始化 void test01() { string ...

  6. “最不合格”的SAP应聘者: 从大学生到SAP成都研究院开发工程师

    让我们把时光之轮倒拨回2006年,SAP成都研究院刚刚成立的时候,有一位年轻的电子科技大学研究生,网名雷米兰(这名字一看就是AC米兰铁杆粉丝),加入了SAP成都研究院并被派遣到SAP德国总部进行实习. ...

  7. 【转】在 Delphi 中创建 Linux 守护程序(服务进程)

    转自波哥的译文,必须转过来,太有价值了!原文地址在这里.以下为原文内容: 本文译自 原文链接,语言上做了精炼和排版的变更,以便更简洁明了. Delphi 开始支持 Linux 平台为 Delphi 开 ...

  8. Async 配置线程池

    需要注意一下 ThreadPoolTaskExecutor  和 Executor  区别 @Configuration public class ExecutorConfig { /** Set t ...

  9. web开发:jquery之DOM

    一.文档结构 二.文档操作 三.文档操作案例 四.form表单 五.正则 六.form案例 一.文档结构 ```jsvar $sup = $('.sup');console.log($sup.chil ...

  10. Hadoop_14_MapReduce框架结构及其运行流程

    1.MapReduce原理篇 Mapreduce是一个分布式运算程序的编程框架,是用户开发“基于hadoop的数据分析应用”的核心框架: Mapreduce核心功能是将用户编写的业务逻辑代码和自带默认 ...