首页 > 其他分享 >P2893 [USACO08FEB] Making the Grade G 题目分析

P2893 [USACO08FEB] Making the Grade G 题目分析

时间:2024-11-10 19:57:59浏览次数:1  
标签:题目 Grade leq num mathcal USACO08FEB Making include 单调

P2893 [USACO08FEB] Making the Grade G 题目分析

题目链接

分析题目性质

不难解析出题目中的序列 \(B\) 有“单调不下降”和“单调不上升”两种情况,不难想到分两种情况讨论答案即可。

有一个性质:

在满足答案最小化的情况,一定存在一种方案使得 \(B\) 中的数字一定在 \(A\) 中。

不难证明其方案是不劣于不在 \(A\) 中的数的。

考虑李煜东的证明:

考虑用数学归纳法证明。

命题对 \(n=1\) 显然成立。

设这个性质对于 \(n=k-1\) 成立,此时构造出的序列为 \(B_1,\dots,B_{k-1}.\)

当 \(n = k\) 时,将有以下的两种情况:

  • \(B_{k-1}\leq A_k\),则令 \(B_k=A_k\) 命题成立且满足单调性。
  • \(B_{k-1}>A_k\),则有:
    • 存在一段连续相同的 \(B\),即存在一个 \(j<k\) 使得 \(B_j=B_{j+1}=\dots=B_k=v\),有以下的构造方法:
      • 设 \(A_j,\dots,A_k\) 的中位数为 \(mid\),若 \(mid\geq B_{j-1}\) 则有 \(v=mid\),否则应该有 \(v=B_{j-1}.\)
    • 否则,直接令 \(B_k=B_{k-1}.\)

思路

综上,我们考虑:完成前 \(i\) 个数的构造时,当前前 \(i\) 个计入答案的最小值,也就是把 \(dp\) 的阶段设为已经处理完的前缀序列的长度,转移的时候,我们也要确定 \(B_i\) 和 \(B_{i-1}\) 的值以此来确定单调性。

我们思考了一下,这不就是 \(\text{LIS}\) 问题吗?直接设 \(f_i\) 表示完成前 \(i\) 个数后,并且 \(B_i=A_i\) 时,答案的最小值。

转移是简单的:

\[f_i=\min_{0\leq j<i,A_j\leq A_i} f_j+cost(j+1,i-1) \]

其中的 \(cost(j+1,i-1)\) 表示构造 \(B_x\) 的区间 \(x\in[j+1,i-1]\) 满足条件时,答案的最小值。

不难完成对 \(cost(j+1,i-1)\) 的计算,即只需要计算什么时候前面与 \(A_j\) 相同,后面与 \(A_i\) 相同,使答案最小。

扫一遍即可,总时间复杂度 \(\mathcal{O}(n^3)\),无法通过本题。

考虑状态优化,使的状态和转移的综合在一起最小。

具体的,设 \(f_{i,j}\) 表示已经处理完前 \(i\) 个数后 \(B_i=j\) 时,答案的最小值。

初始化肯定是全为 \(0\) 的(考虑到转移有对应的操作)。

因为状态已经是二维的了,我们要使转移是 \(\mathcal{O}(n)\) 以下的。

怎么想呢?

朴素的,直接枚举上一个数 \(B_{i-1}\) 是什么,我们想到了以下转移:

\[f_{i,j}=\min_{0\leq k\leq j} f_{i-1,k}+|A_i-j| \]

考虑跟 \(\text{LCIS}\) 一样的优化:即把重复的取 \(\min\) 提取出来,存入一个变量。

决策集合只增不减,因此转移是 \(\mathcal{O}(1)\) 的。

而根据性质,\(j\) 可以用离散化解决,也可以设为 \(A_j\)。

因此,总时间复杂度 \(\mathcal{O}(n^2)\) 的。

注意,因为要求单调,所以一定要对离散过的 \(A\) 进行排序,否则就有可能不单调。

代码如下:

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
#include <stdlib.h>
#include <cmath>
#define int long long
#define N 2005 
using namespace std;
int n,a[N],ans = 2e9,f[N][N],num[N];
signed main(){
	cin >> n;
	for (int i = 1;i <= n;i ++) cin >> a[i],num[i] = a[i];
	stable_sort(num + 1,num + 1 + n);
	memset(f,0,sizeof f);
	for (int i = 1;i <= n;i ++) {
		int mn = 2e9;
		for (int j = 1;j <= n;j ++) {
			mn = min(mn,f[i - 1][j]);
			f[i][j] = mn + abs(num[j] - a[i]);
		} 
	}
	for (int j = 1;j <= n;j ++) ans = min(ans,f[n][j]);
	reverse(num + 1,num + 1 + n);
	memset(f,0,sizeof f);
	for (int i = 1;i <= n;i ++) {
		int mn = 2e9;
		for (int j = 1;j <= n;j ++) {
			mn = min(mn,f[i - 1][j]);
			f[i][j] = mn + abs(num[j] - a[i]);
		}
	}
	for (int j = 1;j <= n;j ++) ans = min(ans,f[n][j]);
	cout << ans;
	return 0;
}

标签:题目,Grade,leq,num,mathcal,USACO08FEB,Making,include,单调
From: https://www.cnblogs.com/high-sky/p/18538379

相关文章

  • MSDS 490: Healthcare Analytics and Decision Making
    MSDS 490: Healthcare Analytics and Decision MakingProject 3Due Date: 11/18/2024 (Monday Midnight)Submission Instructions: zip all your files (R code,data,Word document,figures,etc.) into one,followingthe file naming convention......
  • CF1625E2. Cats on the Upgrade
    题目题解题目给了很重要的性质,就是保证询问的[l,r]是合法括号串(没有的话可能要莫队+二分找?)假设给出的s串是合法括号序,按照树转括号序的方法逆向转成树,用左括号下标作为树上点的标号例如()(()()),则有root-1,root-3,3-4,3-6,方法是维护左括号的栈,加入右括号时弹左括号t1,然......
  • helm upgrade
    要更新Helm中的单个依赖Chart的版本,你可以按照以下步骤操作:1.**修改`Chart.yaml`或`requirements.yaml`文件**:在你的主Chart中,找到`Chart.yaml`或`requirements.yaml`文件(Helm3使用`Chart.yaml`,Helm2使用`requirements.yaml`),并修改其中依赖的版本号。......
  • centos7-kernel-upgrade-内核升级
    CentOS7升级内核版本yum安装参考1参考2参考3首先查看当前系统的内核版本uname-rs导入ELRepo仓库的公钥信息rpm--importhttps://www.elrepo.org/RPM-GPG-KEY-elrepo.org安装指令#RHEL-7,SL-7orCentOS-7yuminstallhttps://www.elrepo.org/elrepo-release-7.e......
  • autograde
    autograd自动求导torch.Tensor与torch.Function为autograd的核心类,其相互连接生成DAG,PyTorch采用动态计算图,每次前向传播时会重新构建计算图Tensor部分属性说明:requires_grad属性新建Tensor时,用requires_grad参数指定是否记录对叶子节点的操作,便于backward()求解梯度requi......
  • autoupgrade升级(二)
    AnalyzeProcessingMode分析处理模式会检查您的数据库是否已准备好升级。仅从数据库读取数据,而不会对数据库执行任何更新。您可以在正常工作时间内使用分析模式运行AutoUpgrade。在源OracleDatabase主目录上以分析模式运行AutoUpgrade程序。使用以下语法在分析模式下......
  • autoupgrade升级(一)
    关于autoupgarde建议从MyOracleSupportDocument2485457.1下载最新版的autoupgrade.jar程序。每出一个版本RU(releaseupdate)都提供新的autoupgrade.jar程序。默认下载autoupgrade.jar到oracleHome,(Oracle_home/rdbms/admin)但是我没有,我是放到了/tmp下也可以只适用于EE企......
  • 关于ubuntu系统升级遇到的问题:upgrades to the development release are only.......
    主要问题在于使用的是命令:sudodo-release-upgrade-d这将会寻找最新的版本进行安装,但是如果最新版本不稳定的话请求会受到拒绝,导致更新无法进行。具体区别如下:do-release-upgrade是Ubuntu系统用于升级到新版本的命令。当你运行这个命令时,系统会检查是否有新版本可用,并且会自......
  • 揭秘Windows Anytime Upgrade的守护神:windowsanytimeupgradecpl.dll及缺失应对秘籍
    在Windows操作系统的世界里,有一个不为人知但至关重要的文件——windowsanytimeupgradecpl.dll。这个文件是WindowsAnytimeUpgrade功能的守护者,它负责管理和执行Windows版本的升级过程,确保用户能够顺利地从低版本升级到更高版本的Windows系统。WindowsAnytimeUpgrade的守......
  • spring mybatis upgrade to mybatisplus 实战小记
    我司压箱底儿的灵工服务商系统,系统框架是spring,持久层是mybatis。最近,将Mybatisplus集成到系统中,以提高开发效率。升级版本:mybatis版本3.2.2,升级到3.5.16Mybatisplus版本:3.5.3mybatis-spring版本1.2.0,升级到3.0.0pagehelper版本:5.3.1【注】mybatis官方提供了Myba......