POJ 1664 放置苹果

2 篇文章 0 订阅

Name: 放置苹果
P_ID: POJ1664(BNUOJ1783)
题目描述:
把M个同样的苹果放在N个同样的盘子里,允许有的盘子空着不放,问共有多少种不同的分法?(用K表示)5,1,1和1,5,1 是同一种分法。

Input:
第一行是测试数据的数目t(0 <= t <= 20)。以下每行均包含二个整数M和N,以空格分开。1<=M,N<=10。

Output:
对输入的每组数据M和N,用一行输出相应的K。

Sample Input:
1
7 3

Sample Output:
8

分析:
这个题应该很明显是要用递归做的,关键就是怎么递归。
这个题我自己是没有想出怎么递归的,这里我放一个递归函数:
f(m, n) = f(m-n, n) + f(m, n-1);
其中,
f(m,n)是指把m个苹果放置到n个盘子中的方法数,
f(m-n, n)是指把m个苹果放置到n各盘子中,且满足 每个盘子都有苹果。具体做法就是先每个盘子放一个再说。也就是转化为m-n个苹果放置到n各盘子中的方法数。
f(m, n-1)是指把m个苹果放置到n个盘子中,且存在一个空盘子的情况。
注:之所以等于两者相加,是因为 等号右边第一项其实包含了所有没有空盘子的情况,第二项包含了所有存在空盘子的情况。
因为如果所有盘子都有且只有一个苹果,一次递归就解决了,如果多于一个,会在之后的递归中体现,而不同盘子都有苹果但不一定数量相同的情况会在执行了i次递归后转化为存在空盘子的情况。而相应的,存在空盘子的情况已经移交给等号右边第二项来处理,且随着递归次数增加,n不断减小,减小的那部分,全都是空盘子,所以所有包含空盘子可能性的情况都包含在内了。
这里会导致几个问题:
1. 会出现m-n小于等于0的情况,这种情况直接返回1就好。
2. 会出现n小于等于0的情况,同上。

参考代码:

/**
 * name: Apple
 * P_ID: BNUOJ 1783
 * date: 2016-04-06
 */
#include <cstdio>
#include <cstring>
using namespace std;

int a, b, ans;
int f(int x, int n)
{
    if(x<=1 || n<=1) return 1;
    if(x<n) return f(x, x);
    return (f(x-n, n) + f(x, n-1));

}

int main()
{
    int T;
    scanf("%d", &T);
    while(T--)
    {
        ans = 0;
        scanf("%d%d", &a, &b);
        ans = f(a, b);
        printf("%d\n", ans);
    }
    return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值