[4 T] is the type syntax and is unchanged; it already works in a defvar, a parameter, a field and a return. A let binding is the one position with no type slot, and there the brackets are an array literal of two elements whose second is a type name — which came back as "unknown name rl/Vector2" and cost 32 hand-written Vector2s in one raylib example. (array COUNT TYPE) is a parser form rather than a builtin call, because the second argument is a type and the parser's callers have none. Parse assembles the Tarray itself, so the count takes a constant's name for free and a value in the type position is refused by the type reader's own message. The checker resolves it to Tast.Zero — no new backend node and no new type. (zeroed [4 T]) was proposed first and rejected: the parser can tell, a person cannot. zeroed keeps its job of being inferred; array is the one that is told.
44 lines
1.5 KiB
Plaintext
44 lines
1.5 KiB
Plaintext
;;;; (array COUNT TYPE) — the zeroed fixed array a [let] binding could not ask
|
|
;;;; for. A let has no type slot, so [4 V2] there is an array *literal* of two
|
|
;;;; elements and the second of them is a type name, which is an unknown name
|
|
;;;; and not a helpful error. The type spelling is untouched: `points` below is
|
|
;;;; still declared [3 V2], and the two are the same type, which is the point —
|
|
;;;; the constructor is assignable to the declaration.
|
|
(defstruct V2 [x f32 y f32])
|
|
|
|
(defconst n 3)
|
|
(defvar points [3 V2])
|
|
|
|
(defn sumx [ps [3 V2]] i32
|
|
(let [t (f32 0.0)]
|
|
(dotimes [i 3]
|
|
(set t (+ t (.x (at ps i)))))
|
|
(i32 t)))
|
|
|
|
(defn main [] i32
|
|
;; The case that cost 32 hand-written Vector2s: a local array of structs.
|
|
(let [pts (array 3 V2)]
|
|
(set (.x (at pts 0)) 1.5)
|
|
(set (.x (at pts 2)) 2.5)
|
|
(print (sumx pts)) (println "")) ; 4
|
|
|
|
;; Zeroed, not uninitialised: every element reads as the all-zero value.
|
|
(let [z (array 4 i32)]
|
|
(print (at z 3)) (println "")) ; 0
|
|
|
|
;; The count takes a constant's name, exactly as [n V2] does.
|
|
(let [c (array n V2)]
|
|
(set (.y (at c 1)) 7.0)
|
|
(print (i32 (.y (at c 1)))) (println "")) ; 7
|
|
|
|
;; Element types nest, and the result is assignable to a declaration written
|
|
;; the other way round — same type, two spellings.
|
|
(let [g (array 2 [2 i32])]
|
|
(set (at (at g 1) 1) 9)
|
|
(print (at (at g 1) 1)) (println "")) ; 9
|
|
|
|
(set points (array 3 V2))
|
|
(set (.x (at points 0)) 4.0)
|
|
(print (sumx points)) (println "") ; 4
|
|
0)
|