I realize this is probably a really stupid question but i have no idea why this isnt working and i pretty much gave up. basically i tried:
(setq answer (string (read)))
and
(setq answer 0)
(format answer "~s" (read))
and
(setq answer (read))
when i try to evaluate
(if (stringp answer)
(princ "works")
(princ "failed"))
on any of the above tries it always comes out failed.
what am i doing wrong?
Or you could just do:
(setq answer (read-line))
That gives you a string right there.
[1]> (setq answer (read))
3
3
[2]> (type-of answer)
(INTEGER 0 16777215)
[3]> (setq answer (read-line))
3
"3"
[4]> (type-of answer)
(SIMPLE-BASE-STRING 1)
[5]>
Start a fresh REPL, then try checking the return value of each of your steps:
T1> (read)
foo
FOO
T1> (read)
1
1
T1> (type-of (read))
foo
SYMBOL
T1> (type-of (read))
1
BIT
Now note, that STRING
won't work on all input types:
T1> (string 'foo)
"FOO"
T1> (string 1)
Also note that, unlike setq
, (format foo ...)
won't set foo
, but write to it, if it's a stream or a string with a fill-pointer. Take a look at its Documentation, and you'll see:
format destination control-string &rest args => result
[...]
destination---nil, t, a stream, or a string with a fill pointer.
[...]
format is useful for producing nicely formatted text, producing good-looking messages, and so on. format can generate and return a string or output to destination.
If destination is a string, a stream, or t, then the result is nil. Otherwise, the result is a string containing the `output.'
Try it like this:
T1> (setq *answer*
(with-output-to-string (s)
(format s "~s" (read))))
1
"1"
T1> *answer*
"1"
Or like this:
T1> (setq *answer* (make-array 20 :element-type 'character :fill-pointer 0))
""
T1> (format *answer* "~s" (read))
1
NIL
T1> *answer*
"1"
Those are the only relevant errors I could find in your code. This definitely returns "works"
in every conforming CL (you could also use prin1-to-string
):
T1> (defvar *answer*)
*ANSWER*
T1> (setq *answer* (format nil "~s" (read)))
1
"1"
T1> (if (stringp *answer*)
(princ "works")
(princ "failed"))
works
"works"
Unless you are in a messed-up package (try (in-package cl-user)
before evaluating your code), or redefined basic functionality, this will work. Give some more exact error descriptions, if it still won't.
ED:
Having read Bill's answer, who correctly pointed at read-line
as a shorter solution, I should maybe mention that I didn't try to show the best, most succinct, or most idiomatic approaches in my answer, and that those will vary depending on what you are really trying to do. (The shortest possible solution would have been "works"
:) They are just examples that should help explaining why your code failed.
Another thing I forgot to say is that you should keep in mind, that toplevel setq
s on variables not defined with defvar
or defparameter
are generally to be avoided in anything but dabbling at the REPL, since the consequences are undefined. Also, those variables are, by convention, wrapped in asterisks (also called earmuffs) in order to prevent bugs caused by confusing specials with lexically scoped variables.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With