集合的划分(setsub)

集合的划分(setsub)
题目描述
设s是一个具有n个元素的集合,s={a1,a2,......,an},现将s划分成K个满足下列条件的子集合s1,s2,......,sk,且满足:
1.si≠φ
2.si∩sj=φ(1≤i,j≤ki≠j)
3.s1∪s2∪s3∪...∪sk=s
则称s1,s2,......,sk是集合s的一个划分。它相当于把s集合中的n个元素a1,a2,......,an放入k个(0<k≤n<30)无标号的盒子中,使得没有一个盒子为空。
请你确定n个元素a1,a2,......,an放入k个无标号盒子中去的划分数s(n,k)。

输入
一行,两个整数n、k

输出
一行,一个整数s(n,k)

样例输入
10 6

样例输出
22827

【分析】

我一开始觉得这题写个暴搜应该能AC。

然而我写了,没过。可能因为我太弱了,也可能因为今天中午在食堂干饭没有理同班同学,rp--

回归正题。原题写的不太明白。不过看数据点应该是输出划分出的集合个数。

举个例子。

当n=5时,

k=1-->s(n,k)=1

k=2-->s(n,k)=15

k=3-->s(n,k)=25

k=4-->s(n,k)=10

由此可以推出:

s(n,k)=s(n-1,k-1)+k*s(n-1,k).

当k=1或k=n时,s(n,k)=1;

当n<k或k<0时,s(n,k)=0.

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 int s(int a,int b)
 4 {
 5     if(b<=0||a<=0||a<b)
 6     {
 7         return 0;
 8     }
 9     if(b==1||b==a)
10     {
11         return 1;
12     }
13     return s(a-1,b-1)+s(a-1,b)*b;
14 }
15 int main()
16 {
17     int n,k;
18     scanf("%d %d",&n,&k);
19     printf("%d",s(n,k)) ;
20     return 0;
21 }
原文地址:https://www.cnblogs.com/TheZealous/p/14303153.html