首页 > 其他分享 >cdq分治 提高篇

cdq分治 提高篇

时间:2024-07-26 20:09:50浏览次数:8  
标签:mn int 提高 分治 转移 cdq mx define

优化动态规划

序列

首先要会最长上升子序列的转移,这里就不说了。

我们 \(i\) 位置的初始值为 \(a_i\),可能变成的最大值为 \(mx_i\),可能变成的最小值为 \(mn_i\)。

然后如果 \(j\) 要转移到 \(i\),则需要满足:\(j<i,mx_j\le a_i,a_j\le mn_i\)。然后考虑把 \([l,mid]\) 按照 \(mx\) 排序,使得如果出现 \(j\) 满足 \(mx_j>a_i\) 那么 \([l,j-1]\) 是一个极大的区间满足这个区间的数全部满足前两个要求(因为 \(mx\) 单调不降)。还有就是,因为 \([mid+1,r]\) 按照 \(a\) 排序,所以可以保证如果对于区间 \([l,j]\) 的 \(mx\) 值全部不大于 \(i\) 的 \(a\) 值,那么对于 \(k>i\) 也不会出现 \(mx\) 值更大的情况,所以转移是对的。

然后就是怎么转移,大概就是把 \(j\) 的 \(f\) 值扔进树状数组,到转移的时候查一下 \(a\) 值不大于当前点 \(mn\) 值的点的最大 \(f\) 值进行转移(\(f\) 是动态规划转移数组)。

最后看一下代码:

#include<bits/stdc++.h>
#define int long long
#define N 100005
#define lim 100000
using namespace std;
int n,m,a[N],mx[N],mn[N],f[N],p[N],c[N];
bool cmp1(int x,int y){
	return mx[x]<mx[y];
}
bool cmp2(int x,int y){
	return a[x]<a[y];
}
int lowbit(int x){
	return x&-x;
}
void modify(int x,int v){
	while(x<=lim){
		c[x]=max(c[x],v);
		x+=lowbit(x);
	}
}
int qry(int x){
	int res=0;
	while(x){
		res=max(res,c[x]);
		x-=lowbit(x);
	}
	return res;
}
void clear(int x){
	while(x<=n){
		c[x]=0;
		x+=lowbit(x);
	}
}
void cdq(int l,int r){
	if(l==r){
		f[l]=max(f[l],1ll);
		return;
	}
	int mid=l+r>>1;
	cdq(l,mid);
	for(int i=l;i<=r;i++){
		p[i]=i;
	}
	sort(p+l,p+mid+1,cmp1);
	sort(p+mid+1,p+r+1,cmp2);
	int j=l;
	for(int i=mid+1;i<=r;i++){
		while(j<=mid&&mx[p[j]]<=a[p[i]]){
			modify(a[p[j]],f[p[j]]);
			j++;
		}
		f[p[i]]=max(f[p[i]],qry(mn[p[i]])+1);
	}
	for(int i=l;i<=mid;i++){
		clear(a[i]);
	}
	cdq(mid+1,r);
}
signed main(){
	cin>>n>>m;
	for(int i=1;i<=n;i++){
		cin>>a[i];
		mx[i]=mn[i]=a[i];
	}
	while(m--){
		int x,y;
		cin>>x>>y;
		mx[x]=max(mx[x],y);
		mn[x]=min(mn[x],y);
	}
	cdq(1,n);
	int res=0;
	for(int i=1;i<=n;i++){
		res=max(res,f[i]);
	}
	cout<<res;
	return 0;
}

标签:mn,int,提高,分治,转移,cdq,mx,define
From: https://www.cnblogs.com/zxh923aoao/p/18325709

相关文章

  • 暑假集训CSP提高模拟8
    T1点击查看代码#include<bits/stdc++.h>#definelllonglongusingnamespacestd;lla[5];intmain(){ cin>>a[1]>>a[2]>>a[3]; sort(a+1,a+3+1); llans=(a[3]-a[1])/2+(a[3]-a[2])/2; a[1]+=(a[3]-a[1])/2*2;a[2]+=(a[3]-a[2])/2*2; if(a......
  • 『模拟赛』暑假集训CSP提高模拟8
    Rank诶好像把7咕了,那就咕吧。膜拜博弈论带我上Rank1。A.基础的生成函数练习题(gf)原[ABC093C]SameIntegers先给\(a\),\(b\),\(c\)按升序排个序,求出相邻两数之差。若较小的两数之差(\(a\)和\(b\))为奇数,先操作\(\lfloor{\frac{b-a}{2}}\rfloor\)次使\(a=b-1\),再操......
  • 【YOLOv8改进 - 注意力机制】Gather-Excite : 提高网络捕获长距离特征交互的能力
    YOLOv8目标检测创新改进与实战案例专栏专栏目录:YOLOv8有效改进系列及项目实战目录包含卷积,主干注意力,检测头等创新机制以及各种目标检测分割项目实战案例专栏链接:YOLOv8基础解析+创新改进+实战案例介绍摘要虽然卷积神经网络(CNNs)中使用自下而上的局部操作符与自......
  • 暑假集训CSP提高模拟8
    暑假集训CSP提高模拟8\(T1\)P155.基础的生成函数练习题(gf)\(100pts\)原题:[ABC093C]SameIntegers设通过操作\(a,b,c\)所能达到的最小整数为\(x\)。观察到对同两个数进行操作\(2\)等价于分别对这两个数各进行操作\(1\),在\(a,b,c\)达到\(x\)的过程中优先......
  • P1082 [NOIP2012 提高组] 同余方程
    [NOIP2012提高组]同余方程解法在这个问题中,我们想要找到......
  • 暑假集训CSP提高模拟7
    这个T1的\(n^{3}\)的SPJ效率还是太慢了,膜拜SPJ大神学长,还会画画A.Permutations&Primes这题感觉挺水的但是感觉有不是那么水,主要还是因为我赛时没想出正解,在打的表里找了一组好看的规律,打上了然后就过了.对偶数来说,我的规律正好是正解的特化,但是对奇数来说,我的规律就......
  • 「模拟赛」暑期集训CSP提高模拟6(7.23)
    \(140pts,Rank23\)题目列表A.花间叔祖B.合并rC.回收波特D.斗篷花间叔祖\(98pts\)题意:给定一个数组,选择一个大于等于2的模数,然后把数组中的数变成\(mod\)该模数后的数。只能操作一次,问操作后最少有几种不同的数。赛事分析:开始5分钟想到了算\(a_i\)中所有......
  • 洛谷题单指南-前缀和差分与离散化-P1314 [NOIP2011 提高组] 聪明的质监员
    原题链接:https://www.luogu.com.cn/problem/P1314题意解读:计算m个检验值之和,计算与s差值绝对值的最小值。解题思路:1、首先要搞懂检验值是如何计算的如上图,对于每一个区间的检验值yi,表示为:yi="该区间重量>=W的矿石个数" ✖️"该区间>=W的矿石价值之和"检验值y即所有yi(1<=......
  • 暑假集训csp提高模拟7
    赛时rank42,T180,T213,T30,T420在T4挂死了,赛时胡了一个挺没有前途的\(O(n\log_2^3n)\)的做法,结果赛后发现假了,没有时间打T2,T3的暴力了。糖T1Permutations&PrimesPermutations&Primes赛时有一个特判\(n=3\)错了,挂了20pts结论非常显然,1放中间,2、3各放一边,剩下的随便......
  • 暑假集训CSP提高模拟7
    暑假集训CSP提高模拟7组题人:@KafuuChinocpp|@Chen_jr\(T1\)P122.Permutations&Primes\(20pts\)原题:CF1844BPermutations&Primes假的构造策略,拿到了\(20pts\)。若\(n\)为奇数,则将\(1\)放在\(\left\lceil\frac{n}{2}\right\rceil\)的位置上,前一半......