3 (defprotocol NeuralElement
4 "Protocol implemented by any element of a neural network."
5 (spec [this] "Returns the specification")
6 (run [this x] "Evaluates the net")
7 (learn [this d] "Trains the net using d returning the updated net")
8 (inputs [this] "Number of inputs")
9 (outputs [this] "Number of outputs"))
13 clojure.lang.IPersistentMap ; a map initializes a single n
15 (run [this x] ((this :phi) ((this :accum)
17 (map (fn [x w] (when w (* x w)))
18 x (this :weights))))))
20 (inputs [this] (count (this :weights)))
22 clojure.lang.ISeq ; a list of many ns in the same layer
23 (spec [this] (map spec this))
24 (run [this x] (reduce (fn [x layer] (run layer x)) x this))
25 (learn [this d] (reduce (fn [x layer] (run layer d)) d (reverse this)))
26 (inputs [this] (apply max (map inputs this)))
27 (outputs [this] (reduce + (map outputs this)))
28 clojure.lang.IPersistentVector ; a vector of ns in different layers
29 (spec [this] (vec (map spec this)))
30 (run [this x] (reduce (fn [x layer] (run layer x)) x this))
31 (learn [this d] (reduce (fn [x layer] (run layer d)) d (reverse this)))
32 (inputs [this] (inputs (first this)))
33 (outputs [this] (outputs (last this)))
34 clojure.lang.IPersistentSet ; arbitrary graphs, as a set of edges
35 (spec [this] {:vertices (set (map spec (set (apply concat this))))
39 x (apply hash-map (apply concat (map-indexed #(vec %1 %2) x)))]
43 (filter (comp not (comp contains? (keys x)) first) edges)
45 [(second edge) (run (second edge) (get x (first edge)))])
46 (filter (comp (comp contains? (keys x)) first) edges))))))
49 d (apply hash-map (apply concat (map-indexed #(vec %1 %2) d)))]
53 (filter (comp not (comp contains? (keys d)) second) edges)
55 [(first edge) (learn (first edge) (get d (second edge)))])
56 (filter (comp (comp contains? (keys d)) second) edges))))))
57 (inputs [this] (count (set (filter (comp number? first) this))))
58 (outputs [this] (count (set (filter (comp number? second) this)))))
62 ;; show the numbers of inputs and outputs of some networks
63 (let [n {:phi sigmoid :weights [1 2 1 4 1]}]
64 (outputs [n (list n n) n]) ; 1
65 (outputs (list n (list n n) n)) ; 4
66 (inputs [n (list n n) n]) ; 5
67 (inputs (list n (list n n) n))) ; 3
68 ;; evaluate a simple neuron
70 :accum (partial reduce +)