定义像(defun hi () "Hi!")
这样的函数是否有优势,并且可以使用(hi)
或(HI)
或(Hi)
或(setf a-number 5)
来调用它并且能够使用a-number
,A-NUMBER
或A-Number
访问该号码?
如果有这样的优势,那么为什么大多数其他语言区分大小写?
答案 0 :(得分:26)
在交互式会话中的代码中使用区分大小写的名称更容易出错。
Common Lisp区分大小写。只是Common Lisp reader功能默认情况下将符号的所有非转义字符转换为大写。这也在Common Lisp标准中定义。预定义的Common Lisp符号在内部也都是大写的。
在旧机器上使用大写是常见的。请记住,Common Lisp的设计始于八十年代早期(1982年),其目标是与早期的Maclisp兼容,并且当有更多类型的计算机需要支持时(如所谓的迷你计算机和大型机)。旧计算机上使用的其他编程语言也使用大写标识符,如COBOL或PL / 1.
另请注意,Lisp经常以交互方式使用,因此在交互式编程会话期间获取正确名称的情况更加困难。当Lisp阅读器使用默认情况(此处为大写)并将所有输入转换为此情况时,它会稍微容易一些。
Common Lisp支持其他阅读器模式,您还可以转义符号:|This is a Symbol with mixed CASE and spaces|
。
今天很多软件都是小写的,甚至是区分大小写的,只有小写首选。一些Lisp供应商提供了Common Lisp的非标准变体,默认情况下所有符号都是小写的,读者是保留的。但这使得它与标准的Common Lisp不兼容,期望(symbol-name 'cl:defun)
是“DEFUN”而不是“defun”。
答案 1 :(得分:13)
对于交互式会话,在定义Common Lisp标准时,情况不敏感曾经是默认值。
但是,真正发生的是Common Lisp阅读器在实习和评估之前将所有符号转换为upcase。这是默认设置,但如果需要,您可以随时更改它。
*readtable*
个对象有一个属性readtable-case,用于控制阅读器如何实现内容并评估读取的符号。您可以setf readtable-case
至:upcase
(默认),:downcase
,:preserve
,:invert
。
默认情况下,readtable-case
设置为:upcase
,这会导致所有符号都转换为大写。
如果您想要区分大小写,则应该
(setf (readtable-case *readtable*) :invert)
=> :invert
乍一看,您可能认为最好选择:preserve选项,但它有一些小问题:标准定义的所有符号必须是upcased。因此,您将只对您定义的符号具有区分大小写,并且必须写入:
* (DEFUN hi () "Hi!")
=> hi
* (SETF a-number 5)
=> a-number
* (HI)
=> ;error: the stored function is #'HI in the *readtable*, but by
; calling (HI) you try to acces a function named #'hi(downcase), which
; gives an error
* A-NUMBER
=> ;error: same for the variable
* (hi)
=> "Hi!"
* a-number
=> 5
:downcase
选项与默认选项相反,将所有内容转换为小写,不会出现区分大小写。
但是使用:invert
,您在源代码中编写的符号(如defun
,setf
hi
函数)将转换为upcase,以及CamelCase
中的任何符号{1}}保留原样:
* (setf (readtable-case *readtable*) :invert)
=> :invert
* (defun Hi () "Hi!")
=> Hi
* (Hi)
=> "Hi!"
* (eq 'Hi 'hi)
=> nil
* (eq 'HI 'hi)
=> nil
* (eq 'Hi 'Hi)
=> t
答案 2 :(得分:9)
(正如其他人所指出的那样,它实际上是区分大小写的,但标准的读者行为是为了取消所有内容。)
关于优势:
Hashtable
和HashTable
命名不同的东西吗?name
和一个没有歧义的函数name
。 Name
甚至可以是变量的名称。答案 3 :(得分:3)
默认情况下,CL中的阅读器是大小写转换,所有转义字符都变为大写。您可以使用readtable-case
自定义此行为。这是因为它易于与遵循相同约定的其他语言进行交互。