go: parse.sx — composite literals + 8 tests [nothing]
Some checks failed
Test, Build, and Deploy / test-build-deploy (push) Failing after 26s
Some checks failed
Test, Build, and Deploy / test-build-deploy (push) Failing after 26s
Adds Go composite literals:
T{} empty
T{1, 2} positional
T{X: 1, Y: 2} keyed
[]int{1, 2, 3} slice
[3]int{1, 2, 3} array
map[string]int{"a": 1} map
pkg.Point{1, 2} qualified
[]Point{Point{1,2}, Point{3,4}} nested
AST: (list :composite TYPE-OR-EXPR ELEMS). Each element is an
expression or (list :kv KEY VALUE).
Two parser entry points feed the same AST:
* gp-parse-primary picks up type-prefixed composites by seeing
a literal-type starter ([, map, struct) and parsing a type
first, then optionally a '{' body.
* The postfix loop picks up ident-prefixed composites — after
any base expression, '{' wraps it as a composite literal.
Known limitation flagged in plan: when statement parsing arrives,
the postfix '{' branch will misread `if cond { ... }` as a composite
literal. Standard fix: parser-mode flag suppressing composite-lit
disambiguation in control-flow expression positions. Added to plan.
Elided types in nested composites (`[][]int{{1,2},{3,4}}` with the
inner `{1,2}` typed implicitly) deferred.
parse 114/114, total 243/243.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -650,6 +650,70 @@
|
||||
(list (list :ty-name "int")))
|
||||
(list :method "Close" (list) (list))))))
|
||||
|
||||
(go-parse-test
|
||||
"comp: Point{} (empty)"
|
||||
(go-parse "Point{}")
|
||||
(list :composite (ast-var "Point") (list)))
|
||||
|
||||
(go-parse-test
|
||||
"comp: Point{1, 2} (positional)"
|
||||
(go-parse "Point{1, 2}")
|
||||
(list
|
||||
:composite (ast-var "Point")
|
||||
(list (ast-literal "1") (ast-literal "2"))))
|
||||
|
||||
(go-parse-test
|
||||
"comp: Point{X: 1, Y: 2} (keyed)"
|
||||
(go-parse "Point{X: 1, Y: 2}")
|
||||
(list
|
||||
:composite (ast-var "Point")
|
||||
(list
|
||||
(list :kv (ast-var "X") (ast-literal "1"))
|
||||
(list :kv (ast-var "Y") (ast-literal "2")))))
|
||||
|
||||
(go-parse-test
|
||||
"comp: []int{1, 2, 3} (slice literal)"
|
||||
(go-parse "[]int{1, 2, 3}")
|
||||
(list
|
||||
:composite (list :ty-slice (list :ty-name "int"))
|
||||
(list (ast-literal "1") (ast-literal "2") (ast-literal "3"))))
|
||||
|
||||
(go-parse-test
|
||||
"comp: [3]int{1, 2, 3} (array literal)"
|
||||
(go-parse "[3]int{1, 2, 3}")
|
||||
(list
|
||||
:composite (list :ty-array (ast-literal "3") (list :ty-name "int"))
|
||||
(list (ast-literal "1") (ast-literal "2") (ast-literal "3"))))
|
||||
|
||||
(go-parse-test
|
||||
"comp: map[string]int{\"a\": 1, \"b\": 2} (map literal)"
|
||||
(go-parse "map[string]int{\"a\": 1, \"b\": 2}")
|
||||
(list
|
||||
:composite (list :ty-map (list :ty-name "string") (list :ty-name "int"))
|
||||
(list
|
||||
(list :kv (ast-literal "a") (ast-literal "1"))
|
||||
(list :kv (ast-literal "b") (ast-literal "2")))))
|
||||
|
||||
(go-parse-test
|
||||
"comp: pkg.Point{1, 2} (qualified type)"
|
||||
(go-parse "pkg.Point{1, 2}")
|
||||
(list
|
||||
:composite (list :select (ast-var "pkg") "Point")
|
||||
(list (ast-literal "1") (ast-literal "2"))))
|
||||
|
||||
(go-parse-test
|
||||
"comp: nested — []Point{Point{1,2}, Point{3,4}}"
|
||||
(go-parse "[]Point{Point{1, 2}, Point{3, 4}}")
|
||||
(list
|
||||
:composite (list :ty-slice (list :ty-name "Point"))
|
||||
(list
|
||||
(list
|
||||
:composite (ast-var "Point")
|
||||
(list (ast-literal "1") (ast-literal "2")))
|
||||
(list
|
||||
:composite (ast-var "Point")
|
||||
(list (ast-literal "3") (ast-literal "4"))))))
|
||||
|
||||
(go-parse-test "non-primary: '+'" (go-parse "+") nil)
|
||||
|
||||
(go-parse-test "non-primary: empty" (go-parse "") nil)
|
||||
|
||||
Reference in New Issue
Block a user