2015-05-12 2 views
1
user=> (map inC#{1 2 3}) 
(2 4 3) 
user=> (into #{} (map inC#{1 2 3})) 
#{4 3 2} 

Есть ли способ применить функцию к набору и сразу вернуть набор?Clojure отображает набор на другой набор напрямую?

+0

[algo.generic] (https://github.com/clojure/algo.generic) предоставляет 'fmap', с реализацией, очень похожей на ваш пример для наборов. AFAIK, ничто не встроенное в язык, поддерживает это. – Alex

ответ

1

несколько более общий способ сделать это состоит в использовании empty:

(defn my-map [f c] 
    (into (empty c) 
     (map f c))) 

Это урожайность следующие результаты:

(my-map inC#{1 2 3}) ;; => #{2 3 4} 
(my-map inc [1 2 3]) ;; => [2 3 4] 
(my-map inc '(1 2 3)) ;; => (4 3 2) 

Это будет работать для других persistent collections.

+0

Как показывает ваш третий пример, 'my-map' будет давать результаты в обратном порядке при задании' seq'. Возможно, было бы лучше, если бы 'my-map' отложил' map', когда ему задали 'seq'. –

1

Как сказал Алекс, fmap от algo.generic предоставляет эту функцию, хотя, если вы посмотрите на источник, он делает то же самое, что и ваш код. Я бы рекомендовал просто поместить вашу функцию в пространство имен util в вашем коде, вероятно, не стоит тянуть всю библиотеку для одной функции.

1

С Clojure 1.7.0 (все еще в бета-версии), вы можете сделать это с помощью датчика:

(into #{} (map inc) #{1 2 3}) 
Смежные вопросы