guile-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

srfi-11 let-values using make-symbol


From: Kevin Ryde
Subject: srfi-11 let-values using make-symbol
Date: Sun, 18 Apr 2004 09:34:28 +1000
User-agent: Gnus/5.110002 (No Gnus v0.2) Emacs/21.3 (gnu/linux)

I guess make-symbol now allows a FIXME in srfi-11 to be addressed,

        * srfi-11.scm (let-values): Use make-symbol rather than gensym, for
        guaranteed uniqueness of temp variable symbols.

And just so I'm not accused of making an untested change :),

        * tests/srfi-11.test: New file.
        * Makefile.am (SCM_TESTS): Add it.

--- srfi-11.scm.~1.10.~ 2003-04-07 08:05:29.000000000 +1000
+++ srfi-11.scm 2004-04-18 09:31:13.000000000 +1000
@@ -1,6 +1,6 @@
 ;;; srfi-11.scm --- let-values and let*-values
 
-;; Copyright (C) 2000, 2001, 2002 Free Software Foundation, Inc.
+;; Copyright (C) 2000, 2001, 2002, 2004 Free Software Foundation, Inc.
 ;;
 ;; This library is free software; you can redistribute it and/or
 ;; modify it under the terms of the GNU Lesser General Public
@@ -67,6 +67,7 @@
 ;; I originally wrote this as a define-macro, but then I found out
 ;; that guile's gensym/gentemp was broken, so I tried rewriting it as
 ;; a syntax-rules statement.
+;;     [make-symbol now fixes gensym/gentemp problems.]
 ;;
 ;; Since syntax-rules didn't seem powerful enough to implement
 ;; let-values in one definition without exposing illegal syntax (or
@@ -167,9 +168,6 @@
 ;       ((_ ((vars binding) ...) body ...)
 ;        (lv-builder ((vars binding) ...) () body ...)))))
 
-;; FIXME: This is currently somewhat unsafe (b/c gentemp/gensym is
-;; broken -- right now (as of 1.4.1, it doesn't generate unique
-;; symbols)
 (define-macro (let-values vars . body)
 
   (define (map-1-dot proc elts)
@@ -189,7 +187,7 @@
 
   (define (let-values-helper vars body prev-let-vars)
     (let* ((var-binding (car vars))
-           (new-tmps (map-1-dot (lambda (sym) (gensym))
+           (new-tmps (map-1-dot (lambda (sym) (make-symbol "let-values-var"))
                                 (car var-binding)))
            (let-vars (map (lambda (sym tmp) (list sym tmp))
                           (undot-list (car var-binding))
;;;; srfi-11.test --- exercise SRFI-11 let-values
;;;;
;;;; Copyright 2004 Free Software Foundation, Inc.
;;;;
;;;; This program is free software; you can redistribute it and/or modify
;;;; it under the terms of the GNU General Public License as published by
;;;; the Free Software Foundation; either version 2, or (at your option)
;;;; any later version.
;;;;
;;;; This program is distributed in the hope that it will be useful,
;;;; but WITHOUT ANY WARRANTY; without even the implied warranty of
;;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
;;;; GNU General Public License for more details.
;;;;
;;;; You should have received a copy of the GNU General Public License
;;;; along with this software; see the file COPYING.  If not, write to
;;;; the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
;;;; Boston, MA 02111-1307 USA

(define-module (test-suite test-srfi-11)
  #:use-module (test-suite lib)
  #:use-module (srfi srfi-11))


;;
;; let-values
;;

(with-test-prefix "let-values"

  (with-test-prefix "no exprs"

    (pass-if "no values"
      (let-values ()
        #t)))

  (with-test-prefix "one expr"

    (pass-if "no values"
      (let-values ((() (values)))
        #t))

    (pass-if "one value"
      (let-values (((x) (values 1)))
        (equal? x 1)))

    (pass-if "one value as rest"
      (let-values ((x (values 1)))
        (equal? x '(1))))

    (pass-if "two values"
      (let-values (((x y) (values 1 2)))
        (and (equal? x 1)
             (equal? y 2)))))

  (with-test-prefix "two exprs"

    (pass-if "no values each"
      (let-values ((() (values))
                   (() (values)))
        #t))

    (pass-if "one value / no values"
      (let-values (((x) (values 1))
                   (() (values)))
        (equal? x 1)))

    (pass-if "one value each"
      (let-values (((x) (values 1))
                   ((y) (values 2)))
        (and (equal? x 1)
             (equal? y 2))))

    (pass-if-exception "first binding invisible to second expr"
        '(unbound-variable . ".*")
      (let-values (((x) (values 1))
                   ((y) (values (1+ x))))
        #f))))

;;
;; let*-values
;;

(with-test-prefix "let*-values"

  (with-test-prefix "no exprs"

    (pass-if "no values"
      (let*-values ()
        #t)))

  (with-test-prefix "one expr"

    (pass-if "no values"
      (let*-values ((() (values)))
        #t))

    (pass-if "one value"
      (let*-values (((x) (values 1)))
        (equal? x 1)))

    (pass-if "one value as rest"
      (let-values ((x (values 1)))
        (equal? x '(1))))

    (pass-if "two values"
      (let*-values (((x y) (values 1 2)))
        (and (equal? x 1)
             (equal? y 2)))))

  (with-test-prefix "two exprs"

    (pass-if "no values each"
      (let*-values ((() (values))
                    (() (values)))
        #t))

    (pass-if "one value / no values"
      (let*-values (((x) (values 1))
                    (() (values)))
        (equal? x 1)))

    (pass-if "one value each"
      (let*-values (((x) (values 1))
                    ((y) (values 2)))
        (and (equal? x 1)
             (equal? y 2))))

    (pass-if "first binding visible to second expr"
      (let*-values (((x) (values 1))
                    ((y) (values (1+ x))))
        (and (equal? x 1)
             (equal? y 2))))))

reply via email to

[Prev in Thread] Current Thread [Next in Thread]