Почему AND, OR работает так, как ожидалось, но с XOR отображается ошибка? - PullRequest
0 голосов
/ 04 мая 2020
(define-syntax e.g.
  (syntax-rules (===>)
    ((e.g. proposition)
     (unless proposition
       (error "invalid proposition: "'proposition)))
    ((e.g. proposition ===> value)
     (let ((result proposition))
       (unless (equal? proposition value)
         (error "invalid proposition: "'proposition
                ", expected "value", got "result))))))

(define my-eval
  (let ((ns (make-base-namespace)))
    (lambda (expr) (eval expr ns))))

(e.g. (my-eval '(and #t #t)) ===> #t)
(e.g. (my-eval '(and #t #f)) ===> #f)
(e.g. (my-eval '(or #t #f)) ===> #t)
(e.g. (my-eval '(or #f #f)) ===> #f)
(e.g. (my-eval '(xor #t #t)) ===> #f)
(e.g. (my-eval '(xor #t #f)) ===> #t)

Работает правильно для AND, OR, но для XOR:

XOR: не определено; не может ссылаться на идентификатор перед его определением.

даже жесткий в REPL, кажется, работает правильно:

(xor #t #f)

t

Ответы [ 2 ]

3 голосов
/ 05 мая 2020

Вопрос в том, у кого есть время, чтобы прочитать такие документы целиком?

Вам не нужно читать все это за один присест, но это где информация, и Racket имеет много отличной документации.

eval может быть немного скользким в Racket; вам нужно завершить sh настройку пространства имен, в котором вычисляется выражение eval. Один из способов сделать это - использовать parameterize для создания пустого пространства имен. Это должно происходить внутри выражения lambda, т. Е. Среды, в которой оценивается eval, и вы должны быть уверены, что оба значения racket/base и racket/bool равны require d:

#lang racket

(define-syntax e.g.
  (syntax-rules (===>)
    ((e.g. proposition)
     (unless proposition
       (error "invalid proposition: " 'proposition)))
    ((e.g. proposition ===> value)
     (let ((result proposition))
       (unless (equal? proposition value)
         (error "invalid proposition: " 'proposition
                ", expected " value ", got " result))))))

(define my-eval
  (lambda (expr)
    (parameterize ([current-namespace (make-base-empty-namespace)])
      (namespace-require 'racket/base)
      (namespace-require 'racket/bool)
      (eval expr))))

(e.g. (my-eval '(and #t #t)) ===> #t)
(e.g. (my-eval '(and #t #f)) ===> #f)
(e.g. (my-eval '(or #t #f)) ===> #t)
(e.g. (my-eval '(or #f #f)) ===> #f)
(e.g. (my-eval '(xor #t #t)) ===> #f)
(e.g. (my-eval '(xor #t #f)) ===> #t)
3 голосов
/ 05 мая 2020

Вам необходимо указать racket/bool, который обеспечивает xor, в пространство имен, используемое my-eval. Один из способов сделать это - запустить (my-eval '(require racket/bool)) до ваших xor тестов.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...