In Common Lisp how do I preserve the case of variable output [duplicate]

StackOverflow https://stackoverflow.com/questions/22547929

  •  18-06-2023
  •  | 
  •  

Вопрос

I have a variable of a list of cons cells here?

 (defparameter lookup-animal  '((Cat . kitten) (Bear . cub) (Cow . calf)))

Here is the function I use to parse through them

(defun lookup-animal (name type)
  (if (eq type 'old)
    (setf name (car (assoc name lookup-animal)))
  (if (eq type 'young)
    (setf name (cdr (assoc name lookup-animal)))))
  name)

 I run (lookup-animal 'Cat 'old) and it would output > CAT
 I run (lookup-animal 'Cat 'YOUNG) and it would output > KITTEN

The issue is I would like the name variable at the bottom of the list of defun lookup-animal to preserve the case of the animal list for example, Cat should print Cat not CAT, and Bear should print as Bear not BEAR. I looked over the internet for 3 hours and got nada...I got uppercase, lowercase no preserve case...so if anyone can help me in the code above preserve the case of the output of the final variable name in the function lookup-animal while keeping it the red color of a PRINC not the pinkish color of FORMAT..I would really grateful..

Thanks

Edit:

Here is my current code...It just prints "NAME" instead of the data. SYMBOL-NAME was working at REPL as is don't understand the change...I'll still could use help figuring out how to preserve the case of the cons cell data.

(defun lookup (name language o)
    (if (eq language 'lisp)
      (setf name (car (assoc name lookup)))
    (if (eq language 'C++)
      (setf name (cdr (assoc name lookup)))))

(setf (readtable-case *readtable*)  :preserve)
(SETF O (SYMBOL-NAME 'NAME))
(SETF (READTABLE-CASE *READTABLE*)  :UPCASE)
o)
Это было полезно?

Решение 3

You can preserve the case of a symbol with vertical bars ("pipe symbol"):

? (defparameter l '((cat . |Kitten|) (bear . |Cub|)))
L
? l
((CAT . |Kitten|) (BEAR . |Cub|))

then

? (assoc 'cat l)
(CAT . |Kitten|)
? (cdr (assoc 'cat l))
|Kitten|
? (type-of (cdr (assoc 'cat l)))
SYMBOL

If you want to print the symbol without the bars,:

? (princ (cdr (assoc 'cat l)))
Kitten                    ; printout
|Kitten|                  ; return value
? (format t "Meow said the ~a" (cdr (assoc 'cat l)))
Meow said the Kitten      ; printout
NIL                       ; return value

See here and here.

Другие советы

You're printing out a symbol, not a string. By convention, the symbol reader in lisp reads symbols in upper case (so when you get to writing them, they're written as upper case strings).

You can change this behavior for the reader like so:

(setf (readtable-case *readtable*) :preserve)

printing might work the way you want to, then. Or, you may need to call:

(SYMBOL-NAME 'Cat)

I would not advise that a lisp beginner tinker with the readtable-case. Few common lisp programs use that facility.

First you should become comfortable with the difference between symbols and string, and the role of print-case and read-case.

Learning how to use format will be a skill you can use a lot, and there in you will find tools for gaining fine control over your output.

> (let ((*print-case* :upcase)) (format t "~A ~(~A~) ~@(~A~) ~:(~A~) ~:@(~A~)" 'cow 'cow 'cow 'cow 'cow))
COW cow Cow Cow COW
nil
> (let ((*print-case* :downcase)) (format t "~A ~(~A~) ~@(~A~) ~:(~A~) ~:@(~A~)" 'cow 'cow 'cow 'cow 'cow))
cow cow Cow Cow COW
nil
> 
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top