60 функций PicoLisp. Часть 2: Определяем переменные
Перевод. Оригинал здесь
"Что одному человеку константа, то другому - переменная" (Алан Перлис)
Это вторая часть серии "60 функций PicoLisp" и пятая часть цикла Введение в PicoLisp.
В этой части мы поговорим о переменных: как их определять, как с ними работать и каково их внутреннее представление в виртуальной машине PicoLisp.
Все примеры могут быть выполнены в
REPL PicoLisp. Наберите в своей
командной строке pil +
, чтобы открыть оболочку. В начале
предыдущей статьи
вы найдете несколько базовых команд для работы с ней.
Переменную можно определить командой setq
:
: (setq A 3)
-> 3
Вы можете проверить, какое значение присвоено символу A
, введя в REPL
его имя:
: A
-> 3
Мы видим, что символ A
вычисляется в 3. Символы, которые не
определялись, вычисляются в NIL
:
: B
-> NIL
Давайте попробуем что-нибудь посложнее. Например, присвоим символу
Country
значение Japan
:
: (setq Country Japan)
-> NIL
: Country
-> NIL
Не сработало! Country
вычисляется в NIL
.Что же случилось?
В одной из предыдущих статей мы
уже рассказывали, что за исключением списков и чисел всё остальное -
символы. Для интерпретатора Japan
- это символ, и может быть
вычислен. Однако ему не присвоено никакое значение, и он вычисляется
в NIL
, поэтому и Country
присваивается значение NIL
.
Давайте сделаем значением символа Country
не значение символа Japan
,
а сам символ Japan
. Для этого мы отменим вычисление символа с
помощью одинарнрй кавычки: '
. В этом случае значением станет сам
символ, "как есть":
: (setq Country 'Japan)
-> Japan
: Country
-> Japan
: Japan
-> NIL
Это отличие важное, и его нужно запомнить.
Чтобы получить значение символа, используется команда val
:
: (val 'Country)
-> Japan
: (val 'Japan)
-> NIL
Мы ещё вернёмся к функции quote
(сокращённой формой записи которой
является символ одинарной кавычки '
), когда будем обсуждать
анонимные функции (лямбда исчисление) и другие
концепции функционального программирования.
У каждой переменной могут быть свойства (пары ключ-значение), которые
можно добавить функцией put
. Давайте добавим символу Japan
несколько
свойств, а её значением сделаем "JP":
: (put 'Japan 'language "Japanese")
-> Japanese
: (put 'Japan 'continent "Asia")
-> Asia
: (put 'Japan 'island T)
-> T
: (setq Japan "JP")
-> "JP"
Чтобы получить значение свойства, исполтзуется функция get
:
: (get 'Japan 'language) -> "Japanese"
Чтобы значение и свойства символа на экран, используйте функцию show
:
: (show 'Japan)
Japan "JP"
language "Japanese"
island
continent "Asia"
Чтобы полностью понять, как устроены символы и их свойства, давайте
применим к ним знания, изложенные в статье концепции и типы данных. Вот внутреннее
представление символа Japan
:
Заметьте, ключу "island" не нужна ячейка для хранения символа T
,
само его присутствие предполагает, что этот ключ не равен NIL
Теперь можно явно указать на разницу между Japan
и 'Japan
:
Japan
вычисляется в значение ячейкиVAL
, которое равно "JP".'Japan
возвращает указатель на символJapan
. Это та стрелка со словом "Symbol" наверху.
Понимание этой разницы будет полезно, когда мы начнём обсуждать более сложные операции, например, над списками.
Поздравляем, теперь вы знакомы с базовыми арифметическими операциями и созданием переменных в PicoLisp! В следующей статье речь пойдёт о вводе/выводе и циклах.