标签: multi-stage-programming

F#报价的另一个限制是什么?

今天早些时候我遇到了F#报价的限制,并在这里问了一个问题:F#报价:变量可能会逃避范围

现在,在将MetaOcaml中出现的http://www.cs.rice.edu/~taha/publications/journal/dspg04a.pdf中的示例转换为F#时,我可能遇到了另一个限制.

这次我有这个MetaOcaml片段:

let rec peval2 p env fenv=
    match p with
    Program ([],e) -> eval2 e env fenv
    | Program (Declaration (s1,s2,e1)::tl,e) ->
         .<let rec f x = .~(eval2 e1 (ext env s2 .<x>.)
                                     (ext fenv s1 .<f>.))
           in .~(peval2 (Program(tl,e)) env (ext fenv s1 .<f>.))>.
Run Code Online (Sandbox Code Playgroud)

我把它转换成了

let rec peval2 p env fenv =
    match p with
    | Program ([], e) -> eval2 e env fenv
    | Program (Declaration (s1, s2, e1) :: tl, e) -> …
Run Code Online (Sandbox Code Playgroud)

f# metaprogramming multi-stage-programming metaocaml

8
推荐指数
1
解决办法
532
查看次数

F#引用:变量可能会逃避范围

我有这段代码:

let rec h n z = if n = 0 then z
                else <@ (fun x -> %(h (n - 1) <@ x + %z @>)) n @>
Run Code Online (Sandbox Code Playgroud)

http://www.cs.rice.edu/~taha/publications/journal/dspg04a.pdf中的MetaOcaml示例转换而来

在本文中,解释了上面的例子将产生以下参数3.<1>.(在MetaOcaml表示法中):

.<(fun x_1 -> (fun x_2 -> (fun x_3 -> x_3 + (x_2 + (x_1 + 1))) 1) 2) 3>.
Run Code Online (Sandbox Code Playgroud)

正如你所看到x的那样被替换为x_1,x_2等等,因为x否则只会引用x最里面的fun.

但是在F#中这是不允许的.我得到编译时错误:"变量'x'在引号中绑定,但用作拼接表达式的一部分.这是不允许的,因为它可能会逃避其范围." 所以问题是:如何改变它以便编译并具有与MetaOcaml输出相同的语义?

更新评论:我使用PowerPack来实际评估报价.但我不认为这与它有任何关系,因为错误是在编译时.到目前为止,QuotationEvaluation仍然有效.但是,我知道它可能不是最有效的实现.

更新Tomas的回答: 我真的不希望它x是全局的,或者是为了逃避范围.但我想要的是相当于

let rec h …
Run Code Online (Sandbox Code Playgroud)

f# metaprogramming multi-stage-programming metaocaml

5
推荐指数
1
解决办法
597
查看次数