Skip to content

Commit c487e48

Browse files
java.util.Map for defrecord, #313
Signed-off-by: Stuart Halloway <[email protected]>
1 parent e0e0b6a commit c487e48

File tree

2 files changed

+38
-2
lines changed

2 files changed

+38
-2
lines changed

src/clj/clojure/core_deftype.clj

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -196,8 +196,23 @@
196196
`(without [~'this ~'k] (if (contains? #{~@(map keyword base-fields)} ~'k)
197197
(dissoc (with-meta (into {} ~'this) ~'__meta) ~'k)
198198
(new ~tagname ~@(remove #{'__extmap} fields)
199-
(not-empty (dissoc ~'__extmap ~'k))))))])]
200-
(let [[i m] (-> [interfaces methods] eqhash iobj ilookup imap)]
199+
(not-empty (dissoc ~'__extmap ~'k))))))])
200+
(ijavamap [[i m]]
201+
[(conj i 'java.util.Map)
202+
(conj m
203+
`(size [~'this] (.count ~'this))
204+
`(isEmpty [~'this] (= 0 (.count ~'this)))
205+
`(containsValue [~'this ~'v] (-> ~'this vals (.contains ~'v)))
206+
`(get [~'this ~'k] (.valAt ~'this ~'k))
207+
`(put [~'this ~'k ~'v] (throw (UnsupportedOperationException.)))
208+
`(remove [~'this ~'k] (throw (UnsupportedOperationException.)))
209+
`(putAll [~'this ~'m] (throw (UnsupportedOperationException.)))
210+
`(clear [~'this] (throw (UnsupportedOperationException.)))
211+
`(keySet [~'this] (set (keys ~'this)))
212+
`(values [~'this] (vals ~'this))
213+
`(entrySet [~'this] (set ~'this)))])
214+
]
215+
(let [[i m] (-> [interfaces methods] eqhash iobj ilookup imap ijavamap)]
201216
`(deftype* ~tagname ~classname ~(conj hinted-fields '__meta '__extmap)
202217
:implements ~(vec i)
203218
~@m)))))

test/clojure/test_clojure/protocols.clj

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030
(map #(.getName %))
3131
(sort)))
3232

33+
(defrecord EmptyRecord [])
3334
(defrecord TestRecord [a b])
3435
(defn r
3536
([a b] (TestRecord. a b))
@@ -157,6 +158,26 @@
157158
(is (= (r 1 3 {} {:c 4}) (merge rec {:b 3 :c 4})))))
158159

159160
(deftest defrecord-interfaces-test
161+
(testing "java.util.Map"
162+
(let [rec (r 1 2)]
163+
(is (= 2 (.size rec)))
164+
(is (= 3 (.size (assoc rec :c 3))))
165+
(is (not (.isEmpty rec)))
166+
(is (.isEmpty (EmptyRecord.)))
167+
(is (.containsKey rec :a))
168+
(is (not (.containsKey rec :c)))
169+
(is (.containsValue rec 1))
170+
(is (not (.containsValue rec 3)))
171+
(is (= 1 (.get rec :a)))
172+
(is (thrown? UnsupportedOperationException (.put rec :a 1)))
173+
(is (thrown? UnsupportedOperationException (.remove rec :a)))
174+
(is (thrown? UnsupportedOperationException (.putAll rec {})))
175+
(is (thrown? UnsupportedOperationException (.clear rec)))
176+
(is (= #{:a :b} (.keySet rec)))
177+
(is (= #{1 2} (set (.values rec))))
178+
(is (= #{[:a 1] [:b 2]} (.entrySet rec)))
179+
180+
))
160181
(testing "IPersistentCollection"
161182
(testing ".cons"
162183
(let [rec (r 1 2)]

0 commit comments

Comments
 (0)