2013-03-14 13 views
6

Tôi có một chức năng mà tôi về cơ bản từ một cuộc thảo luận trong nhóm Clojure google, có một bộ sưu tập và danh sách các hàm có độ dài tùy ý và lọc nó để trả về bộ sưu tập mới chứa tất cả các phần tử trong danh sách gốc ít nhất một trong những chức năng để đánh giá đúng:Clojure một phần ứng dụng - Làm thế nào để có được 'bản đồ' để trả lại một tập hợp các chức năng?

(defn multi-any-filter [coll & funcs] 
    (filter #(some true? ((apply juxt funcs) %)) coll)) 

tôi đang chơi xung quanh với thực hiện một giải pháp khái quát hóa để Project Euler Problem 1, vì vậy tôi đang sử dụng nó như thế này:

(def f3 (fn [x] (= 0 (mod x 3)))) 
(def f5 (fn [x] (= 0 (mod x 5)))) 

(reduce + (multi-any-filter (range 1 1000) f3 f5)) 

Mà cho câu trả lời đúng .

Tuy nhiên, tôi muốn thay đổi nó vì vậy tôi có thể vượt qua ints để nó thay vì chức năng, như

(reduce + (multi-any-filter (range 1 1000) 3 5)) 

nơi tôi có thể thay thế 3 và 5 với một số tùy ý ints và thực hiện chức năng gói của (= 0 (mod xy)) dưới dạng hàm ẩn danh bên trong hàm đa bộ lọc.

Thật không may điều này vượt quá giới hạn khả năng Clojure của tôi. Tôi nghĩ rằng tôi sẽ cần phải làm một cái gì đó với map vào danh sách các arg, nhưng tôi không chắc chắn làm thế nào để có được map để trở về một danh sách các chức năng, mỗi trong số đó đang chờ đợi một đối số khác. Clojure dường như không hỗ trợ currying cách tôi đã học làm thế nào để làm điều đó trong các ngôn ngữ chức năng khác. Có lẽ tôi cần phải sử dụng partial ở đúng vị trí, nhưng tôi không hoàn toàn chắc chắn như thế nào.

Nói cách khác, tôi muốn có thể chuyển một số đối số tùy ý (không phải là hàm) và sau đó có mỗi đối số được gói trong cùng một hàm, và sau đó danh sách hàm được chuyển đến juxt thay cho số funcs trong hàm multi-any-filter của tôi ở trên.

Cảm ơn mọi mẹo!

Trả lời

6
(defn evenly-divisible? [x y] 
    (zero? (mod x y))) 

(defn multi-any-filter [col & nums] 
    (let [partials (map #(fn [x] (evenly-divisible? x %)) nums) 
     f (apply juxt partials)] 
    (filter #(some true? (f %)) col))) 

Tôi không sử dụng partial vì nó áp dụng arg ở vị trí đầu tiên của fn. Chúng tôi muốn nó ở vị trí thứ hai của evenly-divisible? Chúng tôi có thể sắp xếp lại trong evenly-divisible? nhưng sau đó nó sẽ không thực sự nhìn chính xác khi sử dụng nó độc lập.

user=> (reduce + (multi-any-filter (range 1 1000) 3 5)) 
233168 
+0

Bạn đá, đây chính xác là những gì tôi đang tìm kiếm. – kyllo

Các vấn đề liên quan