2012 Multi-University Training Contest 1 Divide Chocolate(递推)

状态表示:

      dp[i][0][j]:前i行有j部分且第i行的两个格子属于同一部分的方法数

      dp[i][1][j]:前i行有j部分且第i行的两个格子属于不同部分的方法数

#include <stdio.h>
#include <string.h>
#define N 100000007 
int dp[1005][2][2005]; 
int n,k; 
void solve()
{
		int i,j;
		memset(dp,0,sizeof(dp));
		dp[1][0][1]=dp[1][1][2]=1;
		for(i=1;i<=n;i++)
			for(j=0;j<=k;j++) 
			{ 
				 dp[i+1][0][j]=(dp[i+1][0][j]+dp[i][0][j]+(dp[i][1][j])*2)%N;
		         dp[i+1][0][j+1]=(dp[i+1][0][j+1]+dp[i][0][j]+dp[i][1][j])%N;
		         dp[i+1][1][j]=(dp[i+1][1][j]+dp[i][1][j])%N;
		         dp[i+1][1][j+1]=(dp[i+1][1][j+1]+(dp[i][0][j]*2)+(dp[i][1][j]*2))%N;
		         dp[i+1][1][j+2]=(dp[i+1][1][j+2]+dp[i][0][j]+dp[i][1][j])%N;
			 }	
		
} 
int main()
{
	int T;
	scanf("%d",&T);
	while(T--)
	{
		scanf("%d%d",&n,&k);
		solve();
		printf("%d\n",(dp[n][1][k]+dp[n][0][k])%N);	
	} 
		
		 
} 


 

你可能感兴趣的:(Training)