Как проверить / экспортировать / сериализовать среду схемы (guile)

#scheme #environment #guile

#схема #Окружающая среда #хитрость

Вопрос:

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

 (map (lambda (var val) (display (quasiquote (define ,var ,val))
                       (newline))
     (get-current-environment))
  

И затем я бы прочитал / оценил это на другом конце.

Однако, хотя существуют функции, которые возвращают текущую среду, они находятся в некотором внутреннем формате, который я не могу просто map просмотреть. Как я могу «обойти» среду, как указано выше? В качестве альтернативы, как еще я могу скопировать среду в другой процесс?

Ответ №1:

вы можете разложить так называемую «текущую среду» следующим образом:

 (define (get-current-binding-list)
        (let* ((e (current-module))  ;; assume checking current-module

               (h (struct-ref e 0))  ;; index 0 is current vars hashtable
              )
       (hash-map->list cons h)  ;; return a vars binding list
    ))
  

и вы можете вызвать (get-current-binding-list), чтобы получить список привязки переменных в текущем модуле.
Пожалуйста, обратите внимание, что каждый элемент в этом списке представляет собой пару символов и тип переменной, скажем, (symbol-name . тип переменной). Итак, вы можете распечатать это следующим образом:
например, вы получили привязку к var:

 (define abc 5)
  

затем:

 (let ((vl (get-current-binding-list)))
      (assoc-ref vl 'abc)
      )
  

==> #<variable 9bb5108 value: 5>
Этот результат является «типом переменной» переменной «abc». Вы можете получить это значение с помощью процедуры переменной-ref.

Таким образом, вы можете отслеживать все привязки и что-то делать в своем коде, это просто вывести var-name и var-value.

Я знаю, что мой ответ слишком краток, но я думаю, что информации достаточно, чтобы помочь вам найти более подробную информацию в руководстве. Надеюсь, это вам поможет.

Комментарии:

1. Потрясающий ответ. Похоже, что суть этого в том, (current-module) что может быть только хитростью, но это нормально. Я просто хочу понять.

Ответ №2:

На самом деле вы не можете сериализовать среду Scheme. Я даже не знаю, возможно ли (переносимо) сериализовать продолжения. О, и не забудь о FFIS. Порты и потоки также несериализуемы.

Комментарии:

1. О да, я не думал о портах и тому подобном. Однако я не думаю, что мне это нужно для того, что я делаю. Я действительно просто хочу реплицировать переменные и функции в другой среде для поддержки своего рода RPC.