OILS / spec / ysh-expr-compare.test.sh View on Github | oilshell.org

389 lines, 242 significant
1## oils_failures_allowed: 0
2
3#### Exact equality with === and !==
4shopt -s ysh:all
5
6if (3 === 3) {
7 echo 'ok'
8}
9if (3 === '3') {
10 echo 'FAIL'
11}
12
13if (3 !== 3) {
14 echo 'FAIL'
15}
16if (3 !== '3') {
17 echo 'ok'
18}
19
20# dicts
21var d1 = {'a': 1, 'b': 2}
22var d2 = {'a': 1, 'b': 2}
23var d3 = {'a': 1, 'b': 3}
24if (d1 === d2) {
25 echo 'ok'
26}
27if (d1 === d3) {
28 echo 'FAIL'
29}
30if (d1 !== d3) {
31 echo 'ok'
32}
33
34## STDOUT:
35ok
36ok
37ok
38ok
39## END
40
41#### Approximate equality of Str x {Str, Int, Bool} with ~==
42shopt -s ysh:all
43
44# Note: for now there's no !~== operator. Use: not (a ~== b)
45
46if (' foo ' ~== 'foo') {
47 echo Str-Str
48}
49if (' BAD ' ~== 'foo') {
50 echo FAIL
51}
52
53if ('3 ' ~== 3) {
54 echo Str-Int
55}
56if ('4 ' ~== '3') {
57 echo FAIL
58}
59
60if (' true ' ~== true) {
61 echo Str-Bool
62}
63if (' true ' ~== false) {
64 echo FAIL
65}
66
67const matrix = [
68 ' TRue ' ~== true, # case insentiive
69 ' FALse ' ~== false,
70]
71
72# = matrix
73if (matrix === [true, true]) {
74 echo 'bool matrix'
75}
76
77## STDOUT:
78Str-Str
79Str-Int
80Str-Bool
81bool matrix
82## END
83
84#### Wrong Types with ~==
85shopt -s ysh:all
86
87# The LHS side should be a string
88
89echo one
90if (['1'] ~== ['1']) {
91 echo bad
92}
93echo two
94
95if (3 ~== 3) {
96 echo bad
97}
98
99## status: 1
100## STDOUT:
101one
102## END
103
104#### === on float not allowed
105
106$SH -c '
107shopt -s ysh:upgrade
108pp test_ (1.0 === 2.0)
109echo ok
110'
111echo status=$?
112
113$SH -c '
114shopt -s ysh:upgrade
115pp test_ (42 === 3.0)
116echo ok
117'
118echo status=$?
119
120## STDOUT:
121status=3
122status=3
123## END
124
125
126#### floatsEqual()
127
128var x = 42.0
129pp test_ (floatsEqual(42.0, x))
130
131pp test_ (floatsEqual(42.0, x + 1))
132
133## STDOUT:
134(Bool) true
135(Bool) false
136## END
137
138#### Comparison converts from Str -> Int or Float
139echo ' i i' $[1 < 2]
140echo 'si i' $['1' < 2]
141echo ' i si' $[1 < '2']
142echo ---
143
144echo ' f f' $[2.5 > 1.5]
145echo 'sf f' $['2.5' > 1.5]
146echo ' f sf' $[2.5 > '1.5']
147echo ---
148
149echo ' i f' $[4 <= 1.5]
150echo 'si f' $['4' <= 1.5]
151echo ' i sf' $[4 <= '1.5']
152echo ---
153
154echo ' f i' $[5.0 >= 2]
155echo 'sf i' $['5.0' >= 2]
156echo ' f si' $[5.0 >= '2']
157
158## STDOUT:
159 i i true
160si i true
161 i si true
162---
163 f f true
164sf f true
165 f sf true
166---
167 i f false
168si f false
169 i sf false
170---
171 f i true
172sf i true
173 f si true
174## END
175
176#### Comparison of Int
177shopt -s oil:upgrade
178
179if (1 < 2) {
180 echo '<'
181}
182if (2 <= 2) {
183 echo '<='
184}
185if (5 > 4) {
186 echo '>'
187}
188if (5 >= 5) {
189 echo '>='
190}
191
192if (2 < 1) {
193 echo no
194}
195
196## STDOUT:
197<
198<=
199>
200>=
201## END
202
203#### Comparison of Str does conversion to Int
204shopt -s oil:upgrade
205
206if ('2' < '11') {
207 echo '<'
208}
209if ('2' <= '2') {
210 echo '<='
211}
212if ('11' > '2') {
213 echo '>'
214}
215if ('5' >= '5') {
216 echo '>='
217}
218
219if ('2' < '1') {
220 echo no
221}
222
223## STDOUT:
224<
225<=
226>
227>=
228## END
229
230
231#### Mixed Type Comparison does conversion to Int
232shopt -s oil:upgrade
233
234if (2 < '11') {
235 echo '<'
236}
237if (2 <= '2') {
238 echo '<='
239}
240if (11 > '2') {
241 echo '>'
242}
243if (5 >= '5') {
244 echo '>='
245}
246
247if (2 < '1') {
248 echo no
249}
250
251## STDOUT:
252<
253<=
254>
255>=
256## END
257
258
259#### Invalid String is an error
260shopt -s oil:upgrade
261
262if ('3' < 'bar') {
263 echo no
264}
265echo 'should not get here'
266
267## status: 3
268## STDOUT:
269## END
270
271
272#### Bool conversion -- explicit allowed, implicit not allowed
273
274shopt -s ysh:upgrade
275
276if (int(false) < int(true)) {
277 echo '<'
278}
279
280if (int(false) <= int(false) ) {
281 echo '<='
282}
283
284# JavaScript and Python both have this, but Oil prefers being explicit
285
286if (true < false) {
287 echo 'BAD'
288}
289echo 'should not get here'
290
291## status: 3
292## STDOUT:
293<
294<=
295## END
296
297
298#### Chained Comparisons
299shopt -s ysh:upgrade
300
301if (1 < 2 < 3) {
302 echo '123'
303}
304if (1 < 2 <= 2 <= 3 < 4) {
305 echo '123'
306}
307
308if (1 < 2 < 2) {
309 echo '123'
310} else {
311 echo 'no'
312}
313## STDOUT:
314123
315123
316no
317## END
318
319#### List / "Tuple" comparison is not allowed
320
321shopt -s oil:upgrade
322
323var t1 = 3, 0
324var t2 = 4, 0
325var t3 = 3, 1
326
327if (t2 > t1) { echo yes1 }
328if (t3 > t1) { echo yes2 }
329if ( (0,0) > t1) { echo yes3 }
330
331## status: 3
332## STDOUT:
333## END
334
335#### Ternary op behaves like if statement
336shopt -s ysh:upgrade
337
338if ([1]) {
339 var y = 42
340} else {
341 var y = 0
342}
343echo y=$y
344
345var x = 42 if [1] else 0
346echo x=$x
347
348## STDOUT:
349y=42
350x=42
351## END
352
353#### Undefined comparisons
354shopt -s ysh:all
355
356func f() { true }
357var mydict = {}
358var myexpr = ^[123]
359
360var unimpl = [
361 / [a-z]+ /, # Eggex
362 myexpr, # Expr
363 ^(echo hello), # Block
364 f, # Func
365 mydict=>keys, # BoundFunc
366 # These cannot be constructed
367 # - Proc
368 # - Slice
369 # - Range
370]
371
372for val in (unimpl) {
373 try { = val === val }
374 if (_status !== 3) {
375 exit 1
376 }
377}
378## STDOUT:
379## END
380
381#### Non-comparable types in case arms
382var myexpr = ^[123]
383
384case (myexpr) {
385 (myexpr) { echo 123; }
386}
387## status: 3
388## STDOUT:
389## END