当我们开始思考如何统计函数定义中的单词时,第一个问题(或者说应该问的问题)是:我们要统计什么?
当我们针对 Lisp 函数定义谈论 “单词” 时,实际上大部分指的是符号。例如,下面的 multiply-by-seven
函数包含五个符号:defun、multiply-by-seven、number、* 和 7。
此外,在文档字符串中还包含四个单词:‘Multiply’、‘NUMBER’、‘by’ 和 ‘seven’。
符号 ‘number’ 重复出现,因此该定义总共有十个单词与符号。
(defun multiply-by-seven (number) "Multiply NUMBER by seven." (* 7 number))
但如果我们用 C-M-h(mark-defun)标记 multiply-by-seven 定义,
然后对其调用 count-words-example,会发现 count-words-example 声称该定义
有十一个单词,而不是十个!哪里出了问题!
问题有两方面:count-words-example 不把 ‘*’ 算作单词,并且将单个符号
multiply-by-seven 计为三个单词。连字符被当作单词间的分隔符,而非单词内部连接符:
‘multiply-by-seven’ 被当作 ‘multiply by seven’ 统计。
造成这种混淆的原因是 count-words-example 定义中用于逐个单词移动光标位置的正则表达式搜索。
在标准版本的 count-words-example 中,正则表达式为:
"\\w+\\W*"
该正则表达式定义的模式是:一个或多个单词构成字符,后接可选的一个或多个非单词构成字符。 而“单词构成字符”的含义将我们引向语法问题,这值得单独用一节讲解。