当前位置: 首页 > news >正文

题解:P10299 [CCC 2024 S5] Chocolate Bar Partition

更差的阅读体验


先将所有格子的权值都减去这些格子的平均数。为了方便,我们先将所有格子的权值乘以 \(2n\) 保证平均数是整数。问题转化成,将 \(2 \times n\) 的网格划分成尽可能多的连通块,使得每一块的权值和为 \(0\)

我们可以先考虑一个朴素的 dp:设 \(f_{i, j, k}\) 表示只考虑前 \(i\) 行,上面的格子所在连通块和为 \(j\),下面的格子所在连通块和为 \(k\) 的答案。然而状态数是 \(O(nV^2)\)\(V\) 为值域,没有什么前途。

然而我们发现很多状态是无用的。具体地,我们只关心一个连通块的最后一个格子在哪里,即要从哪里划分连通块。所以由上面的状态设计,一个有用的状态,一定是上面的格子或下面的格子所在连通块的和为 \(0\),即 \(jk = 0\)。更进一步地,由于目前状态下只有一个连通块的权值和不为 \(0\),因此我们甚至不需要记录 \(j\)\(k\),而是直接通过上下两行的前缀和得出答案。

我们设 \(f_{0/1, i}\) 表示目前考虑前 \(i\) 行,上面或下面的格子所在连通块的权值和不为 \(0\)。设目前考虑 \(f_{j, i}\),令 \(k = j \oplus 1\),则转移分三种:

  • 将上下的格子都划分到前一列不为 \(0\) 的格子所在连通块。则连通块数量不会增加,从 \(\max(f_{j, i-1}, f_{k, i-1})\) 转移。
  • 将第 \(k\) 行末尾的若干个格子形成一个和为 \(0\) 的连通块,从 \(f_{k, l} + 1\) 转移,其中 \(l\) 是一个合法转移点满足 \(\sum\limits_{x=l+1}^{i}a_{k, x} = 0\)
  • 将第 \(k\) 行末尾的若干个格子和前面不为 \(0\) 的格子形成一个和为 \(0\) 的连通块,从 \(f_{k, l} + 1\) 转移,其中 \(l\) 是一个合法转移点满足 \(\sum\limits_{x=l+1}^{x}a_{k, x} + \sum\limits_{x=1}^{l}a_{k, x} + \sum\limits_{x=1}^{l}a_{j, x} = 0\)
  • 该行上下格子所在的格子连通块和都为 \(0\),这种条件需满足 \(\sum \limits_{x=1}^{i}a_{j, x}+\sum \limits_{x=1}^{i}a_{k, x} = 0\),用 \(\max(f_{j, i}, f_{k, i}) + 1\) 转移,表示可以新开一个连通块。

第一和第四个转移直接做就好了。第二、三开一个桶存满足条件的最大 \(f_{k, l}\)。由于前缀和值域很大,需要离散化。

那么这道题就做完了,复杂度 \(O(n \log n)\)

#include<bits/stdc++.h>
#define int long long
#define endl '\n'
#define N 800006
using namespace std;
inline void chkmax(int &x,int y){x=x<y?y:x;}
int n,bn,sum,b[N],a[2][N],s[2][N],s_[2][N];
int f[2][N],g[4][N];
main()
{scanf("%lld",&n);for(int i=0;i<2;i++)for(int j=1;j<=n;j++)scanf("%lld",&a[i][j]),sum+=a[i][j];for(int i=0;i<2;i++)for(int j=1;j<=n;j++)a[i][j]=a[i][j]*2*n-sum+a[i][j-1];for(int i=0;i<2;i++)for(int j=0;j<=n;j++)b[++bn]=a[i][j],b[++bn]=-a[i][j];sort(b+1,b+1+bn),bn=unique(b+1,b+1+bn)-b-1;for(int i=0;i<2;i++)for(int j=0;j<=n;j++)s[i][j]=lower_bound(b+1,b+1+bn,a[i][j])-b;for(int i=0;i<2;i++)for(int j=0;j<=n;j++)s_[i][j]=lower_bound(b+1,b+1+bn,-a[i][j])-b;memset(g,-0x3f,sizeof(g));for(int i=1;i<=n;i++){for(int j=0;j<2;j++)chkmax(g[j][s[j][i-1]],f[j^1][i-1]);for(int j=0;j<2;j++)chkmax(g[j|2][s[j^1][i-1]],f[j][i-1]);for(int j=0;j<2;j++)chkmax(f[j][i],max(f[0][i-1],f[1][i-1]));for(int j=0;j<2;j++)chkmax(f[j][i],max(g[j^1][s[j^1][i]],g[(j^1)|2][s_[j^1][i]])+1);if(a[0][i]+a[1][i]==0)f[0][i]=f[1][i]=max(f[0][i],f[1][i])+1;}printf("%lld\n",f[0][n]);return 0;
}
http://www.aitangshan.cn/news/571.html

相关文章:

  • 关闭Ollama开机启动项
  • MySQL 根据一个表的字段值,更新另一个表的字段
  • DeepCompare文件深度对比软件:智能同步滚动与对比视图管理功能完全指南
  • 书单
  • 2025 款潘通色卡 PS/AI 插件推荐:解锁高效配色新体验
  • Dubbo源码—1.服务发布的主要流程
  • 剑指offer-20、包含min函数的栈
  • CF1456E XOR-ranges 题解
  • QueryCon 2019:osquery的重大转折点 - 技术治理与社区共建
  • 基于Transformer的百万级文本分类技术
  • 详细介绍:网络基础1-11综合实验(eNSP):vlan/DHCP/Web/HTTP/动态PAT/静态NAT
  • Omnissa Horizon Windows OS Optimization Tool 2506 - Windows 系统映像优化工具
  • docker 容器化部署 vLLM 启动大模型
  • App Linking 助力应用场景创新,操作步骤立省 60%
  • ChatGpt 5系列文章1——编码与智能体
  • Cisco Catalyst 9800-CL IOS XE 17.18.1 发布,新增功能简介
  • Cisco Modeling Labs (CML) 2.9.0 - 网络仿真工具
  • Omnissa App Volumes 4, version 2506 - 实时应用程序交付系统
  • Omnissa Dynamic Environment Manager 2506 - 个性化动态 Windows 桌面环境管理
  • AES 加密模式演进:从 ECB、CBC 到 GCM 的 C# 深度实践
  • Cisco Catalyst 9800 WLC IOS XE 17.18.1 发布,新增功能简介
  • 详细介绍:python办自动化--读取邮箱中特定的邮件,并下载特定的附件
  • 微软开源的 MCP 教程「GitHub 热点速览」
  • 题解:qoj10322 Matching Query
  • ZR Summer 2025 CD ACM暨 ZR Summer 2025 C 游记
  • flutter flutter_inappwebview插件里js上传调用相机和图库碰到的问题
  • ruoyi-cloud微服务docker部署
  • #dp#L 最多变的序列
  • idea系列问题
  • Infoblox推出革命性高级威胁防御方案,通过DNS层防护主动抵御AI驱动的复杂攻击