#!/usr/local/bin/guile \
-e main -s

;;; $Id: lists.guile,v 1.2 2001/06/29 23:12:37 doug Exp $
;;; http://www.bagley.org/~doug/shootout/
;;; from Brad Knotwell

(use-modules (ice-9 format))

(define SIZE 10000)
(define Li1 (cdr (iota (+ SIZE 1))))
(define Li2 (list-copy Li1))
(define Li3 '())

;;;  note the reverses
;;;  AFAIK, guile doesn't have a primitive for grabbing elts from the
;;;  end of a list.  no scheme programmer would do this anyway.  they'd
;;;  reverse the list in place
(define (test-lists)
    (do ((elt (car Li2) (car Li2)))
    ((eq? (cdr Li2) '()) (begin  (set! Li3 (cons elt Li3))
                     (set! Li2 '())
                     (set! Li3 (reverse! Li3))))
      (begin (set! Li3 (cons elt Li3))
         (set! Li2 (cdr Li2))))
    (set! Li3 (reverse! Li3))
    (do ((elt (car Li3) (car Li3)))
    ((eq? (cdr Li3) '()) (begin (set! Li2 (cons elt Li2))
                    (set! Li3 '())
                    (set! Li2 (reverse! Li2))))
      (begin (set! Li2 (cons elt Li2))
         (set! Li3 (cdr Li3))))
    (set! Li1 (reverse! Li1))
    (if (and (= (car Li1) SIZE) (every-2? = Li1 Li2)) (length Li1) 0)))
(define every-2? (lambda (test l1 l2)
  (or (null? l1)
      (and (test (car l1) (car l2))
           (every-2? test (cdr l1) (cdr l2))))))

(define (main args)
  (let ((n (or (and (= (length args) 2) (string->;number (cadr args))) 1)))
    (do ((i n (set! n (1- n))))
    ((= n 1) (write-line (test-lists)))