【问题标题】:Run a function whose name is in a list运行名称在列表中的函数
【发布时间】:2019-08-16 02:07:36
【问题描述】:

我还在学习球拍。

我必须调用一个未知函数。该函数及其参数在以下列表中:

(define l1 '((function-name parameter1)
(function-name parameter3)))

要运行该功能,我正在做:

(first (car l1)) (second (car l1)) another-parameter

但我得到了错误:

 application: not a procedure;
 expected a procedure that can be applied to arguments
  given: 'function-name
  arguments...:

如何运行 function-name

更新:

我试过 Óscar 的回答:

(eval (first (car l1)) (second (car l1)) another-parameter)

我得到了错误:

 eval: arity mismatch;
 the expected number of arguments does not match the given number
  given: 3
  arguments...:

我也试过了:

(define-namespace-anchor a)
(define ns (namespace-anchor->namespace a))
(eval (first (car l1)) (second (car l1)) another-parameter ns)

我得到了同样的错误:

 eval: arity mismatch;
 the expected number of arguments does not match the given number
  given: 4
  arguments...:

然后,我尝试了这个:

(eval (list (first (car l1)) (second (car l1)) another-parameter))

我得到了错误:

function-name: unbound identifier;
 also, no #%app syntax transformer is bound in: function-name

最后,我试过了:

(eval (list (first (car l1)) (second (car l1)) another-parameter) ns)

我收到来自function-name 的内部错误。但是这个功能,效果很好。

function-name 至少可以是三个(或更多)函数,这就是我之前没有放在这里的原因。它们都将有两个列表作为参数,它们将返回#t 或#f。

其中一个,然后一个正在测试的是:

(define match (lambda (list1 list2) ...))

显然,list1list2 是列表。

更新 2:
我已经尝试过 Óscar 的 Minimal、Complete 和可验证的示例,并且它有效。但是,我已经修改为用于我的工作,它不起作用。看:

(define function-name
  (lambda (list1 list2)
    (append list1 list2)))

(define parameter1 '(1 2))
(define parameter3 '(3 4))
(define another-parameter '(5 6))

(define l1 '((function-name parameter1)
             (function-name parameter3)))

(define-namespace-anchor a)
(define ns (namespace-anchor->namespace a))

(define another-function
  (lambda (l1 the-parameter)
    (cond
      [(eval (list (first (car l1)) (second (car l1)) 'the-parameter) ns) l1])
  )
)

(another-function l1 another-parameter)

我创建了another-function,但由于参数'the-parameter 而失败。它抱怨说:

the-parameter: undefined;
 cannot reference an identifier before its definition

所以问题是当我使用函数的参数作为eval 函数的参数时。

【问题讨论】:

    标签: list functional-programming scheme racket


    【解决方案1】:

    请考虑像这样评估程序:

    (define l1 `((,sin ,(+ 1 2))
                 (,+ 1 2 3)))
    
    (sin (+ 1 2))                 ; ==> 0.14..
    ((caar l1) (cadar l1))        ; ==> 0.14..
    (apply (caar l1) (cdar l1))   ; ==> 0.14..
    
    (+ 1 2 3)                     ; ==> 6
    (apply (caadr l1) (cdadr l1)) ; ==> 6
    

    为什么会这样?好吧。您试图调用过程的名称。通过评估过程名称,您可以获得实际的过程对象。您确实可以评估 REPL 中的过程并查看您得到的结果:

    +  ; ==> #<procedure:+>
    l1 ; ==> ((#<procedure:sin> 3) (#<procedure:+> 1 2 3))
    

    如果 l1 被定义为 '((sin (+ 1 2)) (+ 1 2 3)) 评估它会返回 ((sin (+ 1 2)) (+ 1 2 3)) 所以会有很大的不同。

    当然。使用 quasiquote/unquote 只是一种写法:

    (define l1 (list (list sin (+ 1 2))
                     (list + '1 '2 '3)))
    

    【讨论】:

      【解决方案2】:

      您可以为此使用evalquasiquoting,它适用于您的输入。 注意,你应该这样发布你的问题,这是一个Minimal, Complete, and Verifiable example,任何人都可以复制和运行,而不必猜测你在想什么:

      (define function-name
        (lambda (list1 list2)
          (append list1 list2)))
      
      (define parameter1 '(1 2))
      (define parameter3 '(3 4))
      (define another-parameter '(5 6))
      
      (define l1 '((function-name parameter1)
                   (function-name parameter3)))
      
      (define-namespace-anchor a)
      (define ns (namespace-anchor->namespace a))
      
      (define another-function
        (lambda (l1 the-parameter)
          (cond
            [(eval `(,(first (car l1)) ,(second (car l1)) ',the-parameter) ns)
             l1])))
      
      (another-function l1 another-parameter)
      => '((function-name parameter1) (function-name parameter3))
      

      【讨论】:

      • 感谢您的回答。我已经尝试过了,我得到了错误。我已经更新了我的问题。我正在测试最后一个错误,以了解是否是我的错。谢谢。
      • 一如既往:请发布您用于测试的真实功能。至少是一个骨架,所以我们知道他们期望什么参数,等等。
      • 这应该可行,并注意another-parameter之前的引用:(eval (list (first (car l1)) (second (car l1)) 'another-parameter) ns)。如果您仍然收到来自function-name 的内部错误,则说明function-name 有问题,而不是eval 的工作方式。
      • 我想我找到了我的问题。我已经更新了这个问题,但问题是我正在使用 another-parameter 内部函数中的一个参数作为参数 eval 。非常感谢。
      • 完成。您是否看到为答案提供所有上下文以及制作 MCV 示例所需的所有程序的重要性?真正的问题与您在两次重大修改之前发布的内容大不相同。
      猜你喜欢
      • 1970-01-01
      • 2019-01-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-07-09
      • 1970-01-01
      • 2013-09-12
      • 1970-01-01
      相关资源
      最近更新 更多