trackler 2.0.6.16 → 2.0.6.17
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/trackler/version.rb +1 -1
- data/tracks/ecmascript/exercises/luhn/example.js +28 -51
- data/tracks/ecmascript/exercises/luhn/luhn.spec.js +16 -41
- data/tracks/fsharp/exercises/simple-cipher/SimpleCipherTest.fs +3 -2
- data/tracks/go/exercises/custom-set/cases_test.go +80 -225
- data/tracks/go/exercises/custom-set/custom_set_test.go +46 -106
- data/tracks/go/exercises/custom-set/example.go +39 -78
- data/tracks/go/exercises/custom-set/example_gen.go +43 -63
- data/tracks/go/exercises/custom-set/example_slice.go +52 -70
- data/tracks/javascript/exercises/luhn/example.js +28 -57
- data/tracks/javascript/exercises/luhn/luhn.spec.js +16 -41
- data/tracks/ruby/README.md +1 -0
- data/tracks/swift/docs/TESTS.md +4 -4
- metadata +2 -2
@@ -6,20 +6,16 @@ package stringset
|
|
6
6
|
//
|
7
7
|
// New() Set
|
8
8
|
// NewFromSlice([]string) Set
|
9
|
-
// (s Set) Add(string) // modify s
|
10
|
-
// (s Set) Delete(string) // modify s
|
11
|
-
// (s Set) Has(string) bool
|
12
|
-
// (s Set) IsEmpty() bool
|
13
|
-
// (s Set) Len() int
|
14
|
-
// (s Set) Slice() []string
|
15
9
|
// (s Set) String() string
|
16
|
-
//
|
17
|
-
//
|
10
|
+
// (s Set) IsEmpty() bool
|
11
|
+
// (s Set) Has(string) bool
|
12
|
+
// Subset(s1, s2 Set) bool
|
18
13
|
// Disjoint(s1, s2 Set) bool
|
14
|
+
// Equal(s1, s2 Set) bool
|
15
|
+
// (s Set) Add(string)
|
19
16
|
// Intersection(s1, s2 Set) Set
|
17
|
+
// Difference(s1, s2 Set) Set
|
20
18
|
// Union(s1, s2 Set) Set
|
21
|
-
// Difference(s1, s2 Set) Set // return s1 ∖ s2
|
22
|
-
// SymmetricDifference(s1, s2 Set) Set
|
23
19
|
//
|
24
20
|
// For Set.String, use '{' and '}', output elements as double-quoted strings
|
25
21
|
// safely escaped with Go syntax, and use a comma and a single space between
|
@@ -28,12 +24,11 @@ package stringset
|
|
28
24
|
|
29
25
|
import (
|
30
26
|
"math/rand"
|
31
|
-
"reflect"
|
32
27
|
"strconv"
|
33
28
|
"testing"
|
34
29
|
)
|
35
30
|
|
36
|
-
const targetTestVersion =
|
31
|
+
const targetTestVersion = 4
|
37
32
|
|
38
33
|
func TestTestVersion(t *testing.T) {
|
39
34
|
if testVersion != targetTestVersion {
|
@@ -79,65 +74,36 @@ func TestNewFromSlice(t *testing.T) {
|
|
79
74
|
}
|
80
75
|
}
|
81
76
|
|
82
|
-
func TestSlice(t *testing.T) {
|
83
|
-
// empty set should produce empty slice
|
84
|
-
s := New()
|
85
|
-
if l := s.Slice(); len(l) != 0 {
|
86
|
-
t.Fatalf(`s.Slice() = %q, want []`, l)
|
87
|
-
}
|
88
|
-
|
89
|
-
// one element:
|
90
|
-
want := []string{"a"}
|
91
|
-
s = NewFromSlice(want)
|
92
|
-
got := s.Slice()
|
93
|
-
if !reflect.DeepEqual(got, want) {
|
94
|
-
t.Fatalf(`%v Slice = %q, want %q`, s, got, want)
|
95
|
-
}
|
96
|
-
|
97
|
-
// two elements:
|
98
|
-
w1 := []string{"a", "b"}
|
99
|
-
w2 := []string{"b", "a"}
|
100
|
-
s = NewFromSlice(w1)
|
101
|
-
got = s.Slice()
|
102
|
-
if !reflect.DeepEqual(got, w1) && !reflect.DeepEqual(got, w2) {
|
103
|
-
t.Fatalf(`%v Slice = %q, want %q`, s, got, w1)
|
104
|
-
}
|
105
|
-
}
|
106
|
-
|
107
77
|
// Trusting NewFromSlice now, remaining tests are table driven, taking data
|
108
78
|
// from cases_test.go and building sets with NewFromSlice.
|
109
79
|
|
110
80
|
// test case types used in cases_test.go
|
81
|
+
|
111
82
|
type (
|
112
|
-
// binary function, bool result (Equal, Subset, Disjoint)
|
113
|
-
binBoolCase struct {
|
114
|
-
set1 []string
|
115
|
-
set2 []string
|
116
|
-
want bool
|
117
|
-
}
|
118
83
|
// unary function, bool result (IsEmpty)
|
119
84
|
unaryBoolCase struct {
|
120
85
|
set []string
|
121
86
|
want bool
|
122
87
|
}
|
123
|
-
// unary function, int result (Len)
|
124
|
-
unaryIntCase struct {
|
125
|
-
set []string
|
126
|
-
want int
|
127
|
-
}
|
128
88
|
// set-element function, bool result (Has)
|
129
89
|
eleBoolCase struct {
|
130
90
|
set []string
|
131
91
|
ele string
|
132
92
|
want bool
|
133
93
|
}
|
134
|
-
//
|
94
|
+
// binary function, bool result (Subset, Disjoint, Equal)
|
95
|
+
binBoolCase struct {
|
96
|
+
set1 []string
|
97
|
+
set2 []string
|
98
|
+
want bool
|
99
|
+
}
|
100
|
+
// set-element operator (Add)
|
135
101
|
eleOpCase struct {
|
136
102
|
set []string
|
137
103
|
ele string
|
138
104
|
want []string
|
139
105
|
}
|
140
|
-
// set-set operator (
|
106
|
+
// set-set operator (Intersection, Difference, Union)
|
141
107
|
binOpCase struct {
|
142
108
|
set1 []string
|
143
109
|
set2 []string
|
@@ -145,45 +111,16 @@ type (
|
|
145
111
|
}
|
146
112
|
)
|
147
113
|
|
148
|
-
|
149
|
-
|
150
|
-
for _, tc := range cases {
|
151
|
-
s1 := NewFromSlice(tc.set1)
|
152
|
-
s2 := NewFromSlice(tc.set2)
|
153
|
-
got := f(s1, s2)
|
154
|
-
if got != tc.want {
|
155
|
-
t.Fatalf("%s(%v, %v) = %t, want %t", name, s1, s2, got, tc.want)
|
156
|
-
}
|
157
|
-
}
|
158
|
-
}
|
159
|
-
|
160
|
-
func TestEqual(t *testing.T) {
|
161
|
-
testBinBool("Equal", Equal, eqCases, t)
|
162
|
-
}
|
163
|
-
|
164
|
-
// With Equal tested, remaining tests use it to judge correctness.
|
165
|
-
|
166
|
-
// helper for testing Add, Delete
|
167
|
-
func testEleOp(name string, op func(Set, string), cases []eleOpCase, t *testing.T) {
|
168
|
-
for _, tc := range cases {
|
114
|
+
func TestIsEmpty(t *testing.T) {
|
115
|
+
for _, tc := range emptyCases {
|
169
116
|
s := NewFromSlice(tc.set)
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
t.Fatalf("%v %s %q = %v, want %v",
|
174
|
-
NewFromSlice(tc.set), name, tc.ele, s, want)
|
117
|
+
got := s.IsEmpty()
|
118
|
+
if got != tc.want {
|
119
|
+
t.Fatalf("%v IsEmpty = %t, want %t", s, got, tc.want)
|
175
120
|
}
|
176
121
|
}
|
177
122
|
}
|
178
123
|
|
179
|
-
func TestAdd(t *testing.T) {
|
180
|
-
testEleOp("Add", Set.Add, addCases, t)
|
181
|
-
}
|
182
|
-
|
183
|
-
func TestDelete(t *testing.T) {
|
184
|
-
testEleOp("Delete", Set.Delete, delCases, t)
|
185
|
-
}
|
186
|
-
|
187
124
|
func TestHas(t *testing.T) {
|
188
125
|
for _, tc := range hasCases {
|
189
126
|
s := NewFromSlice(tc.set)
|
@@ -194,22 +131,14 @@ func TestHas(t *testing.T) {
|
|
194
131
|
}
|
195
132
|
}
|
196
133
|
|
197
|
-
|
198
|
-
|
199
|
-
|
200
|
-
|
201
|
-
|
202
|
-
|
203
|
-
}
|
204
|
-
}
|
205
|
-
}
|
206
|
-
|
207
|
-
func TestLen(t *testing.T) {
|
208
|
-
for _, tc := range lenCases {
|
209
|
-
s := NewFromSlice(tc.set)
|
210
|
-
got := s.Len()
|
134
|
+
// helper for testing Subset, Disjoint, Equal
|
135
|
+
func testBinBool(name string, f func(Set, Set) bool, cases []binBoolCase, t *testing.T) {
|
136
|
+
for _, tc := range cases {
|
137
|
+
s1 := NewFromSlice(tc.set1)
|
138
|
+
s2 := NewFromSlice(tc.set2)
|
139
|
+
got := f(s1, s2)
|
211
140
|
if got != tc.want {
|
212
|
-
t.Fatalf("%v
|
141
|
+
t.Fatalf("%s(%v, %v) = %t, want %t", name, s1, s2, got, tc.want)
|
213
142
|
}
|
214
143
|
}
|
215
144
|
}
|
@@ -222,7 +151,22 @@ func TestDisjoint(t *testing.T) {
|
|
222
151
|
testBinBool("Disjoint", Disjoint, disjointCases, t)
|
223
152
|
}
|
224
153
|
|
225
|
-
|
154
|
+
func TestEqual(t *testing.T) {
|
155
|
+
testBinBool("Equal", Equal, eqCases, t)
|
156
|
+
}
|
157
|
+
|
158
|
+
func TestAdd(t *testing.T) {
|
159
|
+
for _, tc := range addCases {
|
160
|
+
s := NewFromSlice(tc.set)
|
161
|
+
s.Add(tc.ele)
|
162
|
+
want := NewFromSlice(tc.want)
|
163
|
+
if !Equal(s, want) {
|
164
|
+
t.Fatalf("%v Add %q = %v, want %v", NewFromSlice(tc.set), tc.ele, s, want)
|
165
|
+
}
|
166
|
+
}
|
167
|
+
}
|
168
|
+
|
169
|
+
// helper for testing Intersection, Difference, Union
|
226
170
|
func testBinOp(name string, f func(Set, Set) Set, cases []binOpCase, t *testing.T) {
|
227
171
|
for _, tc := range cases {
|
228
172
|
s1 := NewFromSlice(tc.set1)
|
@@ -235,10 +179,6 @@ func testBinOp(name string, f func(Set, Set) Set, cases []binOpCase, t *testing.
|
|
235
179
|
}
|
236
180
|
}
|
237
181
|
|
238
|
-
func TestUnion(t *testing.T) {
|
239
|
-
testBinOp("Union", Union, unionCases, t)
|
240
|
-
}
|
241
|
-
|
242
182
|
func TestIntersection(t *testing.T) {
|
243
183
|
testBinOp("Intersection", Intersection, intersectionCases, t)
|
244
184
|
}
|
@@ -247,8 +187,8 @@ func TestDifference(t *testing.T) {
|
|
247
187
|
testBinOp("Difference", Difference, differenceCases, t)
|
248
188
|
}
|
249
189
|
|
250
|
-
func
|
251
|
-
testBinOp("
|
190
|
+
func TestUnion(t *testing.T) {
|
191
|
+
testBinOp("Union", Union, unionCases, t)
|
252
192
|
}
|
253
193
|
|
254
194
|
func BenchmarkNewFromSlice1e1(b *testing.B) { bench(1e1, b) }
|
@@ -2,12 +2,9 @@
|
|
2
2
|
|
3
3
|
package stringset
|
4
4
|
|
5
|
-
import
|
6
|
-
"fmt"
|
7
|
-
"reflect"
|
8
|
-
)
|
5
|
+
import "fmt"
|
9
6
|
|
10
|
-
const testVersion =
|
7
|
+
const testVersion = 4
|
11
8
|
|
12
9
|
// Set represents some properties of a mathematical set.
|
13
10
|
// Sets are finite and all elements are unique string values.
|
@@ -27,23 +24,18 @@ func NewFromSlice(l []string) Set {
|
|
27
24
|
return s
|
28
25
|
}
|
29
26
|
|
30
|
-
//
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
}
|
43
|
-
|
44
|
-
// Has returns true if e is an element of s.
|
45
|
-
func (s Set) Has(e string) bool {
|
46
|
-
return s[e]
|
27
|
+
// String returns a printable representation of s.
|
28
|
+
func (s Set) String() string {
|
29
|
+
r := "{"
|
30
|
+
i := 0
|
31
|
+
for e := range s {
|
32
|
+
if i > 0 {
|
33
|
+
r += ", "
|
34
|
+
}
|
35
|
+
r += fmt.Sprintf("%q", e)
|
36
|
+
i++
|
37
|
+
}
|
38
|
+
return r + "}"
|
47
39
|
}
|
48
40
|
|
49
41
|
// IsEmpty returns true if s represents the empty set.
|
@@ -51,44 +43,40 @@ func (s Set) IsEmpty() bool {
|
|
51
43
|
return len(s) == 0
|
52
44
|
}
|
53
45
|
|
54
|
-
//
|
55
|
-
func (s Set)
|
56
|
-
return
|
46
|
+
// Has returns true if e is an element of s.
|
47
|
+
func (s Set) Has(e string) bool {
|
48
|
+
return s[e]
|
57
49
|
}
|
58
50
|
|
59
|
-
//
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
for e := range s {
|
64
|
-
l[i] = e
|
65
|
-
i++
|
66
|
-
}
|
67
|
-
return l
|
51
|
+
// Add adds element e to Set s.
|
52
|
+
// If e is already in s, s is unchanged.
|
53
|
+
func (s Set) Add(e string) {
|
54
|
+
s[e] = true
|
68
55
|
}
|
69
56
|
|
70
|
-
//
|
71
|
-
func (
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
if i > 0 {
|
76
|
-
r += ", "
|
57
|
+
// Subset returns true if all elements of s1 are also in s2.
|
58
|
+
func Subset(s1, s2 Set) bool {
|
59
|
+
for e := range s1 {
|
60
|
+
if !s2[e] {
|
61
|
+
return false
|
77
62
|
}
|
78
|
-
r += fmt.Sprintf("%q", e)
|
79
|
-
i++
|
80
63
|
}
|
81
|
-
return
|
64
|
+
return true
|
82
65
|
}
|
83
66
|
|
84
67
|
// Disjoint returns true if s1 and s2 have no elements in common.
|
85
68
|
func Disjoint(s1, s2 Set) bool {
|
86
|
-
|
69
|
+
for e := range s1 {
|
70
|
+
if s2[e] {
|
71
|
+
return false
|
72
|
+
}
|
73
|
+
}
|
74
|
+
return true
|
87
75
|
}
|
88
76
|
|
89
77
|
// Equal returns true if s1 and s2 contain the same elements.
|
90
78
|
func Equal(s1, s2 Set) bool {
|
91
|
-
return
|
79
|
+
return Subset(s1, s2) && Subset(s2, s1)
|
92
80
|
}
|
93
81
|
|
94
82
|
// Intersection constructs a new Set populated with the elements common to
|
@@ -103,19 +91,6 @@ func Intersection(s1, s2 Set) Set {
|
|
103
91
|
return r
|
104
92
|
}
|
105
93
|
|
106
|
-
// Union constructs a new Set populated with elements that appear in s1, s2,
|
107
|
-
// or both.
|
108
|
-
func Union(s1, s2 Set) Set {
|
109
|
-
r := Set{}
|
110
|
-
for e := range s1 {
|
111
|
-
r[e] = true
|
112
|
-
}
|
113
|
-
for e := range s2 {
|
114
|
-
r[e] = true
|
115
|
-
}
|
116
|
-
return r
|
117
|
-
}
|
118
|
-
|
119
94
|
// Difference returns a new Set populated with elements that appear in s1
|
120
95
|
// but not in s2.
|
121
96
|
func Difference(s1, s2 Set) Set {
|
@@ -128,29 +103,15 @@ func Difference(s1, s2 Set) Set {
|
|
128
103
|
return r
|
129
104
|
}
|
130
105
|
|
131
|
-
//
|
132
|
-
|
133
|
-
|
134
|
-
if !s2[e] {
|
135
|
-
return false
|
136
|
-
}
|
137
|
-
}
|
138
|
-
return true
|
139
|
-
}
|
140
|
-
|
141
|
-
// SymmetricDifference constructs a new set populated with elements that are
|
142
|
-
// members of s1 or s2 but not both.
|
143
|
-
func SymmetricDifference(s1, s2 Set) Set {
|
106
|
+
// Union constructs a new Set populated with elements that appear in s1, s2,
|
107
|
+
// or both.
|
108
|
+
func Union(s1, s2 Set) Set {
|
144
109
|
r := Set{}
|
145
110
|
for e := range s1 {
|
146
|
-
|
147
|
-
r[e] = true
|
148
|
-
}
|
111
|
+
r[e] = true
|
149
112
|
}
|
150
113
|
for e := range s2 {
|
151
|
-
|
152
|
-
r[e] = true
|
153
|
-
}
|
114
|
+
r[e] = true
|
154
115
|
}
|
155
116
|
return r
|
156
117
|
}
|
@@ -42,70 +42,58 @@ func strSlice(ns []int) []string {
|
|
42
42
|
|
43
43
|
// The JSON structure we expect to be able to unmarshal into
|
44
44
|
type js struct {
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
Union
|
54
|
-
Intersection binaryOp
|
55
|
-
Difference binaryOp
|
56
|
-
SymmetricDifference binaryOp `json:"symmetric-difference"`
|
45
|
+
IsEmpty unaryBool `json:"empty"`
|
46
|
+
Contains eleBool
|
47
|
+
Subset binaryBool
|
48
|
+
Disjoint binaryBool
|
49
|
+
Equal binaryBool
|
50
|
+
Add eleOp
|
51
|
+
Intersection binaryOp
|
52
|
+
Difference binaryOp
|
53
|
+
Union binaryOp
|
57
54
|
}
|
58
55
|
|
59
|
-
type
|
60
|
-
Description
|
56
|
+
type unaryBool struct {
|
57
|
+
Description string
|
61
58
|
Cases []struct {
|
62
59
|
Description string
|
63
|
-
|
64
|
-
Set2 []int
|
60
|
+
Set []int
|
65
61
|
Expected bool
|
66
62
|
}
|
67
63
|
}
|
68
64
|
|
69
|
-
type
|
70
|
-
Description
|
65
|
+
type eleBool struct {
|
66
|
+
Description string
|
71
67
|
Cases []struct {
|
72
68
|
Description string
|
73
69
|
Set []int
|
74
70
|
Element int
|
75
|
-
Expected []int
|
76
|
-
}
|
77
|
-
}
|
78
|
-
|
79
|
-
type unaryBool struct {
|
80
|
-
Description []string
|
81
|
-
Cases []struct {
|
82
|
-
Description string
|
83
|
-
Set []int
|
84
71
|
Expected bool
|
85
72
|
}
|
86
73
|
}
|
87
74
|
|
88
|
-
type
|
89
|
-
Description
|
75
|
+
type binaryBool struct {
|
76
|
+
Description string
|
90
77
|
Cases []struct {
|
91
78
|
Description string
|
92
|
-
|
93
|
-
|
79
|
+
Set1 []int
|
80
|
+
Set2 []int
|
81
|
+
Expected bool
|
94
82
|
}
|
95
83
|
}
|
96
84
|
|
97
|
-
type
|
98
|
-
Description
|
85
|
+
type eleOp struct {
|
86
|
+
Description string
|
99
87
|
Cases []struct {
|
100
88
|
Description string
|
101
89
|
Set []int
|
102
90
|
Element int
|
103
|
-
Expected
|
91
|
+
Expected []int
|
104
92
|
}
|
105
93
|
}
|
106
94
|
|
107
95
|
type binaryOp struct {
|
108
|
-
Description
|
96
|
+
Description string
|
109
97
|
Cases []struct {
|
110
98
|
Description string
|
111
99
|
Set1 []int
|
@@ -122,9 +110,6 @@ type binaryOp struct {
|
|
122
110
|
var tmpl = `
|
123
111
|
{{/* nested templates for repeated stuff */}}
|
124
112
|
|
125
|
-
{{define "cmts"}}{{range .}}// {{.}}
|
126
|
-
{{end}}{{end}}
|
127
|
-
|
128
113
|
{{define "binaryBool"}} = []binBoolCase{
|
129
114
|
{{range .}}{ // {{.Description}}
|
130
115
|
{{strs .Set1 | printf "%#v"}},
|
@@ -156,46 +141,41 @@ package stringset
|
|
156
141
|
{{if .Commit}}// Commit: {{.Commit}}
|
157
142
|
{{end}}
|
158
143
|
|
159
|
-
{{
|
160
|
-
|
161
|
-
{{template "cmts" .J.Add.Description}}var addCases{{template "eleOp" .J.Add.Cases}}
|
162
|
-
|
163
|
-
{{template "cmts" .J.Delete.Description}}var delCases{{template "eleOp" .J.Delete.Cases}}
|
164
|
-
|
165
|
-
{{range .J.IsEmpty.Description}}// {{.}}
|
166
|
-
{{end}}var emptyCases = []unaryBoolCase{
|
144
|
+
// {{.J.IsEmpty.Description}}
|
145
|
+
var emptyCases = []unaryBoolCase{
|
167
146
|
{{range .J.IsEmpty.Cases}}{ // {{.Description}}
|
168
147
|
{{strs .Set | printf "%#v"}},
|
169
148
|
{{.Expected}},
|
170
149
|
},
|
171
150
|
{{end}}}
|
172
151
|
|
173
|
-
{{
|
174
|
-
|
175
|
-
{{range .J.
|
176
|
-
{{strs .Set | printf "%#v"}},
|
177
|
-
{{.Expected}},
|
178
|
-
},
|
179
|
-
{{end}}}
|
180
|
-
|
181
|
-
{{range .J.Element.Description}}// {{.}}
|
182
|
-
{{end}}var hasCases = []eleBoolCase{
|
183
|
-
{{range .J.Element.Cases}}{ // {{.Description}}
|
152
|
+
// {{.J.Contains.Description}}
|
153
|
+
var hasCases = []eleBoolCase{
|
154
|
+
{{range .J.Contains.Cases}}{ // {{.Description}}
|
184
155
|
{{strs .Set | printf "%#v"}},
|
185
156
|
{{str .Element | printf "%q"}},
|
186
157
|
{{.Expected}},
|
187
158
|
},
|
188
159
|
{{end}}}
|
189
160
|
|
190
|
-
{{
|
161
|
+
// {{.J.Subset.Description}}
|
162
|
+
var subsetCases{{template "binaryBool" .J.Subset.Cases}}
|
163
|
+
|
164
|
+
// {{.J.Disjoint.Description}}
|
165
|
+
var disjointCases{{template "binaryBool" .J.Disjoint.Cases}}
|
191
166
|
|
192
|
-
{{
|
167
|
+
// {{.J.Equal.Description}}
|
168
|
+
var eqCases{{template "binaryBool" .J.Equal.Cases}}
|
193
169
|
|
194
|
-
{{
|
170
|
+
// {{.J.Add.Description}}
|
171
|
+
var addCases{{template "eleOp" .J.Add.Cases}}
|
195
172
|
|
196
|
-
{{
|
173
|
+
// {{.J.Intersection.Description}}
|
174
|
+
var intersectionCases{{template "binaryOp" .J.Intersection.Cases}}
|
197
175
|
|
198
|
-
{{
|
176
|
+
// {{.J.Difference.Description}}
|
177
|
+
var differenceCases{{template "binaryOp" .J.Difference.Cases}}
|
199
178
|
|
200
|
-
{{
|
179
|
+
// {{.J.Union.Description}}
|
180
|
+
var unionCases{{template "binaryOp" .J.Union.Cases}}
|
201
181
|
`
|