Clojure 从文件层次结构中创建可折叠集合的惯用方法是什么?

Clojure 从文件层次结构中创建可折叠集合的惯用方法是什么?,clojure,reducers,Clojure,Reducers,有一个文件/目录的集合我想创建一个所有文件的集合。 我希望生成的集合扩展clojure.core.protocols/CollReduce协议 我是否需要扩展协议,或者是否有帮助函数 换句话说。减缩器是否仅在并行减缩中起作用,或者我是否可以使用它们来有效地并行生成可减缩集合 为了说明这个问题,让我展示一个可行的实现,假设文件层次结构不超过两个级别(例如,我们的集合可以包含文件和目录,但目录只能包含文件) 现在,最好使用类似递归的样式(或者更确切地说是转换的级联)来定义扩展,这样它可以适用于所有级

有一个文件/目录的集合我想创建一个所有文件的集合。 我希望生成的集合扩展clojure.core.protocols/CollReduce协议

我是否需要扩展协议,或者是否有帮助函数

换句话说。减缩器是否仅在并行减缩中起作用,或者我是否可以使用它们来有效地并行生成可减缩集合

为了说明这个问题,让我展示一个可行的实现,假设文件层次结构不超过两个级别(例如,我们的集合可以包含文件和目录,但目录只能包含文件)


现在,最好使用类似递归的样式(或者更确切地说是转换的级联)来定义扩展,这样它可以适用于所有级别,但以并行方式执行。与reducer一样,我们可以在reduce中定义提前终止,我希望能够定义生成(集合扩展),当满足某些条件时停止生成(到达目录层次结构树中的文件,如文件示例中所示)

Clojure的集合已经可以还原。有些更适合于并行,因为它们可以比线性时间更快地进行分区。不清楚你想做什么/你到底在问什么。我知道clojure的收藏是可以还原的。问题是如何高效地(以并行方式)将数据填充到它们中。作为一个例子,您可以考虑指向目录的java. Io.Frm。现在,在开始映射之前,我们需要生成一个集合,递归地保存该目录中的所有文件。还原程序能在生成步骤中提供帮助吗?所以您希望并行地重新实现
(defn leaf files[path](filter#(.isFile%)(file seq(clojure.java.io/file path))
?或者对结果进行并行处理?我希望并行生成集合,但不是像您所建议的那样。我想从所有级别的目录访问文件层次结构中的所有叶子。如果可能,最好使用减速机和助手。所以我不会亲自处理线程。我会对seq文件的结果使用一个reducer,正如@a.Webb所描述的。假设fs的行走是快速部分,而并行部分是在每个叶子上采取的动作。此外,考虑到单个FS上的磁盘IO不会随着并行化而变得更快——事实上,并行执行文件操作时的典型结果是由于查找磁盘所花费的时间过多而导致整体性能变差。
(ns user
  [import [java.io File]])

(defn expand [reduction-function]
  (fn [result input]
    (if (.isFile input)
       (reduction-function result input)       
       ; if not a file we assume it's a directory
       (reduce reduction-function result (.listFiles input)))))

(defn process [xfn c]
  (lazy-seq (when-let [s (seq c)]
    (concat ((xfn #(concat %1 (list %2))) '() (first s))
      (process xfn (rest s))))))


(def f (File. "C:\\WORK"))

(process expand [f])    ; => produces list of files