「CF478D」Red – Green Towers
题解
由于高度最多是根号n
那么只要dp+滚动数组就能水过了
f[i][j]表示高度为i而第一种颜色用了j的方案数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 |
#include<iostream> #include<cstdio> #include<cstdlib> #include<algorithm> #include<cmath> #include<cstring> #define inf 1000000000 #define ll long long #define mod 1000000007 using namespace std; int read() { int x=0,f=1;char ch=getchar(); while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();} while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();} return x*f; } int a,b,mx; ll f[2][200005],sum[1005]; int main() { a=read();b=read(); f[0][0]=1; int t=sqrt(2*(a+b)); for(int i=1;i<=t;i++) { int mx=min(a,i*(i+1)/2); for(int j=0;j<=mx;j++) { if(j>=i)f[i&1][j]+=f[(i-1)&1][j-i]; if(i*(i+1)/2-j<=b)f[i&1][j]+=f[(i-1)&1][j]; f[i&1][j]%=mod; sum[i]=(sum[i]+f[i&1][j])%mod; } for(int j=0;j<=mx;j++)f[(i-1)&1][j]=0; } for(int i=t;i;i--) if(sum[i]) { printf("%d\n",sum[i]); break; } return 0; } |
Subscribe