Common Lisp中的字符集

0 xml windows clisp common-lisp xml-parsing

我一直在研究一个通用的lisp程序,它解析两个XML文件,并以自定义的方式组合它们来制作第三个XML.不幸的是,lisp使用CP1252字符集,而我的XML文件使用UTF-8并包含一些不能在CP1252中使用的日文字符.

我一直试图通过添加使clisp使用UTF-8

:external-format 'charset:UTF-8
Run Code Online (Sandbox Code Playgroud)

这两个负载(如建议在这里)和read-line(因为为什么不)的功能,但仍CLISP抛出了这个错误:

READ-LINE:CHARSET:CP1252转换中的字节#x81无效

有没有办法用我的代码做我想要的?我对lisp还不太新鲜.

完整读取功能代码:

(defun readXML (stream libSize)
    (defparameter lib nil)
    (defparameter x 1)
    (loop
        (defparameter lib (cons (read-line stream :external-format 'charset:UTF-8) lib))
        (defparameter x (+ x 1))
        (when (> x libSize) (return lib))))
Run Code Online (Sandbox Code Playgroud)

sds*_*sds 5

误区

read-line

此功能无法接受:external-format的说法.

它确实接受了几个可选参数,但它们与编码无关.

defparameter

这是一个"顶级"运算符,它创建一个全局动态变量. 切勿在功能内使用它.let而是在那里使用- 它以词汇方式绑定变量. loop(见下文)也绑定变量.

正确的代码

(defun read-lines (file-name max-lines)
  "Open the file and read it line-by-line, at most `max-lines'."
  (with-open-file (stream file-name :external-format charset:utf-8)
    (loop :for line = (read-line stream nil nil)
      :for line-number :upfrom 0
      :while (and line (< line-number max-lines))
      :collect line)))
Run Code Online (Sandbox Code Playgroud)

或者,稍微简单一些(由@jkiiski建议):

(defun read-lines (file-name max-lines)
  "Open the file and read it line-by-line, at most `max-lines'."
  (with-open-file (stream file-name :external-format charset:utf-8)
    (loop :for line = (read-line stream nil nil)
      :repeat max-lines
      :while line
      :collect line)))
Run Code Online (Sandbox Code Playgroud)

说明

  • with-open-file打开文件,绑定stream到结果并确保在退出时关闭流.

  • loop是一个非常先进的迭代工具.它绑定line到每个连续的行,使用它们计算它们line-number,并将行收集到返回值中:

PS.请按照答案中的所有链接.他们详细解释了每个操作员.