guile-user
[Top][All Lists]
Advanced

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

eformat


From: kxn30
Subject: eformat
Date: Tue, 19 Dec 2000 10:22:49 -0500
User-agent: Wanderlust/2.4.0 (Rio) SEMI/1.13.7 (Awazu) FLIM/1.13.2 (Kasanui) Emacs/21.0.93 (i686-pc-linux-gnu) MULE/5.0 (SAKAKI)

I have written a Perl's "print <<"-like format facility for Guile.
It can be used as follows:

  guile> (use-modules (eformat))
  guile> (let ((x 1) (y 2) (z 3)) #[#t $x + $y = $z])
  1 + 2 = 3guile> 

  guile> (define ov "ov")
  guile> #[(current-output-port)
  I l${ov}e $(lambda () "Guile").
  ]
  I love Guile.
  guile> 

Have fun.

-- Kei


;;; eformat.scm --- Embedded format facility for Guile.  Public domain.

(define-module (eformat))

(let ()
  ;; Read an expression embedded in a string
  (define (read-exp port)
    (case (peek-char port)
      ;; (...) -> sexp
      ((#\()
       (list (read port)))
      ;; {...} -> variable
      ((#\{)
       (read-char port)
       (do ((c (read-char port) (read-char port))
            (l '() (cons c l)))
           ((eq? c #\}) (list->symbol (reverse! l)))))
      (else
       ;; [a-zA-Z0-9]* -> variable
       (do ((c (read-char port) (read-char port))
            (l '() (cons c l)))
           ((not (or (char-alphabetic? c) (char-numeric? c)))
            (unread-char c port)
            (list->symbol (reverse! l)))))))

  ;; Hash extension function
  (define (embedded-format ch port)
    (define (next) (read-char port))
    (let ((out-port (read port)))
      (next)
      (let loop ((char-list '()) (arg-list '()) (c (next)))
        (case c
          ;; End
          ((#\])
           (let ((form (list->string (reverse! char-list)))
                 (args (reverse! arg-list)))
             `(format ,out-port ,form ,@args)))
          ;; Escape
          ((#\\)
           (let ((list (cons (next) char-list)))
             (loop list arg-list (next))))
          ;; Embed
          ((#\$)
           (let ((list (cons (read-exp port) arg-list)))
             (loop (cons* #\A #\~ char-list) list (next))))
          ;; As is
          (else
           (loop (cons c char-list) arg-list (next)))))))

  ;; Bind it with #[...]
  (read-hash-extend #\[ embedded-format))



reply via email to

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