Новосибирский Государственный Университет
Опубликован: 05.02.2007 | Доступ: свободный | Студентов: 2252 / 437 | Оценка: 4.30 / 4.23 | Длительность: 10:15:00
Лекция 8:

Имена и контексты

< Лекция 7 || Лекция 8: 123 || Лекция 9 >

Программы для Лисп-интерпретатора.

Цель этой части - помочь на первых шагах избежать некоторых общих ошибок.

(CAR '(A B)) = (CAR (QUOTE(A B)))
8.2.

Функция: CAR

Аргументы: ((A B))

Значение есть A. Заметим, что интерпретатор ожидает список аргументов. Единственным аргументом для CAR является (A B). Добавочная пара скобок возникает т.к. APPLY подается список аргументов.

Можно написать (LAMBDA(X)(CAR X)) вместо просто CAR. Это корректно, но не является необходимым.

(CONS 'A '(B . C))
8.3.

Функция: CONS

Аргументы: (A (B . C))

Результат (A . (B . C)) программа печати выведет как (A B . C)

(CONS '(CAR (QUOTE (A . B))) '(CDR (QUOTE (C . D))) )
8.4.

Функция: CONS

Аргументы: ((CAR (QUOTE (A . B))) (CDR (QUOTE (C . D))))

Значением такого вычисления будет ((CAR (QUOTE (A . B))) . (CDR (QUOTE (C . D))))

Скорее всего это отнюдь не то, что ожидал новичок. Он рассчитывал вместо (CAR (QUOTE (A . B)) получить A и ожидал (A . D) в качестве итогового значения CONS. Кроме очевидного стирания апострофов:

(CONS (CAR (QUOTE (A . B))) (CDR (QUOTE (C . D))) )

ниже приведены еще три правильных способа записи нужной формы. Первый состоит в том, что CAR и CDR части функции задаются с помощью LAMBDA в определении функции. Второй - в переносе CONS в аргументы и вычислении их с помощью EVAL при пустом а-списке. Третий - в принудительном выполнении константных действий в представлении аргументов,

((LAMBDA (X Y) (CONS (CAR X) (CDR Y))) '(A . B) '(C . D))

Функция:

(LAMBDA (X Y) (CONS (CAR X) (CDR Y)))

Аргументы:

((A . B)(C . D))
(EVAL '(CONS (CAR (QUOTE (A . B))) (CDR (QUOTE (C . D)))) Nil)

Функция: EVAL

Аргументы:

((CONS (CAR (QUOTE (A . B))) (CDR (QUOTE (C . D)))) Nil)

Значением того и другого является (A . D)

((LAMBDA (X Y) (CONS (EVAL X) (EVAL Y))) '(CAR (QUOTE (A . B)))
                '(CDR (QUOTE (C . D))) )

Функция:

(LAMBDA (X Y) (CONS (EVAL X) (EVAL Y)))

Аргументы:

((CAR (QUOTE (A . B))) (CDR (QUOTE (C . D))))

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

Таблица 8.1. Clisp: Функции для манипулирования именами и категориями объектов.
(Defconstant Атом Форма ) Глобальная константа
(Defparameter Атом Форма ) Глобальная переменная
(Defun Название Параметры Форма ) Определение функции
(Flet ((Название Параметры Форма) … (Спецификации … Формы …)) Вводит локальные нерекурсивные функции
(Labels ( (Название Параметры Форма) … (Спецификации … Формы …) ) Вводит локальные рекурсивные функции

Выводы:

  • Чтобы выполнить вычисление на реальном Лисп-интерпретаторе необходимо уточнить ряд правил по оформлению текста Лисп-программы.
  • Определения функций можно сделать обозримее именованием выражений. Это дает и экономию на времени вычисления совпадающих форм.
  • При реализации практичной системы программирования возникают дополнительные механизмы, такие как списки свойств атома, повышающие скорость доступа к необходимой информации.
  • Некоторые функции системы необходимо реализовывать в виде машинных подпрограмм. Они образуют ядро системы.
  • При подготовке программ для Лисп-интерпретатора грань между программой и данными может устанавливаться в зависимости от требований к решению задачи.
< Лекция 7 || Лекция 8: 123 || Лекция 9 >