33,008
社区成员
发帖
与我相关
我的任务
分享
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
char hash[64];
char test[64];
__int64 DP[64];
__int64 temp[64];
int path[64][64];
void dfs1(int a);
void dfs2(int a,int b,int c,int d,int step);
__int64 TC(__int64 a,__int64 b) // ( C(a,b) a个东西任取b个)
{
__int64 i,j,k;
__int64 num = 1;
memset(test,0,sizeof(char)*64);
for(j=1;j <=b;a--,j++)
{
num = num*a;
for(i = 2;i <=b;i++)
{
if(test[i] == 0)
{
k = num/i;
if(num - k*i == 0)
{
test[i] = 1;
num = k;
}
}
}
}
return num;
}
__int64 CC(__int64 a,__int64 b) //b个盘子,a种水果,每个盘有必需有且只有一个水果
{
__int64 i,j,k;
__int64 num = 0;
j = a <b?a:b;
for(i = 1;i <= j; i++)
{
num = num + TC(a,i)*TC(b-1,i-1);
}
return num;
}
void dfs2(int a,int b,int c,int d,int step) //计算组合
{
__int64 count;
if(step == b)
{
path[d][step] = a;
if(DP[a] == 0) dfs1(a);
count = 1;
memset(hash,0,sizeof(char)*64);
for(step = 1;step <=b;step++) hash[path[d][step]]++;
for(step = 1;step <=40; step++)
{
if(hash[step])
{
count*=CC(DP[step],hash[step]);
}
}
temp[d]+=count;
return;
}
for(;c*(b-step) <=a-c;c++)
{
path[d][step] = c;
if(DP[c] == 0) dfs1(c);
dfs2(a-c,b,c,d,step+1);
}
}
void dfs1(int a) //分割组合
{
int i = a-1;
for(;i>=1;i--)
dfs2(a-1,i,1,a,1);
DP[a] = temp[a];
}
int main()
{
int m;
memset(DP,0,sizeof(__int64)*64);
memset(temp,0,sizeof(__int64)*64);
DP[1] = 1;
dfs1(40);
while(scanf("%d",&m)!=EOF)
{
printf("%I64d\n",DP[m]);
}
return 0;
}
f(1) + f(4) 构造的
O
O
O
O
O
O
O
O
O O
O
O
O O
O
O
O
OOO
f(2) + f(3)构造的
O
O O
O
O
O
O O
O O
f(3) + f(2)构造的
O
O O
O O
O
OOO
O
算f(4) + f(1)构造的?还是应该算是f(5)独有的1个?
O
OOOO