Кадр списка, включающего ассоциированную функцию

Я посмотрел вокруг в сети и не могу найти ответ на свой запрос. Я был бы очень признателен, если бы кто-то смог дать хороший ответ без оценки рейтинга этого поста.

В Лиспе car, cdr используются в режиме данных, как '(whatever here) что имеет смысл для меня.

Теперь в книге Land of Lisp автор объясняет, как создать текстовый движок, и внезапно он использует следующее описание для создания функции.

(defun describe-location (location nodes)
  (cadr (assoc location nodes)))

Могу я спросить, почему он делает кадры в списке и почему он дает ответ, а не ошибку? не должен ли это быть режим данных, то есть с кавычкой перед открывающей скобкой '(whatever here)?

а также почему он использует асс, как в (assoc location nodes) и не (assoc 'garden *nodes*)

Разве это не второй правильный способ использования assoc? Я, возможно, скучаю по общей картине, и поэтому буду очень признателен, если кто-то объяснит эти ключевые моменты, пожалуйста.

Большое спасибо!

2 ответа

Решение

Я помню книгу, очень весело.

assoc просто возвращает минусы, автомобиль которых равен заданному значению. Это как find функция с параметром :key #'car, Так, например:

CL-USER> (assoc 'a '((a "letter a") (b "letter b") (c "letter c")))
(A "letter a")

поэтому, поскольку мы получаем здесь все минусы, автомобиль которых удовлетворяет критерию, мы можем далее применять cadr для этого минусы и получить соответствующее значение:

CL-USER> (cadr (assoc 'a '((a "letter a") (b "letter b") (c "letter c"))))
"letter a"

Это все для исполняемого кода. В режиме данных вы просто получаете списки, а не формы, поэтому они не будут выполнены, попробуйте сами:

CL-USER> '(car '(a "letter a"))
(CAR '(A "letter a"))

Режим данных позволяет хранить списки как данные, не пытаясь их выполнить. Поэтому автор использует режим данных для определения описаний комнат в игре, но в функции нам нужно выполнить формы, чтобы получить результат.

Что касается второй части вашего вопроса, это все равно просто авторский дизайн. Конечно можно поставить

(assoc 'garden *nodes*)

но это будет иметь тот же эффект и работать только для расположения в саду.

ASSOC это функция. Lisp оценивает все свои аргументы и затем вызывает их с этими значениями. Так работает оценка функций в Лиспе.

(assoc 'garden *nodes*)
  • Лисп видит это assoc это функция. Теперь оценим аргументы.
  • Лисп оценивает 'garden к символу garden,
  • Лисп оценивает *nodes* к значению переменной *nodes*,
  • Лисп звонит assoc с этими ценностями.

Сейчас:

(assoc location *nodes*)
  • Лисп видит это assoc это функция. Теперь оценим аргументы.
  • Лисп оценивает location к значению переменной location,
  • Лисп оценивает *nodes* к значению переменной *nodes*,
  • Лисп звонит assoc с этими ценностями.

Если, например, значение переменной location это символ gardenтогда выше assoc выражения возвращают тот же результат.

Другие вопросы по тегам