将尾随换行符作为字节写入 Scheme 中的二进制输出文件

Write trailing newline as byte into binary output file in Scheme

我的代码有问题,我无法使用二进制端口保存换行符,我想为我的 Scheme 实现编写单元测试,但我无法弄清楚为什么我也得到了这个结果Gambit 和 Kawa(Gauche 和 Guile 未能 运行 代码,因为缺少程序)。

(let ((fname "./tests/__x7__.scm")
      (str "hello, world!\n"))
  (if (file-exists? fname)
      (delete-file fname))
  (let ((port (open-binary-output-file fname)))
    (call-with-port port
                    (lambda (p)
                      (write-bytevector (string->utf8 str) p)))
    (define output (with-input-from-file fname
                     (lambda ()
                       (let ((result (list)))
                         (do ((char (read-char) (read-char)))
                           ((eof-object? (peek-char))
                            (apply string result))
                           (set! result (append result (list char))))))))
    (write output)
    (newline)))

我正在将换行符写入文件,但在输出文件中我最后没有换行符,当我读取文件时我得到 "hello world" 而不是 "hello world\n".

奇怪的是我想测试的 Scheme 实现中我也得到了没有换行符的 "hello world"

如果字符串是 "hello, world!\nfoo bar" 换行符保存正确,为什么尾随换行符没有保存?

我在这里错过了什么?为什么换行符没有保存到文件中?

一个换行符被保存到文件中:用 od 检查文件或其他东西会告诉你。

但是您读取文件的逻辑是不正确的:您从未对读取的最后一个字符做任何事情。如果你改为写 (say)

(let loop ((c (read-char)) (a '()))
  (if (eof-object? c)
      (list->string (reverse a))
      (loop (read-char) (cons c a))))

您将从文件中获取所有字符。