【Plan 第六场】【后缀数组模板】

本文深入探讨了深度学习在人工智能领域的应用,包括神经网络、机器学习算法及其在图像处理、自然语言处理和强化学习等领域的实践案例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


题目见2015-1 1.6


A

后缀数组乱搞,蒟蒻看到uoj有人DA胜过DC3,于是又换了个版。。。

#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <cmath>
#include <algorithm>
using namespace std;
#define rep(i,l,r) for(int i=(l),_=(r);i<=_;i++)
#define per(i,r,l) for(int i=(r),_=(l);i>=_;i--)
#define MS(arr,x) memset(arr,x,sizeof(arr))
#define INE(i,u) for(int i=head[u];~i;i=e[i].next)
#define LL long long
#define pii pair<int,int>
inline const int read()
{int r=0,k=1;char c=getchar();for(;c<'0'||c>'9';c=getchar())if(c=='-')k=-1;
for(;c>='0'&&c<='9';c=getchar())r=r*10+c-'0';return k*r;}
////////////////////////////////////////////////
const int N=500010;
char s[N];
int n;
int sa[N],he[N],rk[N],X[N],Y[N],c[N];
pii mi[N*4];
////////////////////////////////////////////////
#define LS o<<1,L,mid
#define RS o<<1|1,mid+1,R
void build(int o,int L,int R)
{
	if(L==R)
	{
		mi[o]=make_pair(he[L],L);
		return;
	}
	int mid=L+R>>1;
	build(LS); build(RS);
	mi[o]=min(mi[o<<1],mi[o<<1|1]);
}
pii getmin(int l,int r,int o,int L,int R)
{
	if(l<=L && R<=r) return mi[o];
	int mid=L+R>>1;
	if(r<=mid) return getmin(l,r,LS);
	else if(l>mid) return getmin(l,r,RS);
	else return min(getmin(l,mid,LS),getmin(mid+1,r,RS));
}
void calheight()
{
	int i,j,k=0;
	for(i=1;i<=n;he[rk[i++]]=k)
	for(k?k--:0,j=sa[rk[i]-1];s[i+k]==s[j+k];k++);
}
void da(int m=26)
{
	#define cmp(u,v,k) (x[u]!=x[v]||x[u+k]!=x[v+k])
	int *x=X,*y=Y,*t,k,p;
	rep(i,1,n) c[x[i]=s[i]-'a'+1]++;
	rep(i,1,m) c[i]+=c[i-1];
	per(i,n,1) sa[c[x[i]]--]=i;
	for(k=1;k<n&&(k==1||m<n);k<<=1,t=x,x=y,y=t)
	{
		p=0;
		rep(i,n-k+1,n) y[++p]=i;
		rep(i,1,n) if(sa[i]>k) y[++p]=sa[i]-k;
		rep(i,1,m) c[i]=0;
		rep(i,1,n) c[x[i]]++;
		rep(i,1,m) c[i]+=c[i-1];
		per(i,n,1) sa[c[x[y[i]]]--]=y[i];
		m=0;
		rep(i,1,n) y[sa[i]]=i==1||cmp(sa[i],sa[i-1],k)?++m:m;
	}
	rep(i,1,n) rk[sa[i]]=i;
	calheight();
}
LL cal(int l,int r)
{
	if(l>=r) return 0;
	pii ret=getmin(l+1,r,1,1,n);
	LL res=0,mid=ret.second;
	res+=(LL)2*((mid-l)*(r-mid+1))*ret.first;
	res+=cal(l,mid-1);
	res+=cal(mid,r);
	return res;
}
////////////////////////////////////////////////
void input()
{
    scanf("%s",s+1);
    n=strlen(s+1);
}
void solve()
{
	da(); he[1]=n;
	//rep(i,1,n) printf("%d\n",he[i]);
	build(1,1,n);
	LL ans=0;
	rep(i,1,n) ans+=(LL)(n-1)*i;
	ans-=cal(1,n);
	cout<<ans<<endl;
}
////////////////////////////////////////////////
int main()
{
    freopen("input.txt","r",stdin); freopen("output.txt","w",stdout);
    input(),solve();
    return 0;
}


B

直接贪心最小割

做过了,就没写代码= =


C

线段树+DP,很水辣

cena卡STL。。。还好窝3个点0.95s卡过去了~

#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <cmath>
#include <algorithm>
#include <set>
using namespace std;
#define rep(i,l,r) for(int i=(l),_=(r);i<=_;i++)
#define per(i,r,l) for(int i=(r),_=(l);i>=_;i--)
#define MS(arr,x) memset(arr,x,sizeof(arr))
#define INE(i,u) for(int i=head[u];~i;i=e[i].next)
#define LL long long
inline const int read()
{int r=0,k=1;char c=getchar();for(;c<'0'||c>'9';c=getchar())if(c=='-')k=-1;
for(;c>='0'&&c<='9';c=getchar())r=r*10+c-'0';return k*r;}
////////////////////////////////////////////////
const int N=200010;
int n,k,a[N];
int dp[2][N];
int mx[2][N*4];
int l[N],r[N],pos[N],_pos[N],ll[N],rr[N];
multiset<pair<int,int> >S;
////////////////////////////////////////////////
#define LS o<<1,L,mid,mx
#define RS o<<1|1,mid+1,R,mx
void MAX(int &a,int b){if(a<b)a=b;}
void insert(int pos,int x,int o,int L,int R,int *mx)
{
	if(L==R)
	{
		MAX(mx[o],x);
		return;
	}
	int mid=L+R>>1;
	if(pos<=mid) insert(pos,x,LS);
	else insert(pos,x,RS);
	mx[o]=max(mx[o<<1],mx[o<<1|1]);
}
int getmax(int l,int r,int o,int L,int R,int *mx)
{
	if(r<1 || l>n) return 0;
	if(l<=L && R<=r) return mx[o];
	int mid=L+R>>1;
	if(r<=mid) return getmax(l,r,LS);
	else if(l>mid) return getmax(l,r,RS);
	else return max(getmax(l,mid,LS),getmax(mid+1,r,RS));
}
////////////////////////////////////////////////
void input()
{
	int cnt=0;
    n=read(); k=read();
    rep(i,1,n) a[i]=read(),S.insert(make_pair(a[i],i));
    for(multiset<pair<int,int> >::iterator it=S.begin();it!=S.end();it++)
        pos[++cnt]=it->second;
    sort(&a[1],&a[n+1]);
    rep(i,1,n) _pos[pos[i]]=i;
}
void solve()
{
	int cur=1;
	rep(i,1,n)
	{
		while(cur<n && a[cur+1]-a[i]<k) cur++;
		r[i]=cur;
	}
	cur=n;
	per(i,n,1)
	{
		while(cur>1 && a[i]-a[cur-1]<k) cur--;
		l[i]=cur;
	}
	cur=1;
	rep(i,1,n)
	{
		while(cur<n && a[cur+1]==a[i]) cur++;
		rr[i]=cur;
	}
	cur=n;
	per(i,n,1)
	{
		while(cur>1 && a[cur-1]==a[i]) cur--;
		ll[i]=cur;
	}
	int ans=0;
	rep(i,1,n)
	{
		dp[0][i]=getmax(1,l[_pos[i]]-1,1,1,n,mx[1])+1;
		dp[1][i]=getmax(r[_pos[i]]+1,n,1,1,n,mx[0])+1;
		if(dp[0][i]==1) dp[0][i]=0;
		insert(_pos[i],dp[0][i],1,1,n,mx[0]);
		insert(_pos[i],dp[1][i],1,1,n,mx[1]);
		MAX(ans,dp[0][i]);
		MAX(ans,dp[1][i]);
		//printf("dp[%d][%d]=%d\n",0,i,dp[0][i]);
		//printf("dp[%d][%d]=%d\n",1,i,dp[1][i]);
	}
	printf("%d\n",ans);
}
////////////////////////////////////////////////
int main()
{
    freopen("input.txt","r",stdin); freopen("output.txt","w",stdout);
    input(),solve();
    return 0;
}




<think>嗯,用户问的是如何获取Java中一个名为plan数组数组数量。首先,我需要确认用户所说的“数组数量”具体指的是什么。在Java中,数组是固定长度的,所以可能用户想知道的是数组的长度,也就是元素的数量。Java里数组是对象,每个数组都有一个length属性,用来表示数组的长度。这个属性是final的,所以一旦数组被创建,它的长度就不能改变。因此,获取数组的长度只需要访问这个length属性即可。 例如,如果数组声明为int[] plan= new int[5];,那么plan.length就会返回5。需要注意的是,length是一个属性而不是方法,所以不需要加括号,直接使用plan.length就可以。 不过,有时候可能会有多维数组的情况。比如二维数组int[][] plan =new int[3][4];,这时候plan.length获取的是第一维的长度,也就是3。而plan[0].length则是第二维的长度,4。这时候用户可能需要注意区分多维数组中不同维度的长度。 但根据用户的问题,他提到的是“plan数组数组数量”,可能指的是单层数组的长度。所以正确的做法就是使用数组的length属性。 另外,用户可能混淆了数组和集合类(如ArrayList)的区别。对于集合类,获取元素数量是使用size()方法,而数组则是length属性。需要确保用户使用的是数组而不是集合,否则方法会不同。 总结来说,用户的问题可以通过直接访问数组的length属性来解决,比如plan.length。需要提醒用户注意数组和集合类的区别,以及多维数组的情况。</think>要获取Java数组的长度,可以使用数组的`length`属性。对于名为`plan`的数组,直接通过`plan.length`即可获取其元素数量。 ```java public class Main { public static void main(String[] args) { int[] plan = {1, 2, 3, 4, 5}; int arrayLength = plan.length; // 获取数组长度 System.out.println("数组长度:" + arrayLength); // 输出:5 } } ``` **解释**: 1. Java数组是固定长度的数据结构,所有数组类型都有一个`length`属性。 2. `length`属性是数组的固有属性,在数组创建时确定,且不可修改。 3. 对于多维数组(如二维数组),`array.length`返回的是第一维的长度(行数),而每个子数组的长度可能不同。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值