05 | 递归(上):泛化数学归纳,如何将复杂问题简单化?
该思维导图由 AI 生成,仅供参考
如何在限定总和的情况下,求所有可能的加和方式?
- 深入了解
- 翻译
- 解释
- 总结
递归与循环都是迭代法的实现,但在某些场景下,递归的解法更容易实现。递归的核心思想类似于数学归纳法,将复杂问题逐步简化,通过函数的嵌套调用保存中间状态和变量值,方便编程处理。本文以舍罕王赏麦和奖赏货币的例子阐述了递归的应用,深入浅出地解释了递归的思想和实际应用。递归在计算机编程领域有广泛应用,不仅局限在求和等运算操作上。读者可以通过文章了解递归的概念和实际应用,以及如何使用递归的思想进行“分而治之”的处理。文章提出了一个思考题,鼓励读者使用递归编程的方法,为给定的整数找到所有可能的分解。这篇文章对于读者快速了解递归的概念和实际应用具有很好的指导意义。
《程序员的数学基础课》,新⼈⾸单¥68
全部留言(175)
- 最新
- 精选
- 黄申置顶由于暂时无法追加回复,我这里再回复一下网友debugtalk 我看了Python的实现,果然很简介👍 奖金的题目没问题。整数的因子分解有点小瑕疵,少了一些可能。比如,输入8,少了 [1, 2, 2, 2] [1, 2, 4] [1, 4, 2] [2, 1, 2, 2]2018-12-2018
- 李尧思考题:请大神帮忙看下,输出少了个 [1,8] 输出:[2, 2, 2, 1] [2, 4, 1][4, 2, 1][8, 1] import java.util.ArrayList; /** * @Auther: yli * @Date: 2018/12/19 17:19 * @Description: */ public class Iteration { public static void recursion(long total, ArrayList<Long> result){ if (total == 1){ result.add(1L); System.out.println(result); return; }else { for(long i = 2; i <= total; i ++){ ArrayList<Long> newList = (ArrayList<Long>)(result.clone()); newList.add(Long.valueOf(i)); if(total%i !=0){ continue; } recursion(total/i, newList); } } } public static void main(String[] args){ long total = 8; recursion(total, new ArrayList<Long>()); } }
作者回复: 循环的时候不能少了1,可以在结果中判断是否已经涵盖1,我稍微修改了一下 public static void recursion(long total, ArrayList<Long> result) { if (total == 1) { if (!result.contains(1L)) result.add(1L); System.out.println(result); return; } else { for (long i = 1; i <= total; i++) { if ((i == 1) && result.contains(1L)) continue; ArrayList<Long> newList = (ArrayList<Long>) (result.clone()); newList.add(Long.valueOf(i)); if (total % i != 0) { continue; } recursion(total / i, newList); } } }
2018-12-19613 - debugtalkPython 实现赏金问题:https://github.com/debugtalk/geektime-notes/blob/master/programmers-mathematics/chapter5.md Python 实现思考题:https://github.com/debugtalk/geektime-notes/blob/master/programmers-mathematics/chapter5.py
作者回复: 很棒 我稍后sync下来看
2018-12-19212 - 文刂 氵共 超整数分解 - C++代码 #include <vector> #include <iostream> #include <algorithm> using namespace std; // 输出函数 void PrintResult(vector<int> &Result) { for (size_t i = 0; i < Result.size(); ++i) { cout << Result[i] << " "; } cout << endl; } //数组中是否存在某值 bool IsExit(vector<int> &Result, int value) { vector<int>::iterator result = std::find(Result.begin(), Result.end(), value); if (result == Result.end()) { return false; } else { return true; } } //整数分解 void RecursionAlgo(int Num, vector<int> &Result) { if (Num == 1) { PrintResult(Result); return; } for (int i = 1; i <= Num; ++i) { //判断1是否在解中 if (IsExit(Result, 1)) { if (i == 1) { continue; } } if (Num%i == 0) { vector<int> newResult = Result; newResult.push_back(i); RecursionAlgo(Num/i, newResult); } } } int _tmain(int argc, _TCHAR* argv[]) { int Totalmoney = 10; vector<int> Result; RecursionAlgo(Totalmoney, Result); return 0; }
作者回复: 回答很棒,下次可以将运行结果也贴出来👍
2018-12-199 - 方得始终参考老师和其他同学的留言, 下面是Pythoni实现的思考题, 应该是个较为简洁的版本. import copy def prod_factors(num, result=[]): if num == 1: print('x'.join([str(_) for _ in result])) if 1 not in result: result.append(1) print('x'.join([str(_) for _ in result])) elif num < 0: return else: for i in range(1, num+1): if (i == 1 and i not in result) or (i !=1 and num % i == 0): newresult = copy.copy(result) newresult.append(i) prod_factors(num/i, newresult) prod_factors(8) 1x2x2x2 1x2x4 1x4x2 1x8 2x1x2x2 2x1x4 2x2x1x2 2x2x2 2x2x2x1 2x4 2x4x1 4x1x2 4x2 4x2x1 8 8x1
作者回复: 同时考虑了1出现和不出现的情况 👍
2018-12-2967 - 松原黄老师,这句“递归和循环其实都是迭代法的实现”我不太理解。 如果递归和循环都属于迭代法,那么就是说递归是从属于迭代法的。而我所理解的迭代法的核心是从1到n的递推,而递归是从n到1的逐步求解的过程,两者应该是并列的关系。希望老师能解答我的这个困惑。
作者回复: 确实两者的递推方向是不一样的,不过递归在计算机的实现中,是使用的函数调用,在满足条件后,函数开始逐级返回,这时候又是正向递推了,所以我觉得这也是从1到n
2018-12-196 - Sawyer老师好,我实现了一个算法,但是没有打印出来1的情况。 还有个问题就是,如果使用老师的示例输入8,结果既有 2x4,又有 4x2 这不是重复了吗? static void getFactorization(long product, ArrayList<Long> result) { for (int i = 2; i <= product / 2; i++) { if (0 == product % i) { ArrayList<Long> newResult = (ArrayList<Long>) result.clone(); newResult.add((long) i); getFactorization(product / i, newResult); newResult.add(product / i); System.out.println(newResult); } } }
作者回复: 这里作为教学案例,可以遍历所有情况,包括4x2和2x4。至于1,需要特殊处理一下,你可以思考看看,或者看看之前读者的留言
2019-03-123 - 杨景胜//因数分解 public static void getMultiFactors(long multi,ArrayList<Long> result){ if (multi == 1){ result.add(multi); System.out.println(result); }else{ for (long i = 2; i <= multi; i++) { if(multi % i == 0){ ArrayList<Long> newResult = (ArrayList<Long>) result.clone(); newResult.add(i); getMultiFactors(multi / i,newResult); } } } }
作者回复: 如果循环从2开始,可能会漏掉一些情况,请参考为我给另一位网友李尧的回复
2018-12-193 - cocu这个案例中的n到底是什么,是奖励总金额,还是取的纸币数?
作者回复: 这里我统一回答一下,是当前迭代的次数,也就是取的纸币数量
2018-12-192 - Noya#include <iostream> #include <vector> using namespace std; const int N = 4; int coins[N] = {1, 2, 5, 10}; vector<int> closen; void dfs(int u) { if(u > 10) return; if(u == 10) { for(int i = 0; i < closen.size(); i++) { if(i > 0) printf(" "); printf("%d", closen[i]); } puts(""); return; } for(int i = 0; i < N; i++) { closen.push_back(coins[i]); u += coins[i]; dfs(u); closen.pop_back(); u -= coins[i]; } return; } int main(void) { dfs(0); return 0; } // 老师 这样写对吗
作者回复: 这个是C版本吗?
2019-12-2221