题目:(转自 https://www.luogu.com.cn/problem/P1541

题目描述

乌龟棋的棋盘是一行NN个格子,每个格子上一个分数(非负整数)。棋盘第1格是唯一的起点,第NN格是终点,游戏要求玩家控制一个乌龟棋子从起点出发走到终点。

乌龟棋中MM张爬行卡片,分成4种不同的类型(MM张卡片中不一定包含所有44种类型的卡片,见样例),每种类型的卡片上分别标有1,2,3,41,2,3,4四个数字之一,表示使用这种卡片后,乌龟棋子将向前爬行相应的格子数。游戏中,玩家每次需要从所有的爬行卡片中选择一张之前没有使用过的爬行卡片,控制乌龟棋子前进相应的格子数,每张卡片只能使用一次。

游戏中,乌龟棋子自动获得起点格子的分数,并且在后续的爬行中每到达一个格子,就得到该格子相应的分数。玩家最终游戏得分就是乌龟棋子从起点到终点过程中到过的所有格子的分数总和。

很明显,用不同的爬行卡片使用顺序会使得最终游戏的得分不同,小明想要找到一种卡片使用顺序使得最终游戏得分最多。

现在,告诉你棋盘上每个格子的分数和所有的爬行卡片,你能告诉小明,他最多能得到多少分吗?

输入格式

每行中两个数之间用一个空格隔开。

第11行22个正整数N,MN,M,分别表示棋盘格子数和爬行卡片数。

第22行NN个非负整数,a_1,a_2,…,a_Na1​,a2​,…,aN​,其中a_iai​表示棋盘第ii个格子上的分数。

第33行MM个整数,b_1,b_2,…,b_Mb1​,b2​,…,bM​,表示M张爬行卡片上的数字。

输入数据保证到达终点时刚好用光MM张爬行卡片。

输出格式

11个整数,表示小明最多能得到的分数。

输入输出样例
输入 #1复制

9 5
6 10 14 2 8 8 18 5 17
1 3 1 2 1
输出 #1复制

73
说明/提示

每个测试点1s1s

小明使用爬行卡片顺序为1,1,3,1,2

1,1,3,1,2,得到的分数为6+10+14+8+18+17=736+10+14+8+18+17=73。注意,由于起点是11,所以自动获得第11格的分数66。

对于30\%30%的数据有1≤N≤30,1≤M≤121≤N≤30,1≤M≤12。

对于50\%50%的数据有1≤N≤120,1≤M≤501≤N≤120,1≤M≤50,且44种爬行卡片,每种卡片的张数不会超过2020。

对于100\%100%的数据有1≤N≤350,1≤M≤1201≤N≤350,1≤M≤120,且44种爬行卡片,每种卡片的张数不会超过4040;0≤a[i]≤100,1≤i≤N,1≤b[i]≤4,1≤i≤M0≤ai​≤100,1≤i≤N,1≤b[i]≤4,1≤i≤M。

很明显,暴力dfs是一个不错的选择,如若是在考试,天梦在这里奉告读者结合实际情况打暴力。但由于是一道dp,我们今天就讲讲正解。

思路:

在做这道题时,我首先这样想:把起始点标注成s和t,在中间找一点i保证 f[s][i] 和 f[i][t] 最优,通过 f[i][j]=f[s][i]+f[i][t]这个式子来让f[s][t]最优,但可以很快证明这个想法是错误的,因为设我们能用的总牌数为K,

前一段(即f[s][i])为了得到最优解会用a张牌,后一段(即f[i][t])为了得到最优解会用b张牌,无法保证a+b=K。

除了枚举分段点,我们还能枚举什么? 用的牌数。接下来我来给大家做简单介绍。

介绍:

设f[i][j][p][k]表示用了i张走一步的牌(下面简写),j张2,p张3,k张4,则我们理想的最优解应该是他走到终点时,即所有牌都用完时。我们以样例为例:f【3】【1】【1】【0】为我们所求的最优解,因为上一步可能走了1格,2格,3格,4格(由于题目限制,4在样例中牌数为0)

那么最优解可以由f[2][1][1][0],f[3][0][1][0],f[3][1][0][0] 得到

一般的f[i][j][k][p]可以由f[i-1][j][k][p], f[i][j-1][k][p], f[i][j][k-1][p], f[i][j][k][p-1]得到,如果读者接着往上推(试试推推样例) 会发现最终的最优解都是由f[0][0][0][0]得到的,它的值是什么?一格都没走——起点值。

下面,让我们来看看代码:

代码:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<queue>
#include<vector>
#define N 400
#define ll long long
using namespace std;
int n,m;
int a[N];
int sum[];
int f[][][][];
int main()
{
cin>>n>>m;
for(int i=;i<=n;i++)
{
cin>>a[i];
}
for(int i=;i<=m;i++)
{
int x;
cin>>x;
sum[x]++;
}//计算牌数
//memset(f,0,sizeof(f));
f[][][][]=a[];
//cout<<sum[1]<<" "<<sum[2]<<" "<<sum[3]<<" "<<sum[4]<<endl<<endl;
for(int i=;i<=sum[];i++)
{
for(int j=;j<=sum[];j++)
{
for(int k=;k<=sum[];k++)
{
for(int p=;p<=sum[];p++)
{
if(!(i==&&j==&&k==&&p==))
{
int ans1,ans2,ans3,ans4;
if(i-<) ans1=; else ans1=f[i-][j][k][p];
if(j-<) ans2=; else ans2=f[i][j-][k][p];
if(k-<) ans3=; else ans3=f[i][j][k-][p];
if(p-<) ans4=; else ans4=f[i][j][k][p-];//防止数组下溢
f[i][j][k][p]=max(max(ans1,ans2),max(ans3,ans4))+a[i*+j*+k*+p*+];//加上这个位置的格子值,别忘了加1
}
}
}
}
}
cout<<f[sum[]][sum[]][sum[]][sum[]];
return ;
}

dp——洛谷 P1541 乌龟棋 —— by hyl天梦的更多相关文章

  1. 洛谷 p1541乌龟棋

    洛谷 p1541乌龟棋 题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行NN个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第NN格是终点,游戏 ...

  2. 洛谷P1541 乌龟棋(四维DP)

    To 洛谷.1541 乌龟棋 题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行N个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第N格是终点,游 ...

  3. 洛谷P1541 乌龟棋 [2010NOIP提高组]

    P1541 乌龟棋 题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行N个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第N格是终点,游戏要求玩家 ...

  4. codevs1068 乌龟棋==洛谷P1541 乌龟棋

    P1541 乌龟棋 题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行N个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第N格是终点,游戏要求玩家 ...

  5. 洛谷 P1541 乌龟棋 Label:O(n^4)的dp

    题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行N个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第N格是终点,游戏要求玩家控制一个乌龟棋子从起 ...

  6. [洛谷P1541] 乌龟棋

    洛谷题目链接:乌龟棋 题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行N个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第N格是终点,游戏要求玩 ...

  7. [NOIP2010] 提高组 洛谷P1541 乌龟棋

    题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行N个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第N格是终点,游戏要求玩家控制一个乌龟棋子从起 ...

  8. 洛谷 P1541 乌龟棋

    题目背景 小明过生日的时候,爸爸送给他一副乌龟棋当作礼物. 题目描述 乌龟棋的棋盘是一行N个格子,每个格子上一个分数(非负整数).棋盘第1格是唯一的起点,第N格是终点,游戏要求玩家控制一个乌龟棋子从起 ...

  9. 洛谷 P1541 乌龟棋 —— DP

    题目:https://www.luogu.org/problemnew/show/P1541 DP. 代码如下: #include<iostream> #include<cstdio ...

随机推荐

  1. win10 uwp 使用 Microsoft.Graph 发送邮件

    在 2018 年 10 月 13 号参加了 张队长 的 Office 365 训练营 学习如何开发 Office 365 插件和 OAuth 2.0 开发,于是我就使用 UWP 尝试使用 Micros ...

  2. The Function() Constructor

    Functions are usually defined using the function keyword, either in the form of a function definitio ...

  3. linux 使用 gdb

    gdb 对于看系统内部是非常有用. 在这个级别精通调试器的使用要求对 gdb 命令有信心, 需要理解目标平台的汇编代码, 以及对应源码和优化的汇编码的能力. 调试器必须把内核作为一个应用程序来调用. ...

  4. js的cookie操作及知识点详解

    <html> <head> <script type="text/javascript"> function getCookie(c_name) ...

  5. 复盘:错误理解zuul路径匹配,无法使用zuul

    场景: 项目中用到zuul时,配置url总是有问题,无法路由到对应微服务. 配置如下: zuul: routes: m2-member: path: /member/* serviceId: m2-m ...

  6. KAFKA报错:COMMIT CANNOT BE COMPLETED SINCE THE GROUP HAS ALREADY REBALANCED AND ASSIGNED THE PARTITIONS TO ANOTHER MEMBER

    转载:https://www.greenhtml.com/archives/Commit-cannot-be-completed-since-the-group-has-already-rebalan ...

  7. 异步加载css 和 谷歌浏览器各实用小工具介绍

    异步加载css资源 加开页面首屏显示速度使我们前端一直在追求的目标,而css资源在这些优化中同样也是不可或缺的. 一个网站可能有一部分css资源是必须的,他需要在页面渲染完之前就被加载完,并和html ...

  8. vue文章学习路线

    vue学习笔记(一)入门 Vue实现简单的购物车功能 vue学习笔记(二)vue的生命周期和钩子函数 使用webstorm搭建vue-cli项目 vue-cli项目中引入第三方插件 vue-cli项目 ...

  9. 机器学习回顾篇(12):集成学习之Bagging与随机森林

    .caret, .dropup > .btn > .caret { border-top-color: #000 !important; } .label { border: 1px so ...

  10. lintcode入门37-算法实现

    lintcode入门级算法题37 一.题目 反转一个3位整数 反转一个只有3位数的整数. 样例          样例 1: 输入: number = 123 输出: 321         样例 2 ...