Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/clojure/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Clojure中的代码生成_Clojure - Fatal编程技术网

Clojure中的代码生成

Clojure中的代码生成,clojure,Clojure,(免责声明:我是一名C#guy。我刚刚开始学习Clojure。) 我知道Clojure程序能够自行操作或轻松生成其他程序。它与Clojure中的所有内容都是数据结构有关,生成程序与创建任何其他类型的数据结构都是一样的 有没有人有一个很好的示例程序(或对它的引用)来说明这一点 如果生成一个程序,能否将该程序“序列化”到磁盘以供以后执行 仅供参考: 我想玩遗传编程。我想生成许多小程序,对它们进行评估,并使用成功的程序生成更多的程序。看到更多和更多 我想我在这里误用了术语。我所说的程序实际上是指clo

(免责声明:我是一名C#guy。我刚刚开始学习Clojure。)

我知道Clojure程序能够自行操作或轻松生成其他程序。它与Clojure中的所有内容都是数据结构有关,生成程序与创建任何其他类型的数据结构都是一样的

有没有人有一个很好的示例程序(或对它的引用)来说明这一点

如果生成一个程序,能否将该程序“序列化”到磁盘以供以后执行

仅供参考:

  • 我想玩遗传编程。我想生成许多小程序,对它们进行评估,并使用成功的程序生成更多的程序。看到更多和更多

  • 我想我在这里误用了术语。我所说的程序实际上是指clojure列表,而代码生成则是指“列表生成”。我只需要列表来包含实际的函数调用和参数。我需要能够控制这个列表何时被“执行”

  • 在文章中找到部分答案:

    pr
    prn
    功能如下 他们的印刷品和印刷品副本, 但它们的输出形式可以 被Clojure的读者阅读。他们 适用于序列化Clojure 数据结构。默认情况下,他们会这样做 不打印元数据。这可能是 通过绑定特殊符号进行更改
    *将meta*
    打印为
    true


    这至少回答了我问题的第二部分。

    看看宏。比如说,

    (defmacro defmacro-
      "Same as defmacro but yields a private definition"
      [name & decls]
      (list* `defmacro (with-meta name (assoc (meta name) :private true)) decls))
    

    对于宏,您不需要序列化宏扩展;编译将自动使用它。

    Clojure是一种LISP,这意味着它是一种语言:数据和代码之间没有结构上的区别。它的清单一路向下。它还有一个可扩展的编译器,允许您通过宏扩展语法。但从你的问题陈述来看,你并不清楚你真的需要这样的东西


    您基本上是在运行生成列表(实际上是下一代程序)的代码,保存它们,然后运行新程序。除非您的世代进化需要新的语法,否则您可能不需要求助于宏。

    这个问题有些误导,因为Clojure在用Java字节码编译Clojure源代码时也会执行动态“代码生成”

    在本例中,我相信您对Lisp宏特别感兴趣。我认为这些可能很有趣:

    请注意,Clojure中的宏与常见的Lisp宏(2型Lisp)非常相似,与Scheme宏不太相似

    快乐的编码。

    考虑一下
    (+12)
    。作为数据,它是一个由三项组成的链表:符号
    +
    和两个整数。作为代码,它是一个函数调用,表示“使用这两个整数作为参数调用名为
    +
    的函数,并给出结果”。您可以对该列表执行任何操作,也可以对任何其他数据列表执行任何操作。您还可以
    eval
    it以获得结果

    user> (def x '(+ 1 2))
    #'user/x
    user> (first x)
    +
    user> (rest x)
    (1 2)
    user> (map class x)
    (clojure.lang.Symbol java.lang.Integer java.lang.Integer)
    user> (reverse x)
    (2 1 +)
    user> (concat x (rest x))
    (+ 1 2 1 2)
    user> (eval x)
    3
    user> (defn foo []
            (let [ops '[+ - * /]               ; SO's lisp-highlighting sucks
                  nums (repeatedly #(rand-int 5))
                  expr (list* (rand-elt ops) (take 10 nums))]
              (prn expr)
              (prn (eval expr))))
    user> (foo)
    (+ 4 1 0 3 2 3 4 3 1 2)
    23
    nil
    user> (foo)
    (- 1 3 2 2 1 2 1 4 0 1)
    -15
    nil
    

    这正是我想要的!如果我理解正确,每个“程序”都将是一个列表。我只需要一种方法,用函数调用和参数“生成”该列表,然后在完成后“执行”该列表。我想我只需要生成一个以引号为前缀的列表,这样列表就不会被“评估”。你会想阅读并理解这一页:记住,我是一个C#guy。我在这里肯定误用了“代码生成”这个术语。我想我真正想说的是“列表生成”,但是列表需要包含实际的函数调用。