1; <PLAINTEXT>
2; Examples for Eager Comprehensions in [outer..inner|expr]-Convention
3; ===================================================================
4;
5; sebastian.egner@philips.com, Eindhoven, The Netherlands, 26-Dec-2007.
6; Scheme R5RS (incl. macros), SRFI-23 (error).
7;
8; Running the examples in Scheme48 (version 1.1):
9;   ,open srfi-23
10;   ,load ec.scm
11;   (define my-open-output-file open-output-file)
12;   (define my-call-with-input-file call-with-input-file)
13;   ,load examples.scm
14;
15; Running the examples in PLT/DrScheme (version 317):
16;   (load "ec.scm")
17;   (define (my-open-output-file filename)
18;     (open-output-file filename 'replace 'text) )
19;   (define (my-call-with-input-file filename thunk)
20;     (call-with-input-file filename thunk 'text) )
21;   (load "examples.scm")
22;
23; Running the examples in SCM (version 5d7):
24;   (require 'macro) (require 'record)
25;   (load "ec.scm")
26;   (define my-open-output-file open-output-file)
27;   (define my-call-with-input-file call-with-input-file)
28;   (load "examples.scm")
29
30(import ec)
31
32
33(define my-open-output-file open-output-file)
34(define my-call-with-input-file call-with-input-file)
35
36
37; Tools for checking results
38; ==========================
39
40(define (my-equal? x y)
41  (cond
42   ((or (boolean? x)
43        (null? x)
44        (symbol? x)
45        (char? x)
46        (input-port? x)
47        (output-port? x) )
48    (eqv? x y) )
49   ((string? x)
50    (and (string? y) (string=? x y)) )
51   ((vector? x)
52    (and (vector? y)
53         (my-equal? (vector->list x) (vector->list y)) ))
54   ((pair? x)
55    (and (pair? y)
56         (my-equal? (car x) (car y))
57         (my-equal? (cdr x) (cdr y)) ))
58   ((real? x)
59    (and (real? y)
60         (eqv? (exact? x) (exact? y))
61         (if (exact? x)
62             (= x y)
63             (< (abs (- x y)) (/ 1 (expt 10 6))) ))) ; will do here
64   (else
65    (error "unrecognized type" x) )))
66
67(define my-check-correct 0)
68(define my-check-wrong   0)
69
70(define-syntax my-check
71  (syntax-rules (=>)
72    ((my-check ec => desired-result)
73     (begin
74       (newline)
75       (write (quote ec))
76       (newline)
77       (let ((actual-result ec))
78         (display "  => ")
79         (write actual-result)
80         (if (my-equal? actual-result desired-result)
81             (begin
82               (display " ; correct")
83               (set! my-check-correct (+ my-check-correct 1)) )
84             (begin
85               (display " ; *** wrong ***, desired result:")
86               (newline)
87               (display "  => ")
88               (write desired-result)
89               (set! my-check-wrong (+ my-check-wrong 1)) ))
90         (newline) )))))
91
92
93; ==========================================================================
94; do-ec
95; ==========================================================================
96
97(my-check
98  (let ((x 0)) (do-ec (set! x (+ x 1))) x)
99  => 1)
100
101(my-check
102  (let ((x 0)) (do-ec (:range i 10) (set! x (+ x 1))) x)
103  => 10)
104
105(my-check
106  (let ((x 0)) (do-ec (:range n 10) (:range k n) (set! x (+ x 1))) x)
107  => 45)
108
109
110; ==========================================================================
111; list-ec and basic qualifiers
112; ==========================================================================
113
114(my-check (list-ec 1) => '(1))
115
116(my-check (list-ec (:range i 4) i) => '(0 1 2 3))
117
118(my-check (list-ec (:range n 3) (:range k (+ n 1)) (list n k))
119  => '((0 0) (1 0) (1 1) (2 0) (2 1) (2 2)) )
120
121(my-check
122  (list-ec (:range n 5) (if (even? n)) (:range k (+ n 1)) (list n k))
123  => '((0 0) (2 0) (2 1) (2 2) (4 0) (4 1) (4 2) (4 3) (4 4)) )
124
125(my-check
126  (list-ec (:range n 5) (not (even? n)) (:range k (+ n 1)) (list n k))
127  => '((1 0) (1 1) (3 0) (3 1) (3 2) (3 3)) )
128
129(my-check
130  (list-ec (:range n 5)
131           (and (even? n) (> n 2))
132           (:range k (+ n 1))
133           (list n k) )
134  => '((4 0) (4 1) (4 2) (4 3) (4 4)) )
135
136(my-check
137  (list-ec (:range n 5)
138           (or (even? n) (> n 3))
139           (:range k (+ n 1))
140           (list n k) )
141  => '((0 0) (2 0) (2 1) (2 2) (4 0) (4 1) (4 2) (4 3) (4 4)) )
142
143(my-check
144 (let ((x 0)) (list-ec (:range n 10) (begin (set! x (+ x 1))) n) x)
145 => 10 )
146
147(my-check
148 (list-ec (nested (:range n 3) (:range k n)) k)
149 => '(0 0 1) )
150
151
152; ==========================================================================
153; Other comprehensions
154; ==========================================================================
155
156(my-check (append-ec '(a b)) => '(a b))
157(my-check (append-ec (:range i 0) '(a b)) => '())
158(my-check (append-ec (:range i 1) '(a b)) => '(a b))
159(my-check (append-ec (:range i 2) '(a b)) => '(a b a b))
160
161(my-check (string-ec #\a) => (string #\a))
162(my-check (string-ec (:range i 0) #\a) => "")
163(my-check (string-ec (:range i 1) #\a) => "a")
164(my-check (string-ec (:range i 2) #\a) => "aa")
165
166(my-check (string-append-ec "ab") => "ab")
167(my-check (string-append-ec (:range i 0) "ab") => "")
168(my-check (string-append-ec (:range i 1) "ab") => "ab")
169(my-check (string-append-ec (:range i 2) "ab") => "abab")
170
171(my-check (vector-ec 1) => (vector 1))
172(my-check (vector-ec (:range i 0) i) => (vector))
173(my-check (vector-ec (:range i 1) i) => (vector 0))
174(my-check (vector-ec (:range i 2) i) => (vector 0 1))
175
176(my-check (vector-of-length-ec 1 1) => (vector 1))
177(my-check (vector-of-length-ec 0 (:range i 0) i) => (vector))
178(my-check (vector-of-length-ec 1 (:range i 1) i) => (vector 0))
179(my-check (vector-of-length-ec 2 (:range i 2) i) => (vector 0 1))
180
181(my-check (sum-ec 1) => 1)
182(my-check (sum-ec (:range i 0) i) => 0)
183(my-check (sum-ec (:range i 1) i) => 0)
184(my-check (sum-ec (:range i 2) i) => 1)
185(my-check (sum-ec (:range i 3) i) => 3)
186
187(my-check (product-ec 1) => 1)
188(my-check (product-ec (:range i 1 0) i) => 1)
189(my-check (product-ec (:range i 1 1) i) => 1)
190(my-check (product-ec (:range i 1 2) i) => 1)
191(my-check (product-ec (:range i 1 3) i) => 2)
192(my-check (product-ec (:range i 1 4) i) => 6)
193
194(my-check (min-ec 1) => 1)
195(my-check (min-ec (:range i 1) i) => 0)
196(my-check (min-ec (:range i 2) i) => 0)
197
198(my-check (max-ec 1) => 1)
199(my-check (max-ec (:range i 1) i) => 0)
200(my-check (max-ec (:range i 2) i) => 1)
201
202(my-check (first-ec #f 1) => 1)
203(my-check (first-ec #f (:range i 0) i) => #f)
204(my-check (first-ec #f (:range i 1) i) => 0)
205(my-check (first-ec #f (:range i 2) i) => 0)
206
207(my-check
208  (let ((last-i -1))
209    (first-ec #f (:range i 10) (begin (set! last-i i)) i)
210    last-i )
211  => 0 )
212
213(my-check (last-ec #f 1) => 1)
214(my-check (last-ec #f (:range i 0) i) => #f)
215(my-check (last-ec #f (:range i 1) i) => 0)
216(my-check (last-ec #f (:range i 2) i) => 1)
217
218(my-check (any?-ec #f) => #f)
219(my-check (any?-ec #t) => #t)
220(my-check (any?-ec (:range i 2 2) (even? i)) => #f)
221(my-check (any?-ec (:range i 2 3) (even? i)) => #t)
222
223(my-check (every?-ec #f) => #f)
224(my-check (every?-ec #t) => #t)
225(my-check (every?-ec (:range i 2 2) (even? i)) => #t)
226(my-check (every?-ec (:range i 2 3) (even? i)) => #t)
227(my-check (every?-ec (:range i 2 4) (even? i)) => #f)
228
229(my-check
230 (let ((sum-sqr (lambda (x result) (+ result (* x x)))))
231   (fold-ec 0 (:range i 10) i sum-sqr) )
232 => 285 )
233
234(my-check
235 (let ((minus-1 (lambda (x) (- x 1)))
236       (sum-sqr (lambda (x result) (+ result (* x x)))))
237   (fold3-ec (error "wrong") (:range i 10) i minus-1 sum-sqr) )
238 => 284 )
239
240(my-check
241 (fold3-ec 'infinity (:range i 0) i min min)
242 => 'infinity )
243
244
245; ==========================================================================
246; Typed generators
247; ==========================================================================
248
249(my-check (list-ec (:list x '()) x) => '())
250(my-check (list-ec (:list x '(1)) x) => '(1))
251(my-check (list-ec (:list x '(1 2 3)) x) => '(1 2 3))
252(my-check (list-ec (:list x '(1) '(2)) x) => '(1 2))
253(my-check (list-ec (:list x '(1) '(2) '(3)) x) => '(1 2 3))
254
255(my-check (list-ec (:string c "") c) => '())
256(my-check (list-ec (:string c "1") c) => '(#\1))
257(my-check (list-ec (:string c "123") c) => '(#\1 #\2 #\3))
258(my-check (list-ec (:string c "1" "2") c) => '(#\1 #\2))
259(my-check (list-ec (:string c "1" "2" "3") c) => '(#\1 #\2 #\3))
260
261(my-check (list-ec (:vector x (vector)) x) => '())
262(my-check (list-ec (:vector x (vector 1)) x) => '(1))
263(my-check (list-ec (:vector x (vector 1 2 3)) x) => '(1 2 3))
264(my-check (list-ec (:vector x (vector 1) (vector 2)) x) => '(1 2))
265(my-check
266 (list-ec (:vector x (vector 1) (vector 2) (vector 3)) x)
267 => '(1 2 3))
268
269(my-check (list-ec (:range x -2) x) => '())
270(my-check (list-ec (:range x -1) x) => '())
271(my-check (list-ec (:range x  0) x) => '())
272(my-check (list-ec (:range x  1) x) => '(0))
273(my-check (list-ec (:range x  2) x) => '(0 1))
274
275(my-check (list-ec (:range x  0  3) x) => '(0 1 2))
276(my-check (list-ec (:range x  1  3) x) => '(1 2))
277(my-check (list-ec (:range x -2 -1) x) => '(-2))
278(my-check (list-ec (:range x -2 -2) x) => '())
279
280(my-check (list-ec (:range x 1 5  2) x) => '(1 3))
281(my-check (list-ec (:range x 1 6  2) x) => '(1 3 5))
282(my-check (list-ec (:range x 5 1 -2) x) => '(5 3))
283(my-check (list-ec (:range x 6 1 -2) x) => '(6 4 2))
284
285(my-check (list-ec (:real-range x 0.0 3.0)     x) => '(0. 1. 2.))
286(my-check (list-ec (:real-range x 0   3.0)     x) => '(0. 1. 2.))
287(my-check (list-ec (:real-range x 0   3   1.0) x) => '(0. 1. 2.))
288
289(my-check
290 (string-ec (:char-range c #\a #\z) c)
291 => "abcdefghijklmnopqrstuvwxyz" )
292
293(my-check
294 (begin
295   (let ((f (my-open-output-file "tmp1.out")))
296     (do-ec (:range n 10) (begin (write n f) (newline f)))
297     (close-output-port f))
298   (my-call-with-input-file "tmp1.out"
299    (lambda (port) (list-ec (:port x port read) x)) ))
300 => (list-ec (:range n 10) n) )
301
302(my-check
303 (begin
304   (let ((f (my-open-output-file "tmp1.out")))
305     (do-ec (:range n 10) (begin (write n f) (newline f)))
306     (close-output-port f))
307   (my-call-with-input-file "tmp1.out"
308     (lambda (port) (list-ec (:port x port) x)) ))
309 => (list-ec (:range n 10) n) )
310
311
312; ==========================================================================
313; The special generators :do :let :parallel :while :until
314; ==========================================================================
315
316(my-check (list-ec (:do ((i 0)) (< i 4) ((+ i 1))) i) => '(0 1 2 3))
317
318(my-check
319 (list-ec
320  (:do (let ((x 'x)))
321       ((i 0))
322       (< i 4)
323       (let ((j (- 10 i))))
324       #t
325       ((+ i 1)) )
326  j )
327 => '(10 9 8 7) )
328
329(my-check (list-ec (:let x 1) x) => '(1))
330(my-check (list-ec (:let x 1) (:let y (+ x 1)) y) => '(2))
331(my-check (list-ec (:let x 1) (:let x (+ x 1)) x) => '(2))
332
333(my-check
334 (list-ec (:parallel (:range i 1 10) (:list x '(a b c))) (list i x))
335 => '((1 a) (2 b) (3 c)) )
336
337(my-check
338 (list-ec (:while (:range i 1 10) (< i 5)) i)
339 => '(1 2 3 4) )
340
341(my-check
342 (list-ec (:until (:range i 1 10) (>= i 5)) i)
343 => '(1 2 3 4 5) )
344
345; with generator that might use inner bindings
346
347(my-check
348 (list-ec (:while (:list i '(1 2 3 4 5 6 7 8 9)) (< i 5)) i)
349 => '(1 2 3 4) )
350; Was broken in original reference implementation as pointed
351; out by sunnan@handgranat.org on 24-Apr-2005 comp.lang.scheme.
352; Refer to http://groups-beta.google.com/group/comp.lang.scheme/
353; browse_thread/thread/f5333220eaeeed66/75926634cf31c038#75926634cf31c038
354
355(my-check
356 (list-ec (:until (:list i '(1 2 3 4 5 6 7 8 9)) (>= i 5)) i)
357 => '(1 2 3 4 5) )
358
359(my-check
360 (list-ec (:while (:vector x (index i) '#(1 2 3 4 5))
361		  (< x 10))
362	  x)
363 => '(1 2 3 4 5))
364; Was broken in reference implementation, even after fix for the
365; bug reported by Sunnan, as reported by Jens-Axel Soegaard on
366; 4-Jun-2007.
367
368; combine :while/:until and :parallel
369
370(my-check
371 (list-ec (:while (:parallel (:range i 1 10)
372                             (:list j '(1 2 3 4 5 6 7 8 9)))
373                  (< i 5))
374          (list i j))
375 => '((1 1) (2 2) (3 3) (4 4)))
376
377(my-check
378 (list-ec (:until (:parallel (:range i 1 10)
379                             (:list j '(1 2 3 4 5 6 7 8 9)))
380                  (>= i 5))
381          (list i j))
382 => '((1 1) (2 2) (3 3) (4 4) (5 5)))
383
384; check that :while/:until really stop the generator
385
386(my-check
387 (let ((n 0))
388   (do-ec (:while (:range i 1 10) (begin (set! n (+ n 1)) (< i 5)))
389          (if #f #f))
390   n)
391 => 5)
392
393(my-check
394 (let ((n 0))
395   (do-ec (:until (:range i 1 10) (begin (set! n (+ n 1)) (>= i 5)))
396          (if #f #f))
397   n)
398 => 5)
399
400(my-check
401 (let ((n 0))
402   (do-ec (:while (:parallel (:range i 1 10)
403                             (:do () (begin (set! n (+ n 1)) #t) ()))
404                  (< i 5))
405          (if #f #f))
406   n)
407 => 5)
408
409(my-check
410 (let ((n 0))
411   (do-ec (:until (:parallel (:range i 1 10)
412                             (:do () (begin (set! n (+ n 1)) #t) ()))
413                  (>= i 5))
414          (if #f #f))
415   n)
416 => 5)
417
418; ==========================================================================
419; The dispatching generator
420; ==========================================================================
421
422(my-check (list-ec (: c '(a b)) c) => '(a b))
423(my-check (list-ec (: c '(a b) '(c d)) c) => '(a b c d))
424
425(my-check (list-ec (: c "ab") c) => '(#\a #\b))
426(my-check (list-ec (: c "ab" "cd") c) => '(#\a #\b #\c #\d))
427
428(my-check (list-ec (: c (vector 'a 'b)) c) => '(a b))
429(my-check (list-ec (: c (vector 'a 'b) (vector 'c)) c) => '(a b c))
430
431(my-check (list-ec (: i 0) i) => '())
432(my-check (list-ec (: i 1) i) => '(0))
433(my-check (list-ec (: i 10) i) => '(0 1 2 3 4 5 6 7 8 9))
434(my-check (list-ec (: i 1 2) i) => '(1))
435(my-check (list-ec (: i 1 2 3) i) => '(1))
436(my-check (list-ec (: i 1 9 3) i) => '(1 4 7))
437
438(my-check (list-ec (: i 0.0 1.0 0.2) i) => '(0. 0.2 0.4 0.6 0.8))
439
440(my-check (list-ec (: c #\a #\c) c) => '(#\a #\b #\c))
441
442(my-check
443 (begin
444   (let ((f (my-open-output-file "tmp1.out")))
445     (do-ec (:range n 10) (begin (write n f) (newline f)))
446     (close-output-port f))
447   (my-call-with-input-file "tmp1.out"
448     (lambda (port) (list-ec (: x port read) x)) ))
449 => (list-ec (:range n 10) n) )
450
451(my-check
452 (begin
453   (let ((f (my-open-output-file "tmp1.out")))
454     (do-ec (:range n 10) (begin (write n f) (newline f)))
455     (close-output-port f))
456   (my-call-with-input-file "tmp1.out"
457     (lambda (port) (list-ec (: x port) x)) ))
458 => (list-ec (:range n 10) n) )
459
460
461; ==========================================================================
462; With index variable
463; ==========================================================================
464
465(my-check (list-ec (:list c (index i) '(a b)) (list c i)) => '((a 0) (b 1)))
466(my-check (list-ec (:string c (index i) "a") (list c i)) => '((#\a 0)))
467(my-check (list-ec (:vector c (index i) (vector 'a)) (list c i)) => '((a 0)))
468
469(my-check
470 (list-ec (:range i (index j) 0 -3 -1) (list i j))
471 => '((0 0) (-1 1) (-2 2)) )
472
473(my-check
474 (list-ec (:real-range i (index j) 0 1 0.2) (list i j))
475 => '((0. 0) (0.2 1) (0.4 2) (0.6 3) (0.8 4)) )
476
477(my-check
478 (list-ec (:char-range c (index i) #\a #\c) (list c i))
479 => '((#\a 0) (#\b 1) (#\c 2)) )
480
481(my-check
482 (list-ec (: x (index i) '(a b c d)) (list x i))
483 => '((a 0) (b 1) (c 2) (d 3)) )
484
485(my-check
486 (begin
487   (let ((f (my-open-output-file "tmp1.out")))
488     (do-ec (:range n 10) (begin (write n f) (newline f)))
489     (close-output-port f))
490   (my-call-with-input-file "tmp1.out"
491     (lambda (port) (list-ec (: x (index i) port) (list x i))) ))
492 => '((0 0) (1 1) (2 2) (3 3) (4 4) (5 5) (6 6) (7 7) (8 8) (9 9)) )
493
494
495; ==========================================================================
496; The examples from the SRFI document
497; ==========================================================================
498
499; from Abstract
500
501(my-check (list-ec (: i 5) (* i i)) => '(0 1 4 9 16))
502
503(my-check
504  (list-ec (: n 1 4) (: i n) (list n i))
505  => '((1 0) (2 0) (2 1) (3 0) (3 1) (3 2)) )
506
507; from Generators
508
509(my-check
510  (list-ec (: x (index i) "abc") (list x i))
511  => '((#\a 0) (#\b 1) (#\c 2)) )
512
513(my-check
514  (list-ec (:string c (index i) "a" "b") (cons c i))
515  => '((#\a . 0) (#\b . 1)) )
516
517
518; ==========================================================================
519; Little Shop of Horrors
520; ==========================================================================
521
522(my-check (list-ec (:range x 5) (:range x x) x) => '(0 0 1 0 1 2 0 1 2 3))
523
524(my-check (list-ec (:list x '(2 "23" (4))) (: y x) y) => '(0 1 #\2 #\3 4))
525
526(my-check
527 (list-ec (:parallel (:integers x)
528                     (:do ((i 10)) (< x i) ((- i 1))))
529          (list x i))
530 => '((0 10) (1 9) (2 8) (3 7) (4 6)) )
531
532
533; ==========================================================================
534; Less artificial examples
535; ==========================================================================
536
537(define (factorial n) ; n * (n-1) * .. * 1 for n >= 0
538  (product-ec (:range k 2 (+ n 1)) k) )
539
540(my-check (factorial  0) => 1)
541(my-check (factorial  1) => 1)
542(my-check (factorial  3) => 6)
543(my-check (factorial  5) => 120)
544
545
546(define (eratosthenes n) ; primes in {2..n-1} for n >= 1
547  (let ((p? (make-string n #\1)))
548    (do-ec (:range k 2 n)
549           (if (char=? (string-ref p? k) #\1))
550           (:range i (* 2 k) n k)
551           (string-set! p? i #\0) )
552    (list-ec (:range k 2 n) (if (char=? (string-ref p? k) #\1)) k) ))
553
554(my-check
555 (eratosthenes 50)
556 => '(2 3 5 7 11 13 17 19 23 29 31 37 41 43 47) )
557
558(my-check
559 (length (eratosthenes 100000))
560 => 9592 ) ; we expect 10^5/ln(10^5)
561
562
563(define (pythagoras n) ; a, b, c s.t. 1 <= a <= b <= c <= n, a^2 + b^2 = c^2
564  (list-ec
565   (:let sqr-n (* n n))
566   (:range a 1 (+ n 1))
567; (begin (display a) (display " "))
568   (:let sqr-a (* a a))
569   (:range b a (+ n 1))
570   (:let sqr-c (+ sqr-a (* b b)))
571   (if (<= sqr-c sqr-n))
572   (:range c b (+ n 1))
573   (if (= (* c c) sqr-c))
574   (list a b c) ))
575
576(my-check
577 (pythagoras 15)
578 => '((3 4 5) (5 12 13) (6 8 10) (9 12 15)) )
579
580(my-check
581 (length (pythagoras 200))
582 => 127 )
583
584
585(define (qsort xs) ; stable
586  (if (null? xs)
587      '()
588      (let ((pivot (car xs)) (xrest (cdr xs)))
589        (append
590         (qsort (list-ec (:list x xrest) (if (<  x pivot)) x))
591         (list pivot)
592         (qsort (list-ec (:list x xrest) (if (>= x pivot)) x)) ))))
593
594(my-check
595 (qsort '(1 5 4 2 4 5 3 2 1 3))
596 => '(1 1 2 2 3 3 4 4 5 5) )
597
598
599(define (pi-BBP m) ; approx. of pi within 16^-m (Bailey-Borwein-Plouffe)
600  (sum-ec
601    (:range n 0 (+ m 1))
602    (:let n8 (* 8 n))
603    (* (- (/ 4 (+ n8 1))
604          (+ (/ 2 (+ n8 4))
605             (/ 1 (+ n8 5))
606             (/ 1 (+ n8 6))))
607       (/ 1 (expt 16 n)) )))
608
609(my-check
610 (pi-BBP 5)
611 => (/ 40413742330349316707 12864093722915635200) )
612
613
614(define (read-line port) ; next line (incl. #\newline) of port
615  (let ((line
616         (string-ec
617          (:until (:port c port read-char)
618                  (char=? c #\newline) )
619          c )))
620    (if (string=? line "")
621        (read-char port) ; eof-object
622        line )))
623
624(define (read-lines filename) ; list of all lines
625  (my-call-with-input-file
626   filename
627   (lambda (port)
628     (list-ec (:port line port read-line) line) )))
629
630(my-check
631 (begin
632   (let ((f (my-open-output-file "tmp1.out")))
633     (do-ec (:range n 10) (begin (write n f) (newline f)))
634     (close-output-port f))
635   (read-lines "tmp1.out") )
636 => (list-ec (:char-range c #\0 #\9) (string c #\newline)) )
637
638
639; ==========================================================================
640; Summary
641; ==========================================================================
642
643(begin
644  (newline)
645  (newline)
646  (display "correct examples : ")
647  (display my-check-correct)
648  (newline)
649  (display "wrong examples   : ")
650  (display my-check-wrong)
651  (newline)
652  (newline) )
653
654(exit my-check-wrong)
655