异或序列 [set优化DP]
\(\mathcal{Description}\)
有一个长度为 \(n\)的自然数序列 \(a\),要求将这个序列分成至少 \(m\) 个连续子段
每个子段的价值为该子段的所有数的按位异或
要使所有子段的价值按位与的结果最大,输出这个最大值
\(T\)组询问
\(T\leq 10,n,m\leq 1000,a_i\leq 2^{30}\)
\(\mathcal{Solution}\)
实际上数据范围可开大很多
我们贪心的一位一位的确定最终答案,即看当前考虑的位能否为\(1\)
记\(s_i\)表示前\(i\)个数的异或和,\(\bigoplus\)表示异或
设当前考虑到了第\(b\)位
令\(res=ans|(1<<b)\)
一段区间\([j+1,i]\)如果是一个合法的区间,可以得到
\(\left(s_i\bigoplus s_j\right)\&res=res\)
于是我们得到了一个\(n^2log\)的\(DP\)方程
\(f_i=max{f_i,f_j+1}\)其中\(\left(s_i\bigoplus s_j\right)=res\)
枚举位是\(log\)的,这样就可以\(AC\)此题了
实际这个\(DP\)可以进一步优化
\(\left(s_i\bigoplus s_j\right)\&res=res\)可以推出
\(\left(s_i \& res\right)\bigoplus \left(s_j\& res\right)=res\)
\(\Rightarrow s_i \& res=\left(s_j\& res\right)\bigoplus res\)
即要将\(s_i\)到\(s_j\)这段作为一个子段必须满足上面的条件
因为题目是至少\(m\)段,所以分的越多越好
则我们可以考虑完\(s_i\)的最优答案后将\(s_i\bigoplus res\)作为第一关键字存进\(set\)
\(f_i=find(s_i\bigoplus res)\)
这样一次转移就是\(log\)的
复杂度为\(nlog^2\)
\(\mathcal{Code}\)
/*******************************
Author:Morning_Glory
LANG:C++
Created Time:2019年10月26日 星期六 09时18分19秒
*******************************/
#include <cstdio>
#include <fstream>
#include <cstring>
#include <set>
#define mp make_pair
using namespace std;
const int maxn = 2003;
//{{{cin
struct IO{
template<typename T>
IO & operator>>(T&res){
res=0;
bool flag=false;
char ch;
while((ch=getchar())>'9'||ch<'0') flag|=ch=='-';
while(ch>='0'&&ch<='9') res=(res<<1)+(res<<3)+(ch^'0'),ch=getchar();
if (flag) res=~res+1;
return *this;
}
}cin;
//}}}
int n,m,T,ans;
int a[maxn],s[maxn];
set < pair<int,int> > v;
set < pair<int,int> > :: iterator it,nx;
//{{{solve
void solve (int x)
{
int res=ans|(1<<x);
bool flag;
v.clear();
for (int i=1;i<=n;++i){
int val=s[i]&res;
v.insert(mp(val,0));
nx=it=v.lower_bound(mp(val,0));
++nx;
while (nx!=v.end()&&nx->first==val){
v.erase(it);
it=nx,++nx;
}
if (it->second==0){
if (val==res){
v.insert(mp(val^res,1));
if (i==n) flag=it->second+1>=m;
}
}
else{
v.insert(mp(val^res,(it->second)+1));
if (i==n) flag=it->second+1>=m;
}
}
if (flag) ans=res;
}
//}}}
int main()
{
cin>>T;
while (T--){
cin>>n>>m;
ans=0;
for (int i=1;i<=n;++i){
cin>>a[i];
s[i]=s[i-1]^a[i];
}
for (int i=29;~i;--i) solve(i);
printf("%d\n",ans);
}
return 0;
}
如有哪里讲得不是很明白或是有错误,欢迎指正
如您喜欢的话不妨点个赞收藏一下吧
异或序列 [set优化DP]的更多相关文章
- CF 1150 D Three Religions——序列自动机优化DP
题目:http://codeforces.com/contest/1150/problem/D 老是想着枚举当前在给定字符串的哪个位置,以此来转移. 所以想对三个串分别建 trie 树,然后求出三个t ...
- 2018.09.29 bzoj3675: [Apio2014]序列分割(斜率优化dp)
传送门 斜率优化dp经典题目. 首先需要证明只要选择的K个断点是相同的,那么得到的答案也是相同的. 根据分治的思想,我们只需要证明有两个断点时成立,就能推出K个断点时成立. 我们设两个断点分成的三段连 ...
- 【bzoj3675】[Apio2014]序列分割 斜率优化dp
原文地址:http://www.cnblogs.com/GXZlegend/p/6835179.html 题目描述 小H最近迷上了一个分隔序列的游戏.在这个游戏里,小H需要将一个长度为n的非负整数序列 ...
- 【洛谷3648】[APIO2014] 序列分割(斜率优化DP)
点此看题面 大致题意: 你可以对一个序列进行\(k\)次分割,每次得分为两个块元素和的乘积,求总得分的最大值. 区间\(DPor\)斜率优化\(DP\) 这题目第一眼看上去感觉很明显是区间\(DP\) ...
- BZOJ 3675 APIO2014 序列切割 斜率优化DP
题意:链接 方法:斜率优化DP 解析:这题BZ的数据我也是跪了,特意去网上找到当年的数据后面二十个最大的点都过了.就是过不了BZ. 看到这道题自己第一发DP是这么推得: 设f[i][j]是第j次分第i ...
- 洛谷 P4093 [HEOI2016/TJOI2016]序列 CDQ分治优化DP
洛谷 P4093 [HEOI2016/TJOI2016]序列 CDQ分治优化DP 题目描述 佳媛姐姐过生日的时候,她的小伙伴从某宝上买了一个有趣的玩具送给他. 玩具上有一个数列,数列中某些项的值可能会 ...
- 4.11 省选模拟赛 序列 二分 线段树优化dp set优化dp 缩点
容易想到二分. 看到第一个条件容易想到缩点. 第二个条件自然是分段 然后让总和最小 容易想到dp. 缩点为先:我是采用了取了一个前缀最小值数组 二分+并查集缩点 当然也是可以直接采用 其他的奇奇怪怪的 ...
- 最长子序列(线性DP)学习笔记
子序列和子串不一样.子串要求必须连续,而子序列不需要连续. 比如说\(\{a_1,a_2\dots a_n\}\),他的子串就是\(\{a_i,a_{i+1},\dots, a_j|1\leq i\l ...
- HDU 2993 MAX Average Problem(斜率优化DP)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2993 题目大意:给定一个长度为n(最长为10^5)的正整数序列,求出连续的最短为k的子序列平均值的最大 ...
随机推荐
- GoCN每日新闻(2019-11-02)
GoCN每日新闻(2019-11-02) GoCN每日新闻(2019-11-02) 1. Go 1.13.4 and Go 1.12.13 are released https://groups.go ...
- shell 命令行参数(基本)
命令行参数 $0 表示程序名.$1 至 \$9则是位置参数.$# 表示参数的个数.$* 将所有参数当做一个整体来引用$@ 把每个参数作为一个字符串返回,可以使用for循环来遍历$? 最近一个执行的命令 ...
- c语言用指针定义一个类型进行输入输出
1 整型数组 // #include "stdafx.h" #include "stdlib.h" int _tmain(int argc, _TCHAR* a ...
- 安装ubuntu 16.04版本时搭建环境参考的文章
重新编译的命令:make all ZIP_DEBUGINFO_FILES=0 DISABLE_HOTSPOT_OS_VERSION_CHECK=ok 解决ubuntu中vi不能正常使用方向键与退格键的 ...
- BigDecimal代码示例
在平常开发中,如果涉及到计算,要求准确的精度,比如单价*数量=总价之类的计算,那么得用到BigDecimal. 初始化 如下: BigDecimal amount=new BigDecimal(&qu ...
- SQL on Hadoop技术综述
一.系统架构 runtime framework v.s. mpp 在SQL on Hadoop系统中,有两种架构: 1.一种是基于某个运行时框架来构建查询引擎,典型案例是Hive: 2.另一种是仿照 ...
- TypeScript in 5 minutes
https://www.typescriptlang.org/docs/handbook/typescript-in-5-minutes.html Let’s get started by build ...
- 讨厌的linux----vsftpd 匿名上传配置
核心一句话: vsftpd: refusing to run with writable anonymous root 匿名账号的根目录,不允许写入,否则匿名登录 验证失败 只有再 ftp 命令操作, ...
- 面试突击(七)——JVM如何加载Java字节码信息的?
声明:本文图片均来自网络,我只是进行了选择,利用一图胜千言的力量来帮助自己快速的回忆相关的知识点 1:先看一下Java类文件的转换过程,如下所示,Java字节码文件是通过类加载子系统来放入JVM的内存 ...
- java多线程(六)线程控制类
1. 多线程控制类 为了保证多线程的三个特性,Java引入了很多线程控制机制,下面介绍其中常用的几种: l ThreadLocal l 原子类 l Lock类 l Volatile关键字 ...