Следующий код схемы работает нормально:
(define (same-parity x . numbers-input)
(define (check-parity a) (= (remainder x 2) (remainder a 2)))
(define (iter numbers-left)
(cond ((null? numbers-left) nil)
((check-parity (car numbers-left)) (cons (car numbers-left) (iter (cdr numbers-left))))
(else (iter (cdr numbers-left)))))
(cons x (iter numbers-input)))
Предполагается, что список будет выводиться с первым элементом, являющимся целым числом x, а последующими элементами будут все целые числа из числового ввода, которые имеют одинаковые паритет как x.
Если кому-то интересно, это моя попытка решить упражнение 2.20 из книги Структура и интерпретация компьютерных программ .
Теперь я хотел заменить (номера машин слева) и (номера дисков слева) переменными "first" и "rest".
(define (same-parity x . numbers-input)
(define (check-parity a) (= (remainder x 2) (remainder a 2)))
(define (iter numbers-left)
(let ((first (car numbers-left))
(rest (cdr numbers-left)))
(cond ((null? numbers-left) nil)
((check-parity first) (cons first (iter rest)))
(else (iter rest)))))
(cons x (iter numbers-input)))
Попытка вызова этой функции теперь дает мне ошибку:
> (same-parity 1 2 3 4 5)
. . mcar: contract violation
expected: mpair?
given: ()
Ракетка подсвечивает (номер машины слева) внутри оператора let. Даже когда я на самом деле никогда не вызываю «first» или «rest» в теле функции и просто оставляю его прежним, я получаю ту же ошибку.
Однако в следующем коде я пытался скопируйте структуру описанной выше процедуры в простом определении теста и, как ни странно, это работает так, как вы ожидаете.
(define (test x . testlist)
(define (test2 test2list)
(let ((first (car test2list)))
first))
(test2 testlist))
> (test 1 2 3 4 5)
2
Оказывается, что если я заменю свой (cond ...) в моей исходной программе на простой вызов тоже хорошо работает, так что как-то оператор (cond ...) запрещает мне использовать переменные.
Я знаю, что это очень специфичная вещь c, и я не знаю, это когда-либо действительно имеет значение (за исключением, может быть, если вы хотите сделать код более читабельным), но мне бы очень хотелось узнать, почему именно он так себя ведет.
Любое понимание будет оценено!