如何在Scheme中正确格式化嵌套列表?代码输出异常求助
Scheme列表嵌套问题修复
你需要生成杨辉三角的行列表,预期输出为((1 3 3 1) (1 2 1) (1 1) (1)),但当前代码返回嵌套过深的(((((1 3 3 1) 1 2 1) 1 1) 1)),原代码如下:
(define p-loop (lambda (row col triangle) (if (= row 0) triangle (if (= col 0) (p-loop (- row 1) (- row 1) (append (list triangle))) (p-loop row (- col 1) (append triangle (list (p-nums row col))))))))
其中p-nums返回单个数字,调用(p-loop 4 4 '())触发问题。
问题分析
原代码核心错误是混淆了「当前行的数字列表」和「存储所有行的外层列表」:
- 当
col>0时,(append triangle (list (p-nums row col)))直接将单个数字追加到外层列表triangle中,没有先收集到当前行的子列表里。 - 当
col=0时,(append (list triangle))将整个外层列表嵌套成新的单元素列表,导致每次循环多一层嵌套。
解决方案
方案1:新增参数收集当前行
新增current-row参数专门收集当前行的数字,明确区分「当前行」和「外层列表」:
(define p-loop (lambda (row col triangle current-row) (if (= row 0) triangle (if (= col 0) ;; 把完整当前行加入外层列表,重置当前行处理下一行 (p-loop (- row 1) (- row 1) (cons (cons (p-nums row col) current-row) triangle) '()) ;; 将当前数字加入当前行,继续遍历 (p-loop row (- col 1) triangle (cons (p-nums row col) current-row))))))
调用方式调整为:
(p-loop 4 4 '() '())
方案2:复用外层列表存储当前行
如果不想新增参数,可利用外层列表的第一个元素存储正在构建的当前行:
(define p-loop (lambda (row col triangle) (if (= row 0) triangle (if (= col 0) (p-loop (- row 1) (- row 1) (cons (list (p-nums row col)) triangle)) (let ((current-row (car triangle))) (p-loop row (- col 1) (cons (cons (p-nums row col) current-row) (cdr triangle))))))))
调用方式保持原逻辑:
(p-loop 4 4 '())
两种方案都能生成预期的((1 3 3 1) (1 2 1) (1 1) (1))格式列表。
内容的提问来源于stack exchange,提问作者KemVolt
相关产品推荐
相关产品推荐

