list - List passed to procedure converts into list of list inside the procedure
问题描述
I'm debugging this code on DrRacket:
#lang racket
(define last-element-on-list
(lambda l
(cond ((null? l) '())
((null? (cdr l)) (car l))
(else (last-element-on-list (cdr l)))
)
)
)
(define lst '(
(n 25 f +)
(s 25 m +)
(ll 20 no -)))
(list-ref lst 0)
(last-element-on-list (list-ref lst 0))
The code (list-ref lst 0)
returns '(n 25 f +)
, but when I get into the procedure last-element-on-list
the parameter l
has the value ((n 25 f +))
.
Why l
is a list of list in procedure last-element-on-list
?
解决方案
There's a difference between the (lambda (x) ...)
form and the (lambda x ...)
form.
Observe the difference between these two examples:
;; Example 1.
(define f
(lambda (x)
(if (list? x)
(display "x is a list!")
(display "x is not a list"))))
(f 1) ; Displays "x is not a list".
;; Example 2.
(define g
(lambda x
(if (list? x)
(display "x is a list!")
(display "x is not a list"))))
(g 1) ; Displays "x is a list!".
The (lambda x ...)
form allows the lambda to take any number of arguments, with all the arguments put into a list bound to x
in the lambda's body. i.e. x
is the list of arguments.
That's why when you give g
a list (e.g. (g '(1 2 3))
), x
will be '((1 2 3))
(a list of lists).
To fix your code:
(define last-element-on-list
(lambda (l) ; <- ATTENTION.
(cond ((null? l) '()) ; FIXME: raise error instead.
((null? (cdr l)) (car l))
(else (last-element-on-list (cdr l))))))
You can read more about lambda
in The Racket Guide. In particular, look at section 4.4.1 (Declaring a Rest Argument).
推荐阅读
- c - 无论如何要创建一个 if 语句来打印一个输出,说明我已经超过了多少公斤?
- selenium-webdriver - 如何用 selenium 和 java 修复这个 NullPointerException?
- java - 我的 CloudWatch 日志中缺少 AWSRequestId
- anypoint-studio - 如何在 Mulesoft 4 中使用 dataweave 获取流中的当前路径?
- c# - asp mvc core 3 自定义属性验证的客户端验证
- c++ - 使用不同的 clang 格式版本统一输出
- python - Jupyter notebook 使用 numpy 导入其他 .py 文件不起作用
- php - 发布可以被多个页面访问的数据
- c# - 为什么我的程序在多次将数据从 c++ dll 传递到 c# 后停止?(没有错误信息)
- python-3.6 - 在类中避免使用“self.”和变量样板