Search Clojure数据结构遍历/搜索

Search Clojure数据结构遍历/搜索,search,data-structures,clojure,traversal,Search,Data Structures,Clojure,Traversal,我希望能够做到这样: (search data list? (fn [x] (and (list? x) (= 4 (first x)))) (fn [x] (and (set? x) (contains x 3)))) 并让它递归搜索嵌套的数据结构数据: 首先是最浅的列表(例如,可能在一组集合中) 然后在最浅的列表中,谁是第一个元素是4 然后在包含3的最浅集合的列表中 最后返回步骤3中找到的项目列表 在我重新发明轮子之前,有没有一种标准的方法可以做到这一点?Clojure有标准

我希望能够做到这样:

(search data 
  list?
  (fn [x] (and (list? x) (= 4 (first x))))
  (fn [x] (and (set? x) (contains x 3))))
并让它递归搜索嵌套的数据结构
数据

  • 首先是最浅的列表(例如,可能在一组集合中)
  • 然后在最浅的列表中,谁是第一个元素是
    4
  • 然后在包含3的最浅集合的列表中
  • 最后返回步骤3中找到的项目列表

  • 在我重新发明轮子之前,有没有一种标准的方法可以做到这一点?

    Clojure有标准的方法来穿越树木。您应该查看clojure.zip以及tree seq

    (loop [loc dz] 
      (if (end? loc) 
        (root loc) 
        (recur (next (if (= '* (node loc)) 
                       (replace loc '/) loc))))) 
    
    (loop [loc dz] 
      (if (end? loc) 
        (root loc) 
        (recur (next (if (= '* (node loc)) 
                       (remove loc) loc))))) 
    

    clojure.zip末尾的这两个示例似乎清楚地表明,您不需要知道数据结构是什么样子的。循环的使用还表明,在遍历数据结构时,您可以轻松地仅累积感兴趣的值。

    Clojure有遍历树的标准方法。您应该查看clojure.zip以及tree seq

    (loop [loc dz] 
      (if (end? loc) 
        (root loc) 
        (recur (next (if (= '* (node loc)) 
                       (replace loc '/) loc))))) 
    
    (loop [loc dz] 
      (if (end? loc) 
        (root loc) 
        (recur (next (if (= '* (node loc)) 
                       (remove loc) loc))))) 
    

    clojure.zip末尾的这两个示例似乎清楚地表明,您不需要知道数据结构是什么样子的。loop的使用还表明,在遍历数据结构时,您可以轻松地仅累积感兴趣的值。

    zip如果您已经知道自己的数据结构,以及应该在更大的结构中查找的位置,那么它似乎很有用。tree seq有点事与愿违,因为它屏蔽了所讨论的数据结构,并使其显示为一个序列,因此您甚至不知道自己是在列表的列表中,还是在集合的集合中。我给了你一个+1,因为它们在构建我正在寻找的函数时可能会很有用。例如,我可以设置tree seq的children函数来注入标记,当我遍历子结构时,这些标记会让我知道。然后,消费搜索功能可以跟踪深度以及它在更大结构中的位置。如果您已经知道自己的数据结构,以及应该在更大结构中查找的位置,那么zip似乎很有用。tree seq有点事与愿违,因为它屏蔽了所讨论的数据结构,并使其显示为一个序列,因此您甚至不知道自己是在列表的列表中,还是在集合的集合中。我给了你一个+1,因为它们在构建我正在寻找的函数时可能会很有用。例如,我可以设置tree seq的children函数来注入标记,当我遍历子结构时,这些标记会让我知道。然后,消费搜索功能可以跟踪深度以及它在更大结构中的位置。