无法在球拍中的用户输入上使用评估

问题描述:

我目前正在学习Scheme(使用Racket),但是我面临的挑战之一是试图执行以下代码,这意味着要使用 eval :

I'm currently learning Scheme (using Racket), but one of the challenges I'm coming upon is trying to execute the following bit of code, which is meant to execute Racket code from user input using eval:

(display (eval (read)))

 

这是到目前为止我观察到的一些奇怪的行为:

Here's some of the weird behavior I've observed so far:

    运行定义时,定义窗口中的
  1. (display(eval(read(read))))会提示您按预期输入键盘.但是,提供输入
    (((lambda(x)(+ x 1))1)
     
    给出错误
    ?:不允许应用功能;没有#%app语法转换器绑定在:((lambda(x)(+ x 1))1)

  1. (display (eval (read))) in the definition window prompts for keyboard input, as expected, when the definitions are run. However, providing the input
    ((lambda (x) (+ x 1)) 1)
     
    gives the error
    ?: function application is not allowed; no #%app syntax transformer is bound in: ((lambda (x) (+ x 1)) 1)

另一方面,使用(display((eval(read))1))并提供输入
(lambda(x)(+ x 1))
 
返回错误
lambda:未绑定的标识符;同样,没有绑定#%app语法转换器:lambda

On the other hand, using (display ((eval (read)) 1)) and providing input
(lambda (x) (+ x 1))
 
returns the error
lambda: unbound identifier; also, no #%app syntax transformer is bound in: lambda

此行为的原因是什么?

似乎您没有设置名称空间.如果您正在文件中运行(评估(读取)),则此操作将无效,因为

It looks like you don't have the namespace set up. If you're running (eval (read)) within a file, it doesn't work because the current-namespace is set to an empty namespace by default. You can set up a namespace with racket/base in it by doing (current-namespace (make-base-namespace)) first:

#lang racket
(current-namespace (make-base-namespace))
(println (eval (read)))

运行该程序并为其输入输入((lambda(x)(+ x 1))1)会导致其打印 2 .

Running this program and giving it the input ((lambda (x) (+ x 1)) 1) results in it printing 2.

它在交互"窗口(奇怪行为列表的项目3)中起作用的原因是,在交互"窗口中,

The reason it worked in the interactions window (item 3 of your weird-behavior list), is that in the interactions window, the current-namespace parameter is set to the namespace of the file.

对于定义窗口(主程序)而言,情况并非如此,因此您必须设置

This is not true for the definitions window, the main program, so you have to set the current-namespace yourself, or pass a namespace in as a second argument to eval:

#lang racket
(define ns (make-base-namespace))
(println (eval (read) ns))