LINUX.ORG.RU

common lisp - ищется реализация лексических переменных времени компиляции

 


0

3

Хочу, чтобы была возможность определить лексическую переменную, которая бы действовала во время чтения или одного из eval-when.

Эта переменная должна быть связана до конца процесса компиляции, а дальше должна пропасть и не мешаться.

Наверное, для этого нужно поменять compile. Может быть, кому-то попадалась библиотека, которая создаёт слой переносимости между реализациями лиспа?

Или что-нибудь в CDR Process может быть есть?

Или это как-то тривиально делается, а просто я туплю?

★★★★★

Вообще-то, в sbcl все лексические переменные «времени компиляции».

В том смысле, что (let ((x 1)) (f x)) транслируется в (f 1).

Или что понимаешь под словами «должна пропасть и не мешаться»?

monk ★★★★★
()
Ответ на: комментарий от den73

возможность определить лексическую переменную

на уровне файла, а не конкретного определения

А как ты определяешь лексическую переменную на уровне файла?

monk ★★★★★
()
Ответ на: комментарий от monk

По-хорошему, мне надо поменять смысл слова kons (который абстракция для cons), для другой темы, см. выше.

Чтобы в одном файле kons всегда означал одно, а в другом файле он же всегда означал другое. А символ kons был при этом один и тот же.

Это делается, для этого kons как-то диспетчеризоваться по значению, зависящему только от того, в каком файле написано это слово. Т.е., я в начале файла пишу:

(в-этом-файле-kons-означает конс-четвёртый:kons)

И далее все вызовы kons, написанные в этом файле, превращаются в конс-четвёртый:kons.

Но на самом деле это не настолько нужно, можно на это и забить. Тем более я на сегодня уже перерасходовал время на свои проекты, давно пора и поработать :)

den73 ★★★★★
() автор топика
Ответ на: комментарий от monk

что (let ((x 1)) (f x)) транслируется в (f 1).

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

  (let ((x 1))
    (define foo (lambda(f) (set! x (f x)) x)))
связывание действительно лексическое, но не времени компиляции.

filequest
()
Ответ на: комментарий от filequest

На самом деле там создается окружение, потому что может быть что-то типа такого

Замыкание или нет — определяется при компиляции. Но имени лексической переменной всё равно после компиляции не остаётся. Только адрес.

monk ★★★★★
()
Ответ на: комментарий от den73

Чтобы в одном файле kons всегда означал одно, а в другом файле он же всегда означал другое. А символ kons был при этом один и тот же.

А что, обычные замыкания для этого не подходят что-ли?

filequest
()
Ответ на: комментарий от monk

ну, с точки зрения семантики это ничего не меняет, я полагаю. Это кстати, одна из причин, видимо, почему лисп запрещает first-class environments. Они не дадут ему сделать подобные оптимизации.

filequest
()
Ответ на: комментарий от den73

Чтобы в одном файле kons всегда означал одно, а в другом файле он же всегда означал другое. А символ kons был при этом один и тот же.

Если kons — лексические, сделай (let ((kons ...)) ...) на весь файл.

monk ★★★★★
()
Ответ на: комментарий от monk

Надо бы попроще. Что-нибудь, что переносимым между реализациями способом переопределяет compile-file и load. Хотя меня устроит и SBCL. И не *GPL чтобы.

let на весь файл превратит top-level формы в не-toplevel. Обычно это плохо заканчивается.

den73 ★★★★★
() автор топика
Ответ на: комментарий от den73

Сделаю через декорирование функции compile-file. В clcon/Яре оно работает. В Lispworks это делается через defadvice на ту же функцию.

Ставлю галочку.

den73 ★★★★★
() автор топика
Последнее исправление: den73 (всего исправлений: 1)
Ответ на: комментарий от den73

И в IDE конечно, нужно будет поменять. Но я умею.

den73 ★★★★★
() автор топика
Ответ на: комментарий от den73

Надо бы попроще. Что-нибудь, что переносимым между реализациями способом переопределяет compile-file и load.

ASDF FLV

Примерно такая реализация:

(defvar *file-local-variables* ()
   "List of file-local special variables.")

(defun make-variable-file-local (symbol)
  "Make special variable named by SYMBOL have a file-local value."
  (pushnew symbol *file-local-variables*))

(defmethod asdf:perform :around
  ((operation asdf:load-op) (file asdf:cl-source-file))
  "Establish new dynamic bindings for file-local variables."
  (progv *file-local-variables*
    (mapcar #’symbol-value *file-local-variables*)
    (call-next-method)))

(defmethod asdf:perform :around
  ((operation asdf:compile-op) (file asdf:cl-source-file))
  "Establish new dynamic bindings for file-local variables."
  (progv *file-local-variables*
    (mapcar #’symbol-value *file-local-variables*)
    (call-next-method)))

monk ★★★★★
()

den73 and monk

Вы уверены что lisp это ваше? Такую ахинею несете оба на этом сайте. Лиспо-ненавистники позавидуют.

anonymous
()
Ответ на: комментарий от monk

Написал по пьяне, sorry :-) Я просто не понимаю что вы пишете, постоянно какие-то непонятные «проблемы» у вас в лиспе. И код который вы приводите для их «решения».

anonymous
()
Ответ на: комментарий от anonymous

Я просто не понимаю что вы пишете, постоянно какие-то непонятные «проблемы» у вас в лиспе. И код который вы приводите для их «решения».

У одного программиста тоже были «проблемы» в C :-) Или с C :-) И тогда появился C++ и много-много реальных проблем :-)

anonymous
()
Ответ на: комментарий от anonymous

C++ков можно при жизни причислять к святым мученикам :)

anonymous
()
Ответ на: комментарий от filequest

Понял, сразу не догнал чет, хотя и set! там же.

loz ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.