【问题标题】:How to read lines from stdin (*in*) in clojure如何从 clojure 中的 stdin (*in*) 读取行
【发布时间】:2010-01-09 16:47:03
【问题描述】:

我正在编写我的第一个 clojure 程序,并且想从标准输入读取行。

当我尝试这个时:

(doall (map #(println %) (line-seq *in*)))

我得到了这个例外:

Exception in thread "main" java.lang.ClassCastException: clojure.lang.LineNumberingPushbackReader cannot be cast to java.io.BufferedReader (test.clj:0)

我在 1.0 和 1.1 版本中得到相同的结果

那么如何将*in* 转换为可以迭代的序列?我原以为这很常见,*in* 本身是可迭代的,但这也不起作用 - 如果我尝试直接使用它,我会得到:

java.lang.IllegalArgumentException: Don't know how to create ISeq from: clojure.lang.LineNumberingPushbackReader (NO_SOURCE_FILE:0)

另外,有没有在 clojure 中进行一般文件处理的示例?

【问题讨论】:

  • 将 (map #(println %) (line-seq.. )) 替换为 (map println (line-seq..)) 会很好

标签: clojure stdin


【解决方案1】:

尝试将*in* 包装在java.io.BufferedReader 中。并且也使用doseq 而不是doall,正如devstopfix 指出的那样:

(doseq [ln (line-seq (java.io.BufferedReader. *in*))]
   (println ln))

请注意,line-seq 被记录为需要 BufferedReader 作为其来源。

【讨论】:

  • 此代码不起作用。我收到错误“doseq 需要一个向量来绑定”尝试是 @devstopfix 写的。它对我有用。
  • @Jason 在这个表单中使用 dorun 而不是 doseq。 doseq 需要一个绑定形式。 dorun 强制执行惰性序列。
  • 这个循环如何使用转义符?
【解决方案2】:

请注意,对于只想阅读一行的任何人,可以使用 read-line 函数。

【讨论】:

    【解决方案3】:

    您可能应该使用doseq 而不是doall

    (doseq [line (line-seq (java.io.BufferedReader. *in*))] 
        (println line))
    

    doall:

    遍历seq的连续next,保留head并返回它,从而导致整个seq一次驻留在内存中。

    doseq:

    不保留序列的头部。返回零。

    【讨论】:

      【解决方案4】:

      对于相当小的输入,以下方法也可以:

      (let [input-string (slurp *in*)]
        (println input-string))
      

      或者,按行分割:

      (let [lines (clojure.string/split-lines (slurp *in*))]
        (println lines))
      

      【讨论】:

      • 什么是“相当小的”?为什么这只适用于“相当小”的输入?
      • @EricIhli, slurp 读取所有可用的输入(直到 EOF,即文件结束)。因此,如果有很多输入——至少有几兆字节或几千兆字节,比方说——那么您将在单个变量input-string 中同时将所有输入加载到内存中。然后之后,您将一次打印出所有内容。如果您的系统中有足够的 RAM,并且如果您使用告诉 Java 使用足够 RAM 的 Java 选项启动 Clojure,那么这将起作用,但您仍然可能需要等待一段时间才能开始看到打印输出。
      猜你喜欢
      • 1970-01-01
      • 2014-01-15
      • 1970-01-01
      • 2012-08-11
      • 2018-06-04
      • 1970-01-01
      • 1970-01-01
      • 2013-12-08
      • 1970-01-01
      相关资源
      最近更新 更多