蒟蒻求助,救救孩子~~
  • 板块学术版
  • 楼主Ackoter
  • 当前回复9
  • 已保存回复9
  • 发布时间2020/7/24 14:50
  • 上次更新2023/11/6 22:24:58
查看原帖
蒟蒻求助,救救孩子~~
13805
Ackoter楼主2020/7/24 14:50

题目是给n(n<=5000)个数,求长度为m(m<=100)的严格上升子序列个数(不必连续),前三个点AC,后面全是5000,100的点RE...

#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdio>
#include<cmath>
#include<list>
#include<map>
#define lkid (now<<1)
#define rkid (now<<1)|1
#define mid ((L+R)>>1)
using namespace std;
int n,m,b[50001],a[50001],ma;
const int mode=1000000007; 
map<int,int>mapp;
struct p{
	int dp[201];
}tree[80001],nu;
p add(p a,p b)
{
	p azhe;
	for(int i=0;i<=n;i++) azhe.dp[i]=(a.dp[i]+b.dp[i])%mode;
	return azhe;
}
p down(p a)
{
	p azhe;
	azhe.dp[0]=0;
	for(int i=1;i<=n;i++) azhe.dp[i]=a.dp[i-1];
	return azhe; 
}
p finds(int L,int R,int now,int l,int r)
{
	if(l>r) return nu;
	if(L>r||R<l) return nu;
	if(l<=L&&R<=r) return tree[now];
	return add(finds(L,mid,lkid,l,r),finds(mid+1,R,rkid,l,r));
}
void updata(int L,int R,int now,int C)
{
	if(L==R)
	{
		tree[now]=add(tree[now],down(finds(1,ma,1,1,C-1)));
		tree[now].dp[1]=(tree[now].dp[1]+1)%mode;
		return;
	}
	if(C<=mid) updata(L,mid,lkid,C); else updata(mid+1,R,rkid,C);
	tree[now]=add(tree[lkid],tree[rkid]);
	return;
}
int main()
{
//	freopen("seq.in","r",stdin);
//	freopen("seq.out","w",stdout);
	scanf("%d%d",&n,&m);
	for(int i=1;i<=n;i++)
	{
		scanf("%d",&a[i]);
		b[i]=a[i]; 
	} 
	sort(b+1,b+1+n);
	for(int i=1;i<=n;i++) if(mapp[b[i]]==0) mapp[b[i]]=i;
	for(int i=1;i<=n;i++)
	{
		a[i]=mapp[a[i]];
		ma=max(ma,a[i]);
	}
	for(int i=1;i<=n;i++)
		updata(1,ma,1,a[i]);
	cout<<tree[1].dp[m];
	return 0;
}
2020/7/24 14:50
加载中...