【DP】【期望】$P1850$换教室

【DP】【期望】\(P1850\)换教室

链接

题目描述

\(2n\) 节课程安排在$ n$ 个时间段上。在第 \(i\)\(1 \leq i \leq n\))个时间段上,两节内容相同的课程同时在不同的地点进行,其中,牛牛预先被安排在教室 \(c_i\)上课,而另一节课程在教室 \(d_i\)进行。

在不提交任何申请的情况下,学生们需要按时间段的顺序依次完成所有的 \(n\)节安排好的课程。如果学生想更换第 \(i\)节课程的教室,则需要提出申请。若申请通过,学生就可以在第 $i $个时间段去教室 \(d_i\) 上课,否则仍然在教室 \(c_i\)上课。

牛牛发现申请更换第\(i\)节课程的教室时,申请被通过的概率是一个已知的实数 \(k_i\),并且对于不同课程的申请,被通过的概率是互相独立的。

所有的申请只能一次性提交,并且每个人只能选择至多 \(m\)节课程进行申请。

牛牛所在的大学有 \(v\)个教室,有 \(e\) 条道路。每条道路连接两间教室,并且是可以双向通行的。由于道路的长度和拥堵程度不同,通过不同的道路耗费的体力可能会有所不同。 当第 \(i\)\(1 \leq i \leq n-1\))节课结束后,牛牛就会从这节课的教室出发,选择一条耗费体力最少的路径前往下一节课的教室。

现在牛牛想知道,申请哪几门课程可以使他因在教室间移动耗费的体力值的总和的期望值最小。

输入格式

第一行四个整数 \(n,m,v,e\)

第二行 \(n\) 个正整数,第 \(i\)\(1 \leq i \leq n\))个正整数表示 c\(c_i\),即第\(i\)个时间段牛牛被安排上课的教室;保证 \(1 \le c_i \le v\)

第三行 \(n\) 个正整数,第 \(i\)\(1 \leq i \leq n\))个正整数表示 \(d_i\),即第 $i $个时间段另一间上同样课程的教室;保证 \(1 \le d_i \le v\)

第四行 \(n\) 个实数,第 \(i\)\(1 \leq i \leq n\))个实数表示 \(k_i\),即牛牛申请在第 \(i\)个时间段更换教室获得通过的概率。保证 \(0 \le k_i \le 1\)

接下来 \(e\) 行,每行三个正整数 \(a_j, b_j, w_j\),表示有一条双向道路连接教室 \(a_j, b_j\),通过这条道路需要耗费的体力值是 \(w_j\);保证 \(1 \le a_j, b_j \le v\)\(1 \le w_j \le 100\)

保证 \(1 \leq n \leq 2000\)\(0 \leq m \leq 2000\)\(1 \leq v \leq 300\)\(0 \leq e \leq 90000\)

保证通过学校里的道路,从任何一间教室出发,都能到达其他所有的教室。

保证输入的实数最多包含 \(3\)位小数。

输出格式

输出一行,包含一个实数,四舍五入精确到小数点后恰好\(2\)位,表示答案。你的输出必须和标准输出完全一样才算正确。

测试数据保证四舍五入后的答案和准确答案的差的绝对值不大于 \(4 \times 10^{-3}\)。 (如果你不知道什么是浮点误差,这段话可以理解为:对于大多数的算法,你可以正常地使用浮点数类型而不用对它进行特殊的处理)

样例

3 2 3 3
2 1 2
1 2 1
0.8 0.2 0.5 
1 2 5
1 3 3
2 3 1
2.80

提示

  1. 道路中可能会有多条双向道路连接相同的两间教室。 也有可能有道路两端连接的是同一间教室。
  2. 请注意区分\(n,m,v,e\)的意义, \(n\)不是教室的数量, \(m\)不是道路的数量。

\(Solution\)

考虑DP。状态怎么设?显然第几节课需要在状态里。还要保证最多换\(m\)次,因此次数也要在状态里。那么,怎么从上一节课转移呢?显然如果我们不知道上一节课在哪个教室上的,就无法转移。因此,还要在加一维,记录当前是否申请换教室。

因此,状态就是\(f[i][j][k], 1 \leq i \leq n, 0 \leq j \leq m, 0 \leq k \leq 1\),表示前\(i\)节课,换了\(j\)次教室,第\(i\)次换或不换的期望。

至于转移则比较简单了

f[i][j][0] = min(f[i - 1][j][0] + w[c[i]][c[i - 1]], f[i - 1][j][1] + w[c[i]][d[i - 1]] * k[i - 1] + w[c[i]][c[i - 1]] * (1 - k[i - 1]));
f[i][j][1] = min(f[i - 1][j - 1][0] + w[c[i]][c[i - 1]] * (1 - k[i]) + w[d[i]][c[i - 1]] * k[i],f[i - 1][j - 1][1] + w[d[i]][d[i - 1]] * k[i - 1] * k[i] + w[c[i]][c[i - 1]] * (1 - k[i - 1]) * (1 - k[i])+ w[c[i - 1]][d[i]] * (1 - k[i - 1]) * k[i]+ w[d[i - 1]][c[i]] * k[i - 1] * (1 - k[i]));

如图为当前不选择换教室

2

如图为当前选择换教室

这道题还有几点需要主意的,在预处理部分。具体看代码

#include <iostream>
#include <cstring>
#include <cstdio>
using namespace std;
long long read(){long long x = 0; int f = 0; char c = getchar();while(c < '0' || c > '9') f |= c == '-', c = getchar();while(c >= '0' && c <= '9') x = (x << 3) + (x << 1) + (c ^ 48), c = getchar();return f? -x:x;
}int n, m, V, E, c[2002], d[2002], w[305][305];
double f[2002][2002][2], k[2002], ans;
int main(){memset(w, 63, sizeof w);//距离初始化n = read(); m = read(); V = read(); E = read();for(int i = 1; i <= n; ++i) c[i] = read();for(int i = 1; i <= n; ++i) d[i] = read();for(int i = 1; i <= n; ++i) scanf("%lf", &k[i]);for(int i = 1; i <= E; ++i){int x = read(), y = read(), z = read();w[x][y] = w[y][x] = min(w[x][y], z);//有可能重边}for(int l = 1; l <= V; ++l)for(int i = 1; i <= V; ++i)for(int j = 1; j <= V; ++j)w[i][j] = min(w[i][j], w[i][l] + w[l][j]);//floyed最短路for(int i = 1; i <= V; ++i) w[i][i] = w[i][0] = w[0][i] = 0;//初始化for(int i = 1; i <= n; ++i) f[i][0][0] = f[i - 1][0][0] + w[c[i]][c[i - 1]], f[i][0][1] = 1e9;//初始化,处理一个也不申请的情况for(int i = 1; i <= n; ++i)for(int j = 1; j <= m; ++j){f[i][j][0] = min(f[i - 1][j][0] + w[c[i]][c[i - 1]], f[i - 1][j][1] + w[c[i]][d[i - 1]] * k[i - 1] + w[c[i]][c[i - 1]] * (1 - k[i - 1]));f[i][j][1] = min(f[i - 1][j - 1][0] + w[c[i]][c[i - 1]] * (1 - k[i]) + w[d[i]][c[i - 1]] * k[i],f[i - 1][j - 1][1] + w[d[i]][d[i - 1]] * k[i - 1] * k[i] + w[c[i]][c[i - 1]] * (1 - k[i - 1]) * (1 - k[i])+ w[c[i - 1]][d[i]] * (1 - k[i - 1]) * k[i]+ w[d[i - 1]][c[i]] * k[i - 1] * (1 - k[i]));}double ans = f[n][0][0];for(int i = 1; i <= m; ++i) ans = min(ans, min(f[n][i][1], f[n][i][0]));//更新答案printf("%.2lf", ans);return 0;
} 

转载于:https://www.cnblogs.com/kylinbalck/p/11258482.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/363383.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

封装cookie设置和获取的简易方法

(function() {var tool {expires: "expires", // 过期时间expirespath: "path", // 路径domain: "domain", // 域secure: "secure" // 安全设置 bool};//设置function setCookie(k, v, options) {if (!options) {document.cookie k…

高并发服务器逻辑处理瓶颈,如何解决?

https://mp.weixin.qq.com/s/GHHHvgURdZpNJ1Ec6RHgPg 高并发衡量指标 响应时间&#xff1a;系统对请求做出响应的时间&#xff0c;即一个http请求返回所用的时间&#xff1b;吞吐量&#xff1a;单位时间内处理的请求数量&#xff1b;QPS&#xff08;TPS&#xff09;&#xff1a…

Oracle学习笔记:blank_trimming的含义

blank_trimming 静态初始化参数控制 【字符串的尾随空格】是否自动截断&#xff01;以便【字符类型】的 【列】或【变量】之间在运算时不用考虑尾随空格的长度&#xff01;这样就和sql-92的标准兼容了 例子&#xff1a; DECLARE v_char1 VARCHAR2(2); v_char2 VARCHAR2(…

InterruptedException和中断线程的说明

如果没有将InterruptedException检查为异常&#xff0c;则可能甚至没人会注意到它-这实际上可以防止这些年来的几个错误。 但是由于必须对其进行处理&#xff0c;因此许多人不正确或不加考虑地处理它。 让我们以一个线程的简单示例为例&#xff0c;该线程定期进行一些清理&…

映射网络驱动器会自动断开的解决方法

映射的网络驱动器在一段时间自动断开&#xff0c;是由于服务器服务自动断开连接功能的默认超时期限造成的&#xff0c;我们可以通过以下两种方法来更改断开时间&#xff1a; 方法一&#xff1a;修改注册表编辑相应的键值来增加默认超时期限在注册表中找到下面的注册表项&#x…

一行上自动控制数据长度,并换行

有的在开发中&#xff0c;遇到传来的数据太长&#xff0c;渲染到页面上会超出可视页面&#xff0c;出现横向滚动条&#xff0c;想解决一个办法就是数据到一定程度换行。 div{word-wrap: break-word;word-break: break-all;width:90%; /*可以根据情况调整*/ } 更多专业前端知识…

springboot(十)-监控应用

微服务的特点决定了功能模块的部署是分布式的&#xff0c;大部分功能模块都是运行在不同的机器上&#xff0c;彼此通过服务调用进行交互&#xff0c;前后台的业务流会经过很多个微服务的处理和传递&#xff0c;出现了异常如何快速定位是哪个环节出现了问题&#xff1f; 在这种框…

【概率DP】$P2059$ 卡牌游戏

【概率DP】P2059 卡牌游戏 链接 题目描述 N个人坐成一圈玩游戏。一开始我们把所有玩家按顺时针从1到N编号。首先第一回合是玩家1作为庄家。每个回合庄家都会随机&#xff08;即按相等的概率&#xff09;从卡牌堆里选择一张卡片&#xff0c;假设卡片上的数字为X&#xff0c;则庄…

基于角色的访问控制'的权限管理的数据库的设计实现

RBAC基于角色的访问控制的权限管理系统数据库设计与实现 use [master] go -- 检查数据库 [RBAC]是否存在,如果存在则删除(只测试用,不然会丢数据.) -- Search from the sysdatabase to see that if the [RBAC] database exist. -- If exists then drop it else create it. if…

Thymeleaf –片段和angularjs路由器局部视图

百里香叶许多很酷的功能之一就是能够渲染模板片段–我发现这是与AngularJs一起使用的特别有用的功能。 可以将AngularJS $ routeProvider或AngularUI路由器配置为返回不同“路径”的部分视图&#xff0c;使用百里香叶返回这些部分视图确实效果很好。 考虑一个简单的CRUD流&am…

web3.js_1.x.x--API(一)event/Constant/deploy/options

/* 事件是使用EVM日志内置功能的方便工具&#xff0c;在DAPP的接口中&#xff0c;它可以反过来调用Javascript的监听事件的回调。事件在合约中可被继承。当被调用时&#xff0c;会触发参数存储到交易的日志中&#xff08;一种区块链上的特殊数据结构&#xff09;。 这些日志与合…

1022: 淘金(2017年中南大学研究生复试机试题 )

1022: 淘金 时间限制: 1 Sec 内存限制: 128 MB提交: 205 解决: 75[提交] [状态] [讨论版] [命题人:外部导入]题目描述 在一片n*m的土地上&#xff0c;每一块1*1的区域里都有一定数量的金子。这一天&#xff0c;你到这里来淘金&#xff0c;然而当地人告诉你&#xff0c;如果你…

CSS 定位 四种定位

absolute 生成绝对定位的元素&#xff0c;相对于static定位以外的第一个父元素进行定位。元素的位置通过“left”&#xff0c;“top”&#xff0c;“right”以及“bottom”属性进行定位。fixed 生成固定定位的元素&#xff0c;相对于浏览器窗口进行定位。元素的位置通过“left…

Apache CXF 3.0:CDI 1.1支持可替代Spring

在几周前刚刚发布Apache CXF 3.0时 &#xff0c;该项目又迈出了满足JAX-RS 2.0规范要求的又一个重要步骤&#xff1a;与CDI 1.1集成。 在此博客文章中&#xff0c;我们将看几个有关Apache CXF 3.0和Apache CXF 3.0如何协同工作的示例。 从3.0版开始&#xff0c; Apache CXF包含…

用堆来求中位数

维护一个大根堆和一个小根堆。使得大根堆堆顶&#xff08;最大的元素&#xff09;比小根堆堆顶&#xff08;最小的元素&#xff09;小&#xff0c;且两个堆的元素个数的差小于等于1。这样元素多的那个堆的堆顶就是已读入数的中位数。如果读入偶数个数&#xff0c;则中位数为两个…

JPA 2.1类型转换器–保留枚举的更好方法

可以使用JPA 2.0保留枚举&#xff0c;但是没有很好的方法来实现。 使用Enumerated批注&#xff0c;可以使用EnumType.ORDINAL或EnumType.STRING将枚举值映射到其数据库表示形式。 但是这两种选择都有一些缺点&#xff0c;我们将在本文的第一部分中进行讨论。 在第二部分中&…

LOADRUNNER8.1中文版加10000客户端破解补订

http://www.17testing.com/download/LR_8.1.iso LOADRUNNER8.1 用迅雷下载http://www.17testing.com/download/LR_8.1ChinesePack.iso 中文包http://blog.chinaunix.net/upfile/070509151030.rar 10000客户端的破解补丁 LR 8.1的介质可以从这里下载&#xff1a;http://www.17t…

css布局笔记(二)Flex

flex Flex是“Flexible Box”的缩写&#xff0c;意为“弹性布局”&#xff0c;用来为盒状模型提供最大的灵活性。 任何一个容器都可指定为Flex布局。 .box{display:flex;} 行内元素也可以使用flex布局。 .box{display:inline-flex;} webkit内核的浏览器&#xff0c;必须加上-w…

BZOJ3709 Bohater 贪心

传送门 思路很妙…… 有个前提条件&#xff1a;血量无限&#xff0c;这样话肯定先打会回血的怪&#xff0c;再打会掉血的怪 对于会回血的怪&#xff0c;按照受到伤害的顺序从小往大打 对于会掉血的怪似乎并不是很好搞&#xff0c;考虑&#xff1a;将每一时刻的血量函数画出来&a…

反射与二次加工标准类型

反射与二次加工标准类型一、反射 反射主要是指程序可以访问、检测和修改它本身状态或行为的一种能力。 有四个可以实现自省(反射)的函数&#xff0c;如下表所示&#xff1a; 函数名含义hasattr(object,name)判断object中有没有一个name字符串对应的方法或属性getattr(object,na…