Scheme 为什么list ref无法获得正确的参数?
我写了一个快速排序方案(racket) 我是scheme的新手,所以我不太明白为什么list ref无法获得正确的输入Scheme 为什么list ref无法获得正确的参数?,scheme,racket,Scheme,Racket,我写了一个快速排序方案(racket) 我是scheme的新手,所以我不太明白为什么list ref无法获得正确的输入'(99 2 9922) 编辑: 谢谢。我成功了 #lang racket (define (quick-sort xs) (let* ([p (first xs)] [tail (rest xs)] [less (filter (lambda (x) (< x p)) tail)] [greater (filte
'(99 2 9922)
编辑:
谢谢。我成功了
#lang racket
(define (quick-sort xs)
(let* ([p (first xs)]
[tail (rest xs)]
[less (filter (lambda (x) (< x p)) tail)]
[greater (filter (lambda (x) (>= x p)) tail)])
(if (equal? (length xs) 1)
xs
(append (quick-sort less) (list p) (quick-sort greater)))))
#朗球拍
(定义(快速排序xs)
(让*([p(第一个X)]
[尾(其余xs)]
[减去(滤波器(λ(x)(=x p))尾)])
(如果(相等)(长度xs)1)
xs
(追加(无快速排序)(列表p)(快速排序更大‘‘‘)’)
当输入列表为空时,您的代码缺少基本大小写。发生这种情况时,list ref
会失败并出现该错误
顺便说一句,注意(列表参考l0)
的更好名称是(第一个l)
,类似地(列表尾部l1)
最好写为(剩余l)
(还有
car
和cdr
,但如果您是新手,现在可以忽略它们。)当输入列表为空时,您的代码缺少基本大小写。发生这种情况时,list ref
会失败并出现该错误
顺便说一句,注意(列表参考l0)
的更好名称是(第一个l)
,类似地(列表尾部l1)
最好写为(剩余l)
(还有
car
和cdr
,但如果你是新手,现在可以忽略它们。)在设计递归算法时,有两件事是至关重要的:终止条件和递归步骤,以及没有终止条件。跟踪代码正在执行的操作:在第一次执行快速排序时,您将调用:
(append (quick-sort (list 2)) (list 99) (quick-sort (list 9922)))
第一个快速排序
调用将依次调用(快速排序“())
。您的代码不能很好地处理空列表,因为它总是尝试引用数组的第一个元素
添加逻辑以优雅地处理空列表
此外,使用first
和rest
来获取列表的第一个和剩余元素被认为更为实用。在设计递归算法时,有两件事至关重要:终止条件和递归步骤,以及没有终止条件。跟踪代码正在执行的操作:在第一次执行快速排序时,您将调用:
(append (quick-sort (list 2)) (list 99) (quick-sort (list 9922)))
第一个快速排序
调用将依次调用(快速排序“())
。您的代码不能很好地处理空列表,因为它总是尝试引用数组的第一个元素
添加逻辑以优雅地处理空列表
此外,使用first
和rest
来获取列表的第一个和剩余元素被认为更为实用。您可能已经知道这一点,但Racket也有一个内置函数。您可能已经知道这一点,但Racket也有一个内置函数。在您的新代码中,(等长?(长度xs)1)
在每个输入上进行测试,它总是计算xs的整个长度(一个线性运算)。由于您不关心长度是多少,除非它是1,您可以使用像(和(非(null?xs))(null?(cdr xs)))这样的恒定时间测试。
。(我建议的代码片段断言列表不是空的,并且第一个元素后面的部分是空的。后者显然意味着长度为1,但会导致错误,除非列表非空,因此是第一个条件。)在新代码中,(等于?(长度xs)1)
在每个输入上进行测试,它总是计算X的整个长度(一个线性运算)。因为你不在乎长度是多少,除非它是1,你可以使用像(和(不是(null?xs))(null?(cdr xs)))这样的恒定时间测试。
。(我建议的代码片段断言列表不是空的,并且第一个元素后面的部分是空的。后者显然意味着长度为1,但会导致错误,除非列表不是空的,因此是第一个条件。)
(append (quick-sort (list 2)) (list 99) (quick-sort (list 9922)))