-
Notifications
You must be signed in to change notification settings - Fork 9
Gotcha: Two dimensional arrays
Brian Marick edited this page Mar 20, 2016
·
4 revisions
I occasionally fool myself with expressions like this:
user=> (built-like {[ALL ALL] [required-path integer?]} [])
[]
I'm thinking "I want a two-dimensional array with all-integer cells". []
seems wrong, since it's not a two-dimensional array.
The issue is that there is no such type as "two-dimensional array" in Clojure. Instead, there are vectors that contain zero or more other vectors. Under that interpretation, []
fits perfectly. The type description says "the argument must be a collection with zero or more elements; if there are any elements, they too must be collections. Their elements, if any, must be integers."
But try convincing my subconscious of that.
If you want to match my subconscious's idea of a two-dimensional array, you want something like this:
user=> (require '[structural-typing.preds :as pred])
user=> (type! :TwoD {[] [pred/not-empty? vector? required-path]
[ALL] vector?
[ALL ALL] integer?})
user=> (built-like :TwoD [])
Value should be a non-empty collection; it is `[]`
=> nil
user=> (built-like :TwoD [ 1 [] ])
[0 ALL] encountered `1` when a collection was expected
[0] should be `vector?`; it is `1`
=> nil
;; The `required-path` is needed to disallow `nil`, since
;; (built-like {[] [any-checkers]} nil) => nil
user=> (built-like :TwoD nil)
The whole value should not be `nil`
=> nil