Gaucheのread-line関数は生成する文字列に行末文字を含めずに捨ててしまう。これは、chompとかchopみたいな関数をわざわざ呼び出さなくてよいという面では、うれしい。
だけど行末文字についての情報は完全に捨ててしまうので、行末文字が何だったのか(あるいはEOFに到達していたのか)を調べたい場合にこまる。
そういう機会は少ないかもしれないけど、たとえば行末を表すのにはCR+LFを使うというプロトコルがあってそれに従っているかを判定する場合とかに必要になる。行末文字を含まない文字列といっしょに行末文字も返す関数があってもよいかもしれない。
(define (read-line/nl . args) (define CR (char->integer #\cr)) (define LF (char->integer #\lf)) (define (line&nl str-out nl) (values (get-output-string str-out) nl)) (let* ((iport (get-optional args (current-input-port))) (str-out (open-output-string))) (if (eof-object? (peek-byte iport)) (values (eof-object) (eof-object)) (let loop () (let1 b (read-byte iport) (cond ((eof-object? b) (line&nl str-out b)) ((= b LF) (line&nl str-out "\n")) ((= b CR) (if (= (peek-byte iport) LF) (begin (read-byte iport) (line&nl str-out "\r\n")) (line&nl str-out "\r"))) (else (write-byte b str-out) (loop))))))))