此函数采用一组数字向量并返回它们的交集:
var width = $(".expand").width();
$('.button').click(function() {
$(this).text(function(i, text) {
return text === "Show Details" ? "Hide Details" : "Show Details";
})
var toggleWidth = $(".expand").width() == 0 ? "60%" : "0";
$(".expand").animate({
width: toggleWidth
}, {
duration: 200,
specialEasing: {
width: 'linear'
}
});
});
例如
(defn foo [& sets] (apply clojure.set/intersection (map #(set %) sets)))
如果输入集的元素是带有user=> (foo [1 2 3] [3 4 5 1] [33 3 3 1])
#{1 3}
键的地图,可以用作地图的唯一属性,那么如何实现同样的目的呢?
即。我试图编写一个执行此操作的函数foo2:
:id
有一种简单的方法吗?
或者是收集ID的唯一方法,获取键的交集然后查找输入集中的键?
有没有办法过载'设置函数(并集,交集等),通过定义键值'返回任意对象的键的函数,还是只能使用具有原始值的集合?
答案 0 :(得分:2)
我会做的几乎相同:clojure.set/intersection
,将每个向量转换为:id
的排序集后:
user> (defn intersect [& colls]
(apply clojure.set/intersection
(map #(apply sorted-set-by
(fn [{id1 :id} {id2 :id}] (compare id1 id2))
%)
colls)))
#'user/intersect
user> (intersect [{:id 1} {:id 2} {:id 3}]
[{:id 3} {:id 4} {:id 5} {:id 1}]
[{:id 33} {:id 3} {:id 3} {:id 1}])
#{{:id 1} {:id 3}}
请注意,此方法会将具有相同:id
值的不同地图视为相同,但我想这就是您所需要的。顺便说一下,sorted-set
正好是超载"设置你要问的功能。
你可以创建一个帮助函数,使它看起来更通用:
user> (defn key-comparator [key]
#(compare (key %1) (key %2)))
#'user/key-comparator
user> (defn intersect [& colls]
(apply clojure.set/intersection
(map #(apply sorted-set-by (key-comparator :id) %)
colls)))
#'user/intersect
user> (intersect [{:id 1} {:id 2} {:id 3 :x 1}]
[{:id 3 :x 10} {:id 4} {:id 5} {:id 1}]
[{:id 33} {:id 3 :x 33} {:id 3 :x 2} {:id 1}])
#{{:id 1} {:id 3, :x 33}}
另一种变体是过滤第一个coll中的所有项目,其id在所有其他coll中出现:
user> (defn intersect-2 [c & cs]
(if (empty? cs) c
(filter (fn [{id :id :as itm}]
(every? (partial some #(when (= id (:id %)) %))
cs))
c)))
#'user/intersect-2
user> (intersect-2 [{:id 1} {:id 2} {:id 3 :x 1}]
[{:id 3 :x 10} {:id 4} {:id 5} {:id 1}]
[{:id 33} {:id 3 :x 33} {:id 3 :x 2} {:id 1}])
({:id 1} {:id 3, :x 1})
答案 1 :(得分:2)
编辑:我以前错误地假设具有相同:id
的地图保证具有相同的键和值。如果允许它们不同,这是一个更好的答案:
(defn intersect-by [key-fn data]
(let [normalized (map (fn [map-data]
(->> map-data
(group-by key-fn)
(map (fn [[key val]]
[key (apply merge val)]))
(into {})))
data)
normalized-keys (map (comp set keys) normalized)
intersection (apply clojure.set/intersection normalized-keys)
merged-data (apply merge-with merge normalized)]
(vals (select-keys merged-data intersection))))
#'user/foo
(def data [[{:id 1} {:id 2} {:id 3, :x 3}]
[{:id 3, :y 4} {:id 4} {:id 5} {:id 1}]
[{:id 33} {:id 3} {:id 3, :z 5} {:id 1}]])
#'user/data
(intersect-by :id data)
({:id 1} {:id 3, :x 3, :y 4, :z 5})
如果您假设两个具有相同:id
的地图保证具有相同的键和值,则您的第一个foo函数已经执行此操作:
(def data [[{:id 1} {:id 2} {:id 3}]
[{:id 3} {:id 4} {:id 5} {:id 1}]
[{:id 33} {:id 3} {:id 3} {:id 1}]])
#'user/data
(defn foo [& sets] (apply clojure.set/intersection (map #(set %) sets)))
#'user/foo
(apply foo data)
#{{:id 1} {:id 3}}