Reputation: 1091
Here's a code snippet that I wrote, but doesn't work:
(let ((separator "|")
(text '("Just" "do" "it" "!")))
(format t "~{~A~A~%~}" text separator))
The output should look like:
Just|
do|
it|
!|
However, it won't work like that - when I'm inside ~{~}
, I don't know how I can add elements from outside the list. I could do this:
(format t "~{~A|~%~}" text)
but this does not allow me to use separator
from variable, and that's what I'm after.
Now I know that I could merge text
with separator, by adding separator in every even place, but that looks ugly to me. Is there other way to do it in format
?
Upvotes: 3
Views: 162
Reputation: 139251
Changing the answer from renzo a bit: if we use SPECIAL declarations, we don't need the global variable:
(defun %d1 (stream arg &rest args)
(declare (ignore args)
(special delim))
(princ arg stream)
(princ delim stream))
(defun my-print (list delim)
(declare (special delim))
(format nil "~{~/%d1/~%~}" list))
Upvotes: 1
Reputation: 27414
You could use a Tilde Slash format directive, that allows a user-defined function as format specifier. This is just to give you a possible example, many variations on this are possible:
CL-USER> (defvar *separator* " ")
*SEPARATOR*
CL-USER> (defun q(stream arg &rest args)
(declare (ignore args))
(format stream "~a~a" arg *separator*))
Q
CL-USER> (let ((*separator* "|")
(text '("Just" "do" "it" "!")))
(format t "~{~/q/~%~}" text))
Just|
do|
it|
!|
NIL
CL-USER> (let ((*separator* "+++")
(text '("Just" "do" "it" "!")))
(format t "~{~/q/~%~}" text))
Just+++
do+++
it+++
!+++
NIL
CL-USER>
Upvotes: 2
Reputation: 139251
This is a hack:
CL-USER 49 > (let ((separator "|")
(text '("Just" "do" "it" "!")))
(format t
(concatenate 'string "~{~A" separator "~%~}")
text))
Just|
do|
it|
!|
Escaping tilde in the separator string:
CL-USER 56 > (flet ((fix-tilde (string)
(with-output-to-string (s)
(loop for c across string
when (char= c #\~)
do (write-string "~~" s)
else do (write-char c s)))))
(let ((separator (fix-tilde "~a~a"))
(text '("Just" "do" "it" "!")))
(format t
(concatenate 'string "~{~A" separator "~%~}")
text)))
Just~a~a
do~a~a
it~a~a
!~a~a
Upvotes: 4