]>
Commit | Line | Data |
---|---|---|
1d09f67e TL |
1 | // Licensed to the Apache Software Foundation (ASF) under one |
2 | // or more contributor license agreements. See the NOTICE file | |
3 | // distributed with this work for additional information | |
4 | // regarding copyright ownership. The ASF licenses this file | |
5 | // to you under the Apache License, Version 2.0 (the | |
6 | // "License"); you may not use this file except in compliance | |
7 | // with the License. You may obtain a copy of the License at | |
8 | // | |
9 | // http://www.apache.org/licenses/LICENSE-2.0 | |
10 | // | |
11 | // Unless required by applicable law or agreed to in writing, software | |
12 | // distributed under the License is distributed on an "AS IS" BASIS, | |
13 | // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
14 | // See the License for the specific language governing permissions and | |
15 | // limitations under the License. | |
16 | ||
17 | package array_test | |
18 | ||
19 | import ( | |
20 | "fmt" | |
21 | "reflect" | |
22 | "strings" | |
23 | "testing" | |
24 | ||
25 | "github.com/apache/arrow/go/v6/arrow/array" | |
26 | "github.com/apache/arrow/go/v6/arrow/memory" | |
27 | ) | |
28 | ||
29 | func TestBooleanSliceData(t *testing.T) { | |
30 | pool := memory.NewCheckedAllocator(memory.NewGoAllocator()) | |
31 | defer pool.AssertSize(t, 0) | |
32 | ||
33 | values := []bool{true, false, true, true, true, true, true, false, true, false} | |
34 | ||
35 | b := array.NewBooleanBuilder(pool) | |
36 | defer b.Release() | |
37 | ||
38 | for _, v := range values { | |
39 | b.Append(v) | |
40 | } | |
41 | ||
42 | arr := b.NewArray().(*array.Boolean) | |
43 | defer arr.Release() | |
44 | ||
45 | if got, want := arr.Len(), len(values); got != want { | |
46 | t.Fatalf("got=%d, want=%d", got, want) | |
47 | } | |
48 | ||
49 | vs := make([]bool, arr.Len()) | |
50 | ||
51 | for i := range vs { | |
52 | vs[i] = arr.Value(i) | |
53 | } | |
54 | ||
55 | if got, want := vs, values; !reflect.DeepEqual(got, want) { | |
56 | t.Fatalf("got=%v, want=%v", got, want) | |
57 | } | |
58 | ||
59 | tests := []struct { | |
60 | interval [2]int64 | |
61 | want []bool | |
62 | }{ | |
63 | { | |
64 | interval: [2]int64{0, 0}, | |
65 | want: []bool{}, | |
66 | }, | |
67 | { | |
68 | interval: [2]int64{10, 10}, | |
69 | want: []bool{}, | |
70 | }, | |
71 | { | |
72 | interval: [2]int64{0, 5}, | |
73 | want: []bool{true, false, true, true, true}, | |
74 | }, | |
75 | { | |
76 | interval: [2]int64{5, 10}, | |
77 | want: []bool{true, true, false, true, false}, | |
78 | }, | |
79 | { | |
80 | interval: [2]int64{2, 7}, | |
81 | want: []bool{true, true, true, true, true}, | |
82 | }, | |
83 | } | |
84 | ||
85 | for _, tc := range tests { | |
86 | t.Run("", func(t *testing.T) { | |
87 | ||
88 | slice := array.NewSlice(arr, tc.interval[0], tc.interval[1]).(*array.Boolean) | |
89 | defer slice.Release() | |
90 | ||
91 | if got, want := slice.Len(), len(tc.want); got != want { | |
92 | t.Fatalf("got=%d, want=%d", got, want) | |
93 | } | |
94 | ||
95 | vs := make([]bool, slice.Len()) | |
96 | ||
97 | for i := range vs { | |
98 | vs[i] = slice.Value(i) | |
99 | } | |
100 | ||
101 | if got, want := vs, tc.want; !reflect.DeepEqual(got, want) { | |
102 | t.Fatalf("got=%v, want=%v", got, want) | |
103 | } | |
104 | }) | |
105 | } | |
106 | } | |
107 | ||
108 | func TestBooleanSliceDataWithNull(t *testing.T) { | |
109 | pool := memory.NewCheckedAllocator(memory.NewGoAllocator()) | |
110 | defer pool.AssertSize(t, 0) | |
111 | ||
112 | values := []bool{true, false, true, false, false, false, true, false, true, false} | |
113 | valids := []bool{true, false, true, true, true, true, true, false, true, true} | |
114 | ||
115 | b := array.NewBooleanBuilder(pool) | |
116 | defer b.Release() | |
117 | ||
118 | b.AppendValues(values, valids) | |
119 | ||
120 | arr := b.NewArray().(*array.Boolean) | |
121 | defer arr.Release() | |
122 | ||
123 | if got, want := arr.Len(), len(valids); got != want { | |
124 | t.Fatalf("got=%d, want=%d", got, want) | |
125 | } | |
126 | ||
127 | if got, want := arr.NullN(), 2; got != want { | |
128 | t.Fatalf("got=%d, want=%d", got, want) | |
129 | } | |
130 | ||
131 | vs := make([]bool, arr.Len()) | |
132 | ||
133 | for i := range vs { | |
134 | vs[i] = arr.Value(i) | |
135 | } | |
136 | ||
137 | if got, want := vs, values; !reflect.DeepEqual(got, want) { | |
138 | t.Fatalf("got=%v, want=%v", got, want) | |
139 | } | |
140 | ||
141 | tests := []struct { | |
142 | interval [2]int64 | |
143 | nulls int | |
144 | want []bool | |
145 | }{ | |
146 | { | |
147 | interval: [2]int64{2, 9}, | |
148 | nulls: 1, | |
149 | want: []bool{true, false, false, false, true, false, true}, | |
150 | }, | |
151 | { | |
152 | interval: [2]int64{0, 7}, | |
153 | nulls: 1, | |
154 | want: []bool{true, false, true, false, false, false, true}, | |
155 | }, | |
156 | { | |
157 | interval: [2]int64{1, 8}, | |
158 | nulls: 2, | |
159 | want: []bool{false, true, false, false, false, true, false}, | |
160 | }, | |
161 | { | |
162 | interval: [2]int64{2, 7}, | |
163 | nulls: 0, | |
164 | want: []bool{true, false, false, false, true}, | |
165 | }, | |
166 | } | |
167 | ||
168 | for _, tc := range tests { | |
169 | t.Run("", func(t *testing.T) { | |
170 | ||
171 | slice := array.NewSlice(arr, tc.interval[0], tc.interval[1]).(*array.Boolean) | |
172 | defer slice.Release() | |
173 | ||
174 | if got, want := slice.NullN(), tc.nulls; got != want { | |
175 | t.Errorf("got=%d, want=%d", got, want) | |
176 | } | |
177 | ||
178 | if got, want := slice.Len(), len(tc.want); got != want { | |
179 | t.Fatalf("got=%d, want=%d", got, want) | |
180 | } | |
181 | ||
182 | vs := make([]bool, slice.Len()) | |
183 | ||
184 | for i := range vs { | |
185 | vs[i] = slice.Value(i) | |
186 | } | |
187 | ||
188 | if got, want := vs, tc.want; !reflect.DeepEqual(got, want) { | |
189 | t.Fatalf("got=%v, want=%v", got, want) | |
190 | } | |
191 | }) | |
192 | } | |
193 | } | |
194 | ||
195 | func TestBooleanSliceOutOfBounds(t *testing.T) { | |
196 | pool := memory.NewCheckedAllocator(memory.NewGoAllocator()) | |
197 | defer pool.AssertSize(t, 0) | |
198 | ||
199 | values := []bool{true, false, true, false, true, false, true, false, true, false} | |
200 | ||
201 | b := array.NewBooleanBuilder(pool) | |
202 | defer b.Release() | |
203 | ||
204 | for _, v := range values { | |
205 | b.Append(v) | |
206 | } | |
207 | ||
208 | arr := b.NewArray().(*array.Boolean) | |
209 | defer arr.Release() | |
210 | ||
211 | slice := array.NewSlice(arr, 3, 8).(*array.Boolean) | |
212 | defer slice.Release() | |
213 | ||
214 | tests := []struct { | |
215 | index int | |
216 | panic bool | |
217 | }{ | |
218 | { | |
219 | index: -1, | |
220 | panic: true, | |
221 | }, | |
222 | { | |
223 | index: 5, | |
224 | panic: true, | |
225 | }, | |
226 | { | |
227 | index: 0, | |
228 | panic: false, | |
229 | }, | |
230 | { | |
231 | index: 4, | |
232 | panic: false, | |
233 | }, | |
234 | } | |
235 | ||
236 | for _, tc := range tests { | |
237 | t.Run("", func(t *testing.T) { | |
238 | ||
239 | var val bool | |
240 | ||
241 | if tc.panic { | |
242 | defer func() { | |
243 | e := recover() | |
244 | if e == nil { | |
245 | t.Fatalf("this should have panicked, but did not; slice value %v", val) | |
246 | } | |
247 | if got, want := e.(string), "arrow/array: index out of range"; got != want { | |
248 | t.Fatalf("invalid error. got=%q, want=%q", got, want) | |
249 | } | |
250 | }() | |
251 | } else { | |
252 | defer func() { | |
253 | if e := recover(); e != nil { | |
254 | t.Fatalf("unexpected panic: %v", e) | |
255 | } | |
256 | }() | |
257 | } | |
258 | ||
259 | val = slice.Value(tc.index) | |
260 | }) | |
261 | } | |
262 | } | |
263 | ||
264 | func TestBooleanStringer(t *testing.T) { | |
265 | pool := memory.NewCheckedAllocator(memory.NewGoAllocator()) | |
266 | defer pool.AssertSize(t, 0) | |
267 | ||
268 | var ( | |
269 | values = []bool{true, false, true, false, true, false, true, false, true, false} | |
270 | valids = []bool{true, true, false, true, true, true, false, true, true, true} | |
271 | ) | |
272 | ||
273 | b := array.NewBooleanBuilder(pool) | |
274 | defer b.Release() | |
275 | ||
276 | b.AppendValues(values, valids) | |
277 | ||
278 | arr := b.NewArray().(*array.Boolean) | |
279 | defer arr.Release() | |
280 | ||
281 | out := new(strings.Builder) | |
282 | fmt.Fprintf(out, "%v", arr) | |
283 | ||
284 | const want = "[true false (null) false true false (null) false true false]" | |
285 | if got := out.String(); got != want { | |
286 | t.Fatalf("invalid stringer:\ngot= %q\nwant=%q", got, want) | |
287 | } | |
288 | } |