sheikh_anton
sheikh_anton

Reputation: 3452

Idiomatic way to long multistring constants (or vars) in Lisp code

What is idiomatic way for inserting long multistrings vars or constants in Common Lisp code? Is there something like HEREDOC in unix shell or some other languages, to eliminate indenting spaces inside string literals?

For example:

(defconstant +help-message+ 
             "Blah blah blah blah blah
              blah blah blah blah blah
              some more more text here")
; ^^^^^^^^^^^ this spaces will appear - not good

And writing this way kinda ugly:

(defconstant +help-message+ 
             "Blah blah blah blah blah
blah blah blah blah blah
some more more text here")

How we should write it. If there any way, when you don't need to escape quotes it'll be even better.

Upvotes: 4

Views: 305

Answers (3)

Elias Mårtenson
Elias Mårtenson

Reputation: 3885

I sometimes use this form:

(concatenate 'string "Blah blah blah"
                     "Blah blah blah"
                     "Blah blah blah"
                     "Blah blah blah")

Upvotes: 1

Peder Klingenberg
Peder Klingenberg

Reputation: 41175

I don't know about idiomatic, but format can do this for you. (naturally. format can do anything.)

See Hyperspec section 22.3.9.3, Tilde newline. Undecorated, it removes both newline and subsequent whitespace. If you want to preserve the newline, use the @ modifier:

(defconstant +help-message+
   (format nil "Blah blah blah blah blah~@
                blah blah blah blah blah~@
                some more more text here"))

CL-USER> +help-message+
"Blah blah blah blah blah
blah blah blah blah blah
some more more text here"

Upvotes: 4

Rainer Joswig
Rainer Joswig

Reputation: 139321

There is no such thing.

Indentation is usually:

(defconstant +help-message+ 
  "Blah blah blah blah blah
blah blah blah blah blah
some more more text here")

Maybe use a reader macro or read-time eval. Sketch:

(defun remove-3-chars (string)
  (with-output-to-string (o)
    (with-input-from-string (s string)
      (write-line (read-line s nil nil) o)
      (loop for line = (read-line s nil nil)
            while line
            do (write-line (subseq line 3) o)))))

(defconstant +help-message+
  #.(remove-3-chars
  "Blah blah blah blah blah
   blah blah blah blah blah
   some more more text here"))

CL-USER 18 > +help-message+
"Blah blah blah blah blah
blah blah blah blah blah
some more more text here
"

Would need more polishing... You could use 'string-trim' or similar.

Upvotes: 2

Related Questions