首页 > 其他分享 >[ABC303G] Bags Game 解题分析

[ABC303G] Bags Game 解题分析

时间:2023-06-12 12:45:13浏览次数:30  
标签:Bags leq sum 物品 Game ABC303G mathcal 取出 DP

1 题目大意

1.1 题目翻译

有两个人轮流取物品。总共有 \(n\) 个物品,第 \(i\) 个物品的价值为 \(w_i\)。

他们按照下面的其中一种方式取物品:

  • 取出这一排物品最前面的或者最后面的。这一步没有代价。

  • 设还剩下 \(m\) 个物品,那么重复取出 \(\min(B, m)\) 个物品,每次取出最前面的或者最后面的。这一步的代价为 \(A\)。

  • 设还剩下 \(m\) 个物品,那么重复取出 \(\min(D, m)\) 个物品,每次取出最前面的或者最后面的。这一步的代价为 \(B\)。

最后一个人取出物品的价值为所有他取出物品价值之和减去他所花费的代价。问当两人均以最优策略取物品时,先手取出物品的价值减去后手取出物品的价值为多少。

1.2 数据范围

对于 \(100\%\) 的数据:

  • \(1 \leq B, D \leq n \leq 3000\)

  • \(A, C \leq 10 ^ 9\)

2 解法分析

2.1 初见此题

首先,一看这道题,我们就会发现:不管怎么取物品,任何时刻的序列一定是原序列的一段连续子区间。所以,我们不难想到区间 DP。

2.2 暴力 DP

设 \(f_{i, j}\) 表示当前序列为原序列从第 \(i\) 个到第 \(j\) 个元素时,答案的最大值。那么,会有 \(3\) 种情况:

  • 操作 1。此时,\(f_{i,j} = \max(w_i - f_{i + 1, j}, w_j - f_{i, j - 1})\)

  • 操作 2。设 \(l = j - i + 1\),则:

    • 当 \(B \geq l\) 时:

    \[f_{i, j} = (\sum_{i \leq k \leq j}w_k) - A \]

    • 当 \(B < l\) 时:

    \[f_{i, j} = \max_{0 \leq k \leq l}\{(\sum_{i \leq p \leq i + k - 1} w_p) + (\sum_{j - B + k + 1 \leq p \leq j}w_p) - C - f_{i + k, j - B + k}\} \]

  • 操作 3。大致与操作 2 相同,这里就不过多叙述。

至此,我们完成了暴力 DP,时间复杂度为 \(\mathcal{O}(n^3)\),显然过不了。

所以,接下来,我们就要考虑优化。

2.3 DP 优化

观察 DP 方程。我们发现,极限复杂度只出现在了操作 2 当 \(B < l\) 的情况。所以,我们把这个式子的 \(\max\) 去掉,得:

\[(\sum_{i \leq p \leq i + k - 1} w_p) + (\sum_{j - B + k + 1 \leq p \leq j}w_p) - C - f_{i + k, j - B + k} \]

我们发现,\((\sum_{i \leq p \leq i + k - 1} w_p) + (\sum_{j - B + k + 1 \leq p \leq j}w_p)\) 可以前缀和 \(\mathcal{O}(1)\) 计算。设 \(s_{l, r}\) 为 \(l\) 到 \(r\) 的物品价值之和,于是得:

\[- s_{i + k, j - B + k} - f_{i + k, j - B + k} - C + s_{i, j} \]

观察这个方程。我们把 \(k\) 视为未知数,\(i, j\) 视为常数,则 \(s_{i,j} - C\) 为常数,可以提到 \(\max\) 外面。所以,我们需要维护的只有:

\[s_{i + k, j - B + k} + f_{i + k, j - B + k} \]

发现这两个区间的长度都是 \((j - B + k) - (i + k) = j - i - B\),那么相当于只需要维护长度为 \(x\) 的 \(f_{i, i + x - 1} + s_{i, i + x - 1}\) 中最小的一个即可。

这有许多维护方法,比如优先队列,线段树,ST 表。

至此,这道题就完成了。时间复杂度为 \(\mathcal{O}(n^2)\) 或者 \(\mathcal{O}(n^2\log{n})\)

标签:Bags,leq,sum,物品,Game,ABC303G,mathcal,取出,DP
From: https://www.cnblogs.com/yh2021shx/p/17474719.html

相关文章

  • 【每日一题】Problem 327A - Flipping Game
    原题解决思路计算数字"1"的最大数目,可以转换成计算数组最大和,即求\(maxSum(oldArraySum-(1\rightarrow0)+(0\rightarrow1))\RightarrowoldArraySum+maxSum(flipSum)\)误区注意:题目要求必须执行一次,因此起始值不是0而是-1#include<bits/stdc++.h>intm......
  • 基于Python+tkinter+pygame的音乐播放器完整源码
    importosimporttkinterimporttkinter.filedialogimportrandomimporttimeimportthreadingimportpygamefolder=''defplay():#folder用来表示存放MP3音乐文件的文件夹globalfoldermusics=[folder+'\\'+musicfo......
  • [ABC166F] Three Variables Game
    ThreeVariablesGameの传送门Solution首先,我们每次操作只会修改两个数。所以考虑dfs枚举操作的顺序,但是这让时间复杂度变为\(O(2^n)\),不能接受。但是,我们可以判断当a<0||b<0||c<0时,就退出,这样可以减少绝大部分状态。边界条件:当枚玩\(n\)个后,输出用\(ans......
  • GameHub项目开发笔记
    技术栈搭建项目项目在HbuilderX中进行开发,新建时使用默认模板,选择Vue2版本,并且启用uniCloud(阿里云)项目代码托管到GitHub,.gitignore文件配置如下#/test/表示忽略根目录下的test目录及其所有内容。/uniCloud-aliyun//.hbuilderx//uni_modules//unpackage/学习参考:https:/......
  • [ABC201D] Game in Momotetsu World 题解
    GameinMomotetsuWorld题目大意在一个\(n\timesm\)的网格中,存在红色和蓝色两种格子,红色格子用-表示,蓝色格子用+表示。现在Takahashi和Aoki要在这个网格中进行游戏,游戏的规则如下:初始时,有一枚棋子摆放在左上角,即\((1,1)\)的位置。两名玩家的分数均为\(0\)。......
  • AtCoder Beginner Contest 258 G Grid Card Game
    洛谷传送门AtCoder传送门记\(b_i=\sum\limits_{j=1}^ma_{i,j},c_j=\sum\limits_{i=1}^na_{i,j}\)。首先考虑这样一个事情,就是对于\(b_i\le0\)的行有没有可能被选。如果选了它:如果没有选任何列,选这一行肯定不优;如果选了若干列,根据题目的要求,这若干列与这......
  • pygame-04加载人物图片与显示
    1-实例代码importmath,randomimportpygamefrompygameimportmixer#游戏初始化pygame.init()#窗口设置screen=pygame.display.set_mode((800,600))#背景设置background=pygame.image.load('background.png')#背景音乐,-1表示循环播放mixer.music.load(......
  • pygame-03游戏界面等环境配置
    1-示例代码importmath,randomimportpygamefrompygameimportmixer#游戏初始化pygame.init()#窗口设置screen=pygame.display.set_mode((800,600))#背景设置background=pygame.image.load('background.png')#背景音乐,-1表示循环播放mixer.music.load(......
  • Pygame制作答题类游戏的实现
    概述个人比较喜欢玩这些答题类的游戏,在这类的游戏中其实存在着一些冷知识在里面。练习pygame的过程中,在网络上搜索,几乎没有找到这类游戏的示例教程,就蒙生了制作一个答题游戏的念头,最开始的时候,这个游戏是使用键盘输入的方式来答题的,没有开始界面,没有结束界面,后来几经修改,改为全鼠标......
  • 【虚幻引擎】UE4源码解析FWorldContent、UWorld、ULevel、UGameInstance、UEngine
    一、UEngineEngine,因为也是很基础的类,再加上开发过程中会经常访问到该类型,因此UE4引擎也在代码全局范围内定义了一个该类型的全局变量:UEngine*GEngine供开发者直接调用。该最基础的类型分化成了两个子类:UGameEngine和UEditorEngine。UGameEngine保存了唯一的一个UGameInstan......