1
2
3
4
5 package specexpr
6
7 import (
8 "reflect"
9 "strings"
10 "testing"
11 )
12
13 func TestParseExpr(t *testing.T) {
14 tests := []struct {
15 expr string
16 want Expr
17 }{
18 {
19 expr: "10",
20 want: Int(10),
21 },
22 {
23 expr: "v",
24 want: Variable("v"),
25 },
26 {
27 expr: "v * 2",
28 want: &BinExpr{OpTimes, Variable("v"), Int(2)},
29 },
30 {
31 expr: "v / 2",
32 want: &BinExpr{OpDiv, Variable("v"), Int(2)},
33 },
34 {
35 expr: "x = y * 2",
36 want: &BinExpr{OpEqual, Variable("x"), &BinExpr{OpTimes, Variable("y"), Int(2)}},
37 },
38 {
39 expr: "a > b",
40 want: &BinExpr{OpGreaterThan, Variable("a"), Variable("b")},
41 },
42 {
43 expr: "a >= b",
44 want: &BinExpr{OpGreaterOrEqual, Variable("a"), Variable("b")},
45 },
46 {
47 expr: "a < b",
48 want: &BinExpr{OpLessThan, Variable("a"), Variable("b")},
49 },
50 {
51 expr: "a <= b",
52 want: &BinExpr{OpLessOrEqual, Variable("a"), Variable("b")},
53 },
54 {
55 expr: "(v * 2) / 3",
56 want: &BinExpr{OpDiv, &BinExpr{OpTimes, Variable("v"), Int(2)}, Int(3)},
57 },
58 {
59 expr: "Int32x4",
60 want: makeVectorL(MakeBasic(&Literal{"int"}, Int(32)), Int(4)),
61 },
62 {
63 expr: "Float64s",
64 want: MakeVector(MakeBasic(&Literal{"float"}, Int(64)), VW()),
65 },
66 {
67 expr: "{B}{N}x{L}",
68 want: makeVectorL(MakeBasic(Variable("B"), Variable("N")), Variable("L")),
69 },
70 {
71 expr: "{B}{N}w{W}",
72 want: MakeVector(MakeBasic(Variable("B"), Variable("N")), Variable("W")),
73 },
74 {
75 expr: "{xB}{xN*2}x{xL/2}",
76 want: makeVectorL(
77 MakeBasic(Variable("xB"), &BinExpr{OpTimes, Variable("xN"), Int(2)}),
78 &BinExpr{OpDiv, Variable("xL"), Int(2)},
79 ),
80 },
81 }
82
83 for _, tc := range tests {
84 t.Run(tc.expr, func(t *testing.T) {
85 got, err := ParseExpr(tc.expr)
86 if err != nil {
87 t.Fatalf("ParseExpr(%q) failed: %v", tc.expr, err)
88 }
89 if !reflect.DeepEqual(got, tc.want) {
90 t.Errorf("ParseExpr(%q) = %+v; want %+v", tc.expr, got, tc.want)
91 }
92 })
93 }
94 }
95
96 func TestParseExprErrors(t *testing.T) {
97 tests := []struct {
98 expr string
99 wantErr string
100 }{
101 {
102 expr: "",
103 wantErr: "unexpected end",
104 },
105 {
106 expr: "12 34",
107 wantErr: "unexpected trailing characters",
108 },
109 {
110 expr: "(12",
111 wantErr: "expected ')'",
112 },
113 {
114 expr: "Int32x",
115 wantErr: "expected number",
116 },
117 {
118 expr: "Int32w",
119 wantErr: "expected number",
120 },
121 {
122 expr: "{B",
123 wantErr: "'{' missing close '}' in symbolic shape at 1",
124 },
125 {
126 expr: "Int32x{}",
127 wantErr: "unexpected character '}'",
128 },
129 }
130
131 for _, tc := range tests {
132 t.Run(tc.expr, func(t *testing.T) {
133 _, err := ParseExpr(tc.expr)
134 if err == nil {
135 t.Fatalf("ParseExpr(%q) succeeded; want error containing %q", tc.expr, tc.wantErr)
136 }
137 if gotErr := err.Error(); !strings.Contains(gotErr, tc.wantErr) {
138 t.Errorf("ParseExpr(%q) returned error %q; want error containing %q", tc.expr, gotErr, tc.wantErr)
139 }
140 })
141 }
142 }
143
View as plain text