简体   繁体   English

clojure过滤器嵌套地图以基于内部地图值返回键

[英]clojure filter nested map to return keys based on inner map values

For this nested map called "tables", 对于这个称为“表格”的嵌套地图,

  (def tables 
   {:tableA {:occupied false :party nil} 
    :tableB {:occupied true :party nil}
    :tableC {:occupied false :party nil}})

how do I filter and get back the keys where :occupied = false ? 我该如何过滤并获取:occupied = false的键?

correct result should be (:tableA :tableC) 正确的结果应该是(:tableA :tableC)

can I do this with "filter" HOF? 我可以使用“过滤器” HOF来做到这一点吗? Should I be using a list comprehension? 我应该使用列表理解吗?

You could do it pretty easily with keep : 您可以使用keep轻松完成此操作:

(keep (fn [[k v]] (if-not (:occupied v) k)) tables)

However, as you observed, using for is often a good solution whenever you're mapping / filtering sequences, especially if you're dealing with nested sequences. 但是,正如您观察到的那样,在映射/过滤序列时,尤其是在处理嵌套序列时,使用for通常是一个很好的解决方案。

(for [[k v] tables :when (not (:occupied v))] k)

I usually prefer using for , especially when I want to use destructuring on the target items. 我通常更喜欢使用for ,尤其是当我想对目标项目使用解构时。 In this case, destructuring is nice for binding the key/value pair with [kv] . 在这种情况下,解构非常适合将键/值对与[kv]绑定。

I'm not sure what your use case is, but can I suggest structuring your data as a set of maps? 我不确定您的用例是什么,但是我可以建议将数据构造为一组地图吗? Sets have certain properties that allow you to query them using relational algebra similar to the way you query tables in SQL. 集具有某些属性,这些属性使您可以使用关系代数来查询它们,类似于在SQL中查询表的方式。 The clojure.set/select function is similar to a WHERE in SQL. clojure.set / select函数类似于SQL中的WHERE。

(use 'clojure.set)

(def tables
    #{{:table "A" :occupied false :party nil} 
      {:table "B" :occupied true :party nil}
      {:table "C" :occupied false :party nil}})

(select #(= false (:occupied %)) tables)

Hope this helps! 希望这可以帮助!

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM