2012-12-05 30 views
1

沒有人知道如何計算列表中的所有數字或字符,並按以下格式成對打印:(number. number_of_occurrences)。例如:在方案中計數列表中的數字或字符

(計數「(3 1 3 2 1 2 3 3 3))

(。(3 5)(1 2)(2 2))

(計數「(dbacbba))

((d 1)(b 3),(A 2)(C。1))

預先感謝幫助我:)

回答

2

這是一個想法 - 使用散列表來跟蹤事件的數量。這是一個O(n)過程:

(define (counter lst) 
    (let ((counts (make-hash))) 
    (let loop ((lst lst)) 
     (cond ((null? lst) 
      (hash->list counts)) 
      (else 
      (hash-update! counts (car lst) add1 
          (lambda() 0)) 
      (loop (cdr lst))))))) 

另外,這裏的方案更簡單的版本(它不使用filter)的@ mobyte的解決方案 - 注意到,這是O(n^2),因此比基於哈希表的過程效率較低:

(define (counter lst) 
    (map (lambda (e) 
     (cons e (count (curry equal? e) lst))) 
     (remove-duplicates lst))) 

無論哪種方式,它按預期工作:

(counter '(3 1 3 2 1 2 3 3 3)) 
=> '((3 . 5) (2 . 2) (1 . 2)) 

(counter '(d b a c b b a)) 
=> '((b . 3) (a . 2) (d . 1) (c . 1)) 
0

這是Clojure中的解決方案。但我希望這會有所幫助:

(defn counter [l] 
    (map (fn [e] 
     [e (count (filter #{e} l))]) 
     (distinct l))) 

(counter [3 1 3 2 1 2 3 3 3]) 
-> ([3 5] [1 2] [2 2]) 

(counter '(d b a c b b a)) 
-> ([d 1] [b 3] [a 2] [c 1]) 
+0

公平地說,在Clojure中,人們可以做'(頻率[:a:a:b:c:c])'並且獲得'{:a 2, :b 1,:c 2}' –

+0

@JasonLewis很高興知道。最初的目的只是爲了展示算法的想法。 – mobyte