" f+ X3 v4 W. I6 w. X8 h% d) S# p 关键要素 6 b9 U1 u6 \1 P7 m1 h+ D! I1. **基线条件(Base Case)** " N- }8 `+ s4 a' G7 R - 递归终止的条件,防止无限循环% u6 Y2 l3 T$ O8 b4 j" S( V
- 例如:计算阶乘时 n == 0 或 n == 1 时返回 1& ^/ L7 p, c% A# M
( E) T* s3 z0 d2 O* w
2. **递归条件(Recursive Case)** 2 J* A1 H9 u6 j7 ~% U' d - 将原问题分解为更小的子问题" T: U* {* t7 z7 j) P- p3 T
- 例如:n! = n × (n-1)! - l3 E, c0 d3 g6 T& @. e 9 h# a+ d7 l3 P5 z6 s 经典示例:计算阶乘 ) O& o& g6 U0 ]4 h* Wpython; e2 S) ~! }% K3 T, V
def factorial(n):- D# X; z2 w( B% [4 ^
if n == 0: # 基线条件8 _9 C& Q5 _2 |7 y/ X
return 1& H" @4 _ m# |+ s6 _* C1 t
else: # 递归条件 " `/ p+ {( Q" n3 Y2 X- T return n * factorial(n-1) % Y: }$ u& Y. _$ e" Z- F' }% i, s执行过程(以计算 3! 为例): 3 }8 B* [+ K# v, ffactorial(3) 7 z( n" Z+ |0 @3 * factorial(2) * c$ e5 _# L& F! j+ X$ n2 f+ z3 * (2 * factorial(1)) 9 l I! D5 R4 w3 * (2 * (1 * factorial(0)))+ b \/ {5 I) J
3 * (2 * (1 * 1)) = 6 : i# E% P& s! n, Q $ `1 D* T% G4 J | 递归思维要点 6 X, p3 K7 g( ]. `8 v1. **信任递归**:假设子问题已经解决,专注当前层逻辑' f- M. A. O9 G: Y; g
2. **栈结构**:每次调用都会创建新的栈帧(内存空间) ( [9 ?/ o# @; O+ a! b: x. q/ t0 [3. **递推过程**:不断向下分解问题(递) - T: S$ g* l* ]4. **回溯过程**:组合子问题结果返回(归) ! M" J7 P3 h/ Q7 i * e2 J% v0 w- a- L$ [* H, C 注意事项 / T {; r( i" V+ n+ {1 _1 z必须要有终止条件 ; y: w, i# Q5 d+ l: v- k* Y递归深度过大可能导致栈溢出(Python默认递归深度约1000层)3 N1 Z' d3 f2 A- T; @+ Q$ p
某些问题用递归更直观(如树遍历),但效率可能不如迭代 ! h+ F* M3 }" `% `; y- k) S$ {8 o尾递归优化可以提升效率(但Python不支持): j- ~+ g: |- I
) o7 `. C% ?8 d4 | 递归 vs 迭代8 h% M) A; K4 q( s# q/ s
| | 递归 | 迭代 | 2 {- m+ N0 ~8 X o& X|----------|-----------------------------|------------------|& H8 p8 F' U8 R$ S) A8 X
| 实现方式 | 函数自调用 | 循环结构 |9 O" w' v L6 B) i" U; e
| 内存消耗 | 需要维护调用栈(可能溢出) | 通常更节省内存 | ! C9 C; }# u9 Y| 代码可读性 | 对符合递归思维的问题更直观 | 线性流程更直接 | & u! x$ R# z4 }+ |* c% p| 适用场景 | 树结构、分治算法、回溯问题等 | 简单重复操作 |1 ~' h2 g0 u: m! d' o
3 E1 {7 M* X5 r4 z& s
经典递归应用场景5 M! w0 N) W/ l e3 N# J" |# j
1. 文件系统遍历(目录树结构) + F5 h5 r# q2 S5 M, a2. 快速排序/归并排序算法+ I# F# P8 N8 v4 w1 h8 e
3. 汉诺塔问题 " ^! B# O! ^% }4. 二叉树遍历(前序/中序/后序) 9 v: J" k8 j/ }( R' f( Q* X5 R5. 生成所有可能的组合(回溯算法) # K5 T* Y3 d) a4 {. K2 m8 C# n2 o 4 k* ?7 Y7 s6 Q+ L试着用递归思维想象:你站在一面镜子前,镜子里有无数个逐渐变小的你在照镜子,这就是递归的直观体现。但记住每个"分身"最终都要有结束的时刻,这就是基线条件的重要性。作者: testjhy 时间: 2025-1-30 00:07
挺好,递归思维要点与我能够回忆起来我当时写递归程序的思路很一致,,或者被它唤醒, ' s" Q7 E' ?. Y% Q0 d3 `我推理机的核心算法应该是二叉树遍历的变种。 $ K6 [% w. m7 Q9 W+ M6 V另外知识系统的推理机搜索深度(递归深度)并不长,没有超过10层的,如果输入变量多的话,搜索宽度很大,但对那时的286-386DOS系统,计算压力也不算大。作者: nanimarcus 时间: 2025-2-2 00:45
Recursion in programming is a technique where a function calls itself in order to solve a problem. It is a powerful concept that allows you to break down complex problems into smaller, more manageable subproblems. Here's a detailed explanation: 7 O K; x# N) q' a, a( A- u2 qKey Idea of Recursion ' y& K8 x) p5 K9 l8 ~( A6 M- v; I, f; a& F9 Q* j$ \2 [" C- k" ?/ Z: Y
A recursive function solves a problem by: ; j/ k) b( h4 ^- p' N; V) a9 Q. L8 p0 M+ m4 T3 M3 Y
Breaking the problem into smaller instances of the same problem. \; `% \7 T6 B: X# Z3 _" Y1 l / D3 @& ]+ P5 z* o/ u E1 X Solving the smallest instance directly (base case). 4 e+ L+ Q. V& @ |3 k/ V 5 j1 d/ h& K/ j' h# i1 H Combining the results of smaller instances to solve the larger problem.0 c$ A' y) Z7 a, @
6 U( Q; T E4 a' K% }Components of a Recursive Function* N) V) R2 O$ V6 ?( ~
( V. F. k, r" n) v' w3 E
Base Case: . ~) @# J' p, U- K. `0 w: U% }" g, f0 O1 X' X
This is the simplest, smallest instance of the problem that can be solved directly without further recursion. , M l. |' D# z: M' X% Z: [. P' [8 S- i' q, B( J
It acts as the stopping condition to prevent infinite recursion., R: N! W: P% E* @$ w8 m" G
/ |/ x. J1 A; `4 z& j: w! b) s
Example: In calculating the factorial of a number, the base case is factorial(0) = 1.( e' O" q, ]8 }% r' P) H: {3 y3 j
+ l+ W9 a, J& N# [$ t4 a4 j
Recursive Case:7 p- j8 L/ I* k+ h! Y
- l- w8 i3 L2 |$ G) J This is where the function calls itself with a smaller or simpler version of the problem.; {) s7 H+ d! `/ a! l/ f
! a) C9 }1 J2 V- p Example: For factorial, the recursive case is factorial(n) = n * factorial(n-1).' V$ E6 Q4 `% h) Z
; i8 e8 R4 E+ E5 {% oExample: Factorial Calculation4 }8 x3 o U' W; I1 N6 V! R
! n+ e# n: y2 }
The factorial of a number n (denoted as n!) is the product of all positive integers less than or equal to n. It can be defined recursively as:$ A% U$ T$ V2 |. D
$ v& F8 A5 h* \) C2 |8 W Base case: 0! = 1 9 ~/ [6 J: [ h- X6 i) n+ } 3 \7 s1 C, [- U1 e0 }0 p Recursive case: n! = n * (n-1)! " S5 K2 @/ c! O* ]8 o+ _% J 3 `' A; z$ c1 @& Q' N* X: ^6 THere’s how it looks in code (Python):' \+ X8 ^6 A' U/ W
python# V' ^- L9 h; q1 |/ d' z
8 C6 ]( A' P. j- }
* D7 z+ y9 g9 d ?( a# pdef factorial(n):) r7 t1 k) p* \$ u
# Base case9 A1 @4 d6 H6 Y! Q9 ^2 I
if n == 0:; k5 T* m3 E8 s0 s3 C9 p
return 1 \( b4 n7 ` D" M) I0 p # Recursive case : Z; D* I7 k' V0 X( B/ [) v8 ?5 i% W- J& t9 w else: + s5 x# N; ^5 P! b7 u0 P) @' l. A return n * factorial(n - 1) ! b; V! `/ M U9 r! x1 ?& } & [6 d+ l: s: e7 j1 Z, j8 N# Example usage7 V5 E. u- E4 q4 Z4 B0 u! ?! |9 F
print(factorial(5)) # Output: 120% x. v1 i; z% m. K! a- s y: _
; S, q% g& j; Y3 z8 e2 PHow Recursion Works ' H r: I1 H( H4 p4 |6 r+ p- _ & z5 x) l6 t6 k& x4 K. K The function keeps calling itself with smaller inputs until it reaches the base case. ' Y5 |4 R1 \0 q& n" s; Q5 ~" ?9 S, Z# k6 X1 X+ T
Once the base case is reached, the function starts returning values back up the call stack. $ \8 P- q/ n" H d I8 Z 2 w- p3 M! E& `/ z7 a. u% B These returned values are combined to produce the final result. ( @ T3 i/ B, l) m , M1 t0 e* A; ~For factorial(5):5 m9 s* M$ T0 ^
* @6 S: C0 g' ]: G; W 9 Y( J- L# |0 Kfactorial(5) = 5 * factorial(4)6 b0 ]# [9 z$ H. W r0 A( g
factorial(4) = 4 * factorial(3)0 [9 B2 F! k8 }, C2 v
factorial(3) = 3 * factorial(2) 4 e; g. m% q# q; [2 J! W. j: }factorial(2) = 2 * factorial(1)9 Z5 r! `1 H# U- ~+ ~2 |
factorial(1) = 1 * factorial(0)7 o* |6 ?. R( J+ p- ^. R
factorial(0) = 1 # Base case + y: Y, A- m( \6 L" P& a& r5 n6 J+ M / h; c8 |4 K. x$ O% T- ^Then, the results are combined:3 D0 g+ U/ w N4 q O! S+ |
3 n+ L4 Z7 E& K. Q
/ `& ~. J9 e1 y
factorial(1) = 1 * 1 = 1 ) M" y6 V, F A! g c, U4 bfactorial(2) = 2 * 1 = 2 $ K+ e* L2 w- afactorial(3) = 3 * 2 = 6 6 R' n* ~# h0 Ffactorial(4) = 4 * 6 = 24: u j" G8 O5 N- K& {/ i! E
factorial(5) = 5 * 24 = 1204 T, ~2 i$ S: {) w/ C
5 [! l; s; ^4 R0 m
Advantages of Recursion . w5 y ~& c. |! O ] 5 ]! z# N" L$ U4 F Simplicity: Recursive solutions are often more intuitive and easier to write for problems that have a natural recursive structure (e.g., tree traversals, divide-and-conquer algorithms). 9 g/ x, I) W- l, c. K0 g 1 ^1 S2 s% b5 r& v- o! d Readability: Recursive code can be more readable and concise compared to iterative solutions.5 y6 {! {# L5 [* y- p) y4 X
$ r2 e3 f& [, x! h ^! \" \
Disadvantages of Recursion0 B/ ?, X* p& ^5 b2 y
6 V. _0 W2 n$ p
Performance Overhead: Each recursive call adds a new layer to the call stack, which can lead to high memory usage and potential stack overflow for deep recursion. : D) M5 c8 m/ i' z& b U) q/ |; ^6 h' @+ E1 ~
Inefficiency: Some problems can be solved more efficiently using iteration (e.g., Fibonacci sequence without memoization). ; d8 u3 S3 Z8 S6 X7 N5 o; x2 m4 m$ [; \: ]
When to Use Recursion 8 f0 V f3 s3 h) J+ K8 O- H ! M' L: ?. ]9 X- b; y7 V; G Problems that can be broken down into smaller, similar subproblems (e.g., tree traversals, sorting algorithms like quicksort and mergesort). , `" v" \4 V: R& ]0 X! n. Q ~8 [7 c8 R( A. @5 x8 f
Problems with a clear base case and recursive case.. i5 u- ]2 w* Y( q9 x' }
% b8 o7 O: S# s$ R7 `2 n
Example: Fibonacci Sequence8 |# p/ b3 U6 C; H& [) r8 y
/ g0 d4 T* f# b6 I$ m
The Fibonacci sequence is another classic example of recursion. Each number is the sum of the two preceding ones: 4 z* e+ C& d1 ?( \& n1 x" A% i: j5 h+ l4 x# t$ K! i1 Z+ [$ T: ?
Base case: fib(0) = 0, fib(1) = 12 P8 a0 @( V P* {: Q% _: X, h5 a4 Z
" n. }, o3 e. Y/ g; {4 G& k$ G0 M Recursive case: fib(n) = fib(n-1) + fib(n-2) 5 o- q" ]: y9 F$ `& P5 K$ J- m ; I1 v" Y/ H6 c/ {python; L9 I5 [' P2 O9 {) Y0 F& I( P
3 c4 l: W# H9 k! O1 K
7 u- `7 ~" T3 f3 c, B* ]3 rdef fibonacci(n):3 o, @- j) @' V6 A2 v
# Base cases ) E& N" M$ }" u# t: _: ?* q! H0 Z if n == 0: * a" N. [9 N2 B9 L2 l return 0 . ^3 K! r6 H7 p& O/ ^# ~1 j; l elif n == 1: , @! ]8 X3 M. k# B K9 v: I8 E return 1 ( K. H; k- b& I3 v" L # Recursive case 9 F2 p% e/ ?5 y+ n# }" l- p* R else: , h8 ^- \# Y8 d return fibonacci(n - 1) + fibonacci(n - 2) " z9 N' G) S# k' }# H/ }" }- `8 J
# Example usage. i& q; ?3 A3 [
print(fibonacci(6)) # Output: 8& u4 g' E: s+ @" X: f
) R) Y9 E5 t4 M( F1 B" e
Tail Recursion 8 S2 D+ l5 _, m( p. ?' f$ H6 I9 ^, c& c6 u3 s/ n
Tail recursion is a special case of recursion where the recursive call is the last operation in the function. Some programming languages optimize tail-recursive functions to avoid stack overflow, but not all languages (e.g., Python does not optimize tail recursion).1 S/ r; L9 i5 I5 p- a
7 W \: \3 a' l/ f3 p. _ H- c. `
In summary, recursion is a fundamental concept in programming that allows you to solve problems by breaking them into smaller, self-similar subproblems. It’s important to define a base case to avoid infinite recursion and to understand the trade-offs between recursion and iteration.作者: nanimarcus 时间: 2025-2-2 00:47
我还让Deepseek 给我讲讲Linux Kernel Driver 现在的开发流程,让一个老同志复习复习,快忘光了。