因为本人是一位编程小白,目前也是刚刚才学习到C语言。今天在牛客网做一些练习的时候,遇到了下面的这一道题,想要来记录和分享一些东西。
下面呢是这一题目的描述:
题目分析: 这一题要是使用循环的方式来实现还是比较容易的,但是这道题目出现在“递归专区”,我感觉还是有一点点难度...(这个地方可能是我太菜了)。
思路分析: 因为我们要使用递归实现这个问题,那么就一定要用“大事化小”的思路。计算一个排列数,就可以理解是选择问题,题目中的示例1的意思就是在4个中选择2个。 这个地方,大事化小的思路就可以分析为:
4个里面选择2个,就是4个里面选一个,选完在3个里面选1个。再举一个例子。5个里面选择3个,就是5个里面选择1个,选完之后在4个里面选择2个;而4个里面选择2个就又和前面的第一个示例一样了! 分析到这里我们就可以写一部分代码了:
#include <stdio.h>
int func(int n, int m)
{
// n 代表从n个数中选择,m 表示从n个数中选择m个数
return n * func(n - 1, m - 1);
}
int main()
{
int n, m;
scanf("%d %d", &n, &m);
int ret = func(n, m);
printf("%d", ret);
return 0;
那么,我们该如何退出递归呢?继续回到我们的分析里面:我们发现当到 “在3个中选择1个时候,这个时候我们有三种选法,在4个中选择1个的时候我们有4种选法,也就是说当最后一步中,当我们从n个中选择1个的时候,我们就n种选法,这样我们就可以退出递归了” ,所以我们就可以补充我们的代码了。
#include <stdio.h>
int func(int n, int m)
{
// 被选择的数等于1的时候,我们就退出递归
if (m == 1)
return n;
else
return n * func(n - 1, m - 1);
// 用一个示例来分析一下,当我们从5个中选择3个,第一个n = 5,m = 3进入函数
// m != 1, 进入else 5 * func(4, 2)
// 第二次 n = 4, m = 2 进入函数
// m != 1, 进入else 4 * func(3, 1)
// 第三次 n = 3, m = 1 进入函数
// 此时 m == 1, 返回 3,退出递归
// 返回到第二层函数, 此时,第二层函数再返回 4 * 3
// 退入第一层函数, 此时第一层函数返回 5 * 4 * 3
// 所以结果就是 60
}
int main()
{
int n, m;
scanf("%d %d", &n, &m);
int ret = func(n, m);
printf("%d", ret);
return 0;
}
再验证题目中的计算方法:n! / (n - m)! = 5! / 2! = 60。 验证正确!
此文是我在"稀土掘金"的第一篇随笔,也算是一篇小文章了,我会在"掘金"持续分享一些我自己的随笔和想法,和大家共同进步!也希望可以在"掘金"中认识一些大佬,在计算机方向中学习到更多技术!