CF140E New Year Garland


CF140E New Year Garland


Count dp regular good questions.

It is found that in addition to the limitations of two adjacent layers, our calculations for each layer are independent.

Therefore, it can be considered to calculate all internal situations first, and then eliminate the limitation that the two adjacent layers cannot be adjacent through inclusion and exclusion (that is, the number of cases without limitation - the number of cases where the two layers are the same).

For the interior of each layer, we consider dp, and let \ (g[i][j] \) represent the number of schemes with \ (j \) colors for the first \ (I \) balls.

The transfer is obviously: \ (g[i][j]=g[i-1][j-1]+g[i-1][j]\times \dbinom {j-1}1 \)

It means that the \ (i \) ball can be a new color, or it can choose a color different from the previous ball from the existing colors.

Then consider the scheme count between layers or dp.

Let \ (f[i][j] \) represent the number of schemes with \ (j \) colors in the front \ (I \) layer and the \ (I \) layer.

The transfer equation is also easy to get: \ (f [i] [J] = \ dbinom MJ \ sum \ limits {k = 1} ^ {\ min (L [I-1], m)} f [i] [k] \ times G [l [i] [J] - F [I-1] [J] \ times G [l [i] [J] \)

It means to transfer directly from the previous layer without considering the restrictions, and subtract the number of schemes equal to the previous layer and this layer.

Then we should remember that colors have labels, so we need to add a label globally: \ (f [i] [J] = J! \ times (\ dbinom MJ \ sum \ limits {k = 1} ^ {\ min (L [I-1], m)} f [I-1] [K] \ times G [l [i] [J] - f [I-1] [J] \ times G [l [i] [J]) \)

But it's not over yet.

First of all, the combination number here is not easy to calculate. Because the modulus is not fixed, we can only calculate \ (exclucas \), but it is found that the external \ (j! \) can be thrown into the permutation number, and the total number is fixed. This calculation is much more convenient.

So we just need to preprocess these permutations and factorials.

Secondly, we find that the transfer here is \ (O(l) \), which will be T lost. Just prefix and optimize it directly.

Next, we will find that the space is a little insufficient, but we know that \ (f \) will only be transferred from the previous one, and \ (g \) is always used, so you can roll \ (f \) into the array, and the array that arranges the number is obviously one-dimensional, because the total number is fixed.

Then it's almost done.


using namespace std;
//	#define getchar() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++)
//	char buf[1<<21],*p1=buf,*p2=buf;
template<typename T>
inline void read(T &x){
	x=0;bool f=false;char ch=getchar();
	return ;
template<typename T>
inline void write(T x){
	if(x<0) x=-x,putchar('-');
	if(x>9) write(x/10);
	return ;
#define ll long long
#define ull unsigned long long
#define ld long double
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define pc putchar
#define PII pair<int,int>
#define rep(i,x,y) for(register int i=(x);i<=(y);i++)
#define dep(i,y,x) for(register int i=(y);i>=(x);i--)
int MOD=100;
inline int inc(int x,int y){x+=y;return x>=MOD?x-MOD:x;}
inline int dec(int x,int y){x-=y;return x<0?x+MOD:x;}
inline void incc(int &x,int y){x+=y;if(x>=MOD) x-=MOD;}
inline void decc(int &x,int y){x-=y;if(x<0) x+=MOD;}
inline void chkmin(int &x,int y){if(y<x) x=y;}
inline void chkmax(int &x,int y){if(y>x) x=y;}
const int N=5005,M=1e6+5,INF=1e9+7;
int n,m,p,l[M],g[N][N],f[2][N],Am[N],fac[N],sum,tmp;
signed main(){
//	freopen(".in","r",stdin);
//	freopen(".out","w",stdout);
//	ios::sync_with_stdio(false);
//	double ST=clock();
	rep(i,1,n) read(l[i]);Am[0]=fac[0]=1;
	rep(i,1,5000) Am[i]=1ll*Am[i-1]*(m-i+1)%MOD,fac[i]=1ll*fac[i-1]*i%MOD;g[0][0]=1;
	rep(i,1,5000) rep(j,1,5000) g[i][j]=inc(g[i-1][j-1],1ll*g[i-1][j]*(j-1)%MOD);
		rep(j,l[i-1]+1,l[i]) f[(i&1)^1][j]=0;
		rep(j,1,l[i]) f[i&1][j]=dec(1ll*sum*g[l[i]][j]%MOD*Am[j]%MOD,1ll*f[(i&1)^1][j]*g[l[i]][j]%MOD*fac[j]%MOD),incc(tmp,f[i&1][j]);
//#ifndef ONLINE_JUDGE
//	cerr<<"\nTime:"<<(clock()-ST)/CLOCKS_PER_SEC<<"s\n";
	return 0;

Posted by xubi on Thu, 28 Oct 2021 12:54:02 -0700