51nod 1636 教育改革 | DP
51nod 1636 教育改革 | DP
题面
最近A学校正在实施教育改革。
一个学年由n天组成。A学校有m门课程,每天学生必须学习一门课,一门课程必须在一天内学习完。在学习完第i门课程后,学生们会收到 xi 个家庭作业,其中 xi是区间[ai,bi]里的一个整数 。每门课还有一个属性,就是复杂度 ci 。A学校现在要制他们的课程表,具体要求如下:
·在课程表中,随着天数的增加,课程的复杂度是严格递增的。
·除了第1天,每天的作业量必须是前一天的k倍,或者比前一天多k个作业。(假设第i天的作业量为 xi ,则对于i(1<i≤n)到满足 xi = k+xi−1 或 xi = k·xi−1 );
现在,给定天数n,系数k,和m门课程的ai,bi,ci(1≤i≤m)。要求计算一个学年可以安排最大的总作业量( 总作业量的表达式是∑ni=1xi )是多少。
Input
单组测试数据
第一行,三个由空格隔开的整数n,m,k(1≤n≤m≤50,1≤k≤100),表示一个学年的天数,课程的数量,和作业增量系数。
接下来的m行,
每行有三个整数,ai,bi,ci(1≤ai≤bi≤10^16,bi-ai≤100,1≤ci≤100)
分别表示第i门课程的最小作业量,和最多作业量,以及复杂度。
不同的课程可以有相同的复杂度。课程编号从1到m。
Output
如果有可行方案,第一行输出“YES”(没有引号),第二行输出最大的作业量。
如果没有可行方案,则输出一行“NO”(没有引号)。
题解
这教育改革怎么越改作业越多2333
dp[i][j][k]表示第i天上j课,当天作业量是k的最大答案
——但是这样显然是不行的因为k太大。
好在虽然k大,k与该课程j作业量的左端点的差不会很大。
那么就让dp[i][j][k]表示第i天上j课,当天作业量是a[j]+k(a的意义如题所述)。然后就可以愉快地转移了!
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long ll;
template <class T>
void read(T &x){
char c;
bool op = 0;
while(c = getchar(), c < '0' || c > '9')
if(c == '-') op = 1;
x = c - '0';
while(c = getchar(), c >= '0' && c <= '9')
x = x * 10 + c - '0';
if(op) x = -x;
}
template <class T>
void write(T x){
if(x < 0) putchar('-'), x = -x;
if(x >= 10) write(x / 10);
putchar('0' + x % 10);
}
const int N = 103, M = 203;
int n, m, K;
ll dp[N][N][M], ans;
struct Lesson {
int c;
ll l, r;
bool operator < (const Lesson b) const{
return c < b.c;
}
} a[N];
int main(){
read(n), read(m), read(K);
for(int i = 1; i <= m; i++)
read(a[i].l), read(a[i].r), read(a[i].c);
sort(a + 1, a + m + 1);
memset(dp, -1, sizeof(dp));
for(int j = 1; j <= m; j++)
for(ll k = a[j].l; k <= a[j].r; k++)
dp[1][j][k - a[j].l] = k;
for(int i = 2; i <= n; i++)
for(int j = 1; j <= m; j++)
for(ll k = a[j].l; k <= a[j].r; k++)
for(int h = 1; a[h].c < a[j].c; h++){
if(k >= K){
ll k1 = k - K;
if(k1 >= a[h].l && k1 <= a[h].r && dp[i - 1][h][k1 - a[h].l] != -1)
dp[i][j][k - a[j].l] = max(dp[i][j][k - a[j].l], dp[i - 1][h][k1 - a[h].l] + k);
}
if(k % K == 0){
ll k2 = k / K;
if(k2 >= a[h].l && k2 <= a[h].r && dp[i - 1][h][k2 - a[h].l] != -1)
dp[i][j][k - a[j].l] = max(dp[i][j][k - a[j].l], dp[i - 1][h][k2 - a[h].l] + k);
}
}
for(int j = 1; j <= m; j++)
for(ll k = a[j].l; k <= a[j].r; k++)
ans = max(ans, dp[n][j][k - a[j].l]);
if(ans) puts("YES"), write(ans), putchar('\n');
else puts("NO");
return 0;
}
51nod 1636 教育改革 | DP的更多相关文章
- 51 Nod 1636 教育改革(dp)
1636 教育改革 题目来源: CodeForces 基准时间限制:1 秒 空间限制:131072 KB 分值: 20 难度:3级算法题 收藏 关注 最近A学校正在实施教育改革. 一个学年由n天 ...
- 51nod 1636 教育改革
题目链接 令f[i][j][k]为第i天选择的课程为j,设置作业为a[j]+k时的最大作业量. 那么f[i][j][k]可以由哪些状态转移而来?先把课程按复杂度排序,那么可以转移来的课程是f[i-1] ...
- 51nod 1636
1636 教育改革 我看过题解了还下了数据,表示很惭愧不想说什么,但还是说两句吧 sol: 因为差值很小只有100,所以对数组下标存的是(选择的数值和左端点的差值) f[i][j][k]即为第i天选了 ...
- 51nod 1353 树 | 树形DP经典题!
51nod 1353 树 | 树形DP好题! 题面 切断一棵树的任意条边,这棵树会变成一棵森林. 现要求森林中每棵树的节点个数不小于k,求有多少种切法. 数据范围:\(n \le 2000\). 题解 ...
- 51nod 1021 石子归并(dp)
51nod 1021 石子归并 题解:从i到j合并的最小值:dp[i][j] = min(dp[i][j], dp[i][k] + dp[k+1][j] + sum[j] - sum[i-1]); 最 ...
- 51nod 1183 - 编辑距离 - [简单DP][编辑距离问题][Levenshtein距离问题]
题目链接:https://www.51nod.com/onlineJudge/questionCode.html#!problemId=1183 编辑距离,又称Levenshtein距离(也叫做Edi ...
- 51nod 1406 位运算/dp
http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1406 1406 与查询 题目来源: CodeForces 基准时间限制: ...
- 51NOD 1202 子序列个数 DP
http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1202&judgeId=225600 这题看起来挺复杂,但是真正的 ...
- 51Nod 1327 棋盘游戏 —— 延迟DP
题目:http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1327 看博客:https://www.cnblogs.com/Na ...
随机推荐
- LintCode——颜色分类
颜色分类:给定一个包含红,白,蓝且长度为 n 的数组,将数组元素进行分类使相同颜色的元素相邻,并按照红.白.蓝的顺序进行排序. 我们可以使用整数 0,1 和 2 分别代表红,白,蓝. 注意事项: 不能 ...
- Ubuntu16.04安装搜狗拼音输入法
为了让自己的电脑相对安全一些,我安装了ubuntu的物理机 因为要经常输入汉字,我就在unbuntu里面安装了搜狗输入法 1.在搜狗输入法官网下载Linux版本的安装包:https://pinyin. ...
- ifup,ifdown命令详解
基础命令学习目录首页 原文链接:https://www.cnblogs.com/jing99/p/7881779.html ifup命令网络配置 ifup命令用于激活指定的网络接口.ifdown命令用 ...
- Python图形界面开发—wxPython库的布局管理及页面切换
前言 wxPython是基于Python的跨平台GUI扩展库,对wxWidgets( C++ 编写)封装实现.GUI程序的开发中界面布局是很重要的一个部分,合理的页面布局能够给予用户良好使用体验.虽然 ...
- python循环综合运用
循环很重要,计算机很蠢,唯一的优势就是按照指令不停的执行,所以决定在说一下. break语句,用在循环体中,迫使循环立即终止,即跳出所在循环体,继续执行循环体后面的语句. sum=0 i=1 whil ...
- OGG 跳过事务(转)
http://blog.chinaunix.net/uid-26190993-id-3434074.html 在OGG运行过程中,通常会因为各种各样的原因导致容灾端的REPLICAT进程ABEN ...
- Node.js中module文件定义的top-level变量为何是私有的
在Node.js中,module文件里面使用var,const或者let定义的top-level变量为何是私有的,只能在这个模块文件中使用呢? 原因就是,在模块文件中的内容执行之前,node.js会降 ...
- 【Alpha发布】贡献分分配
最后贡献分分配: (1211)王嘉豪:32 (1186)黄雨萌:36 (1182)佘彦廷:40 (1208)何小松:50 (1200)鲁聃:62 (1174)邢浩:64 (1193)刘乾:66
- java语言复制数组的四种方法
JAVA语言的下面几种数组复制方法中,哪个效率最高? B.效率:System.arraycopy > clone > Arrays.copyOf > for循环 1.System.a ...
- 《构建之法》第四&十七章读书笔记
<构建之法>第四&十七章读书笔记 一. 前言 再次阅读<构建之法>,愈发被其中生动有趣的举例吸引.作为一本给予软件工程学生的书籍,其不以枯燥的理论知识 ...