| Allegro CL version 10.0 Unrevised from 9.0 to 10.0. 9.0 version |
Arguments: string &optional stream (eof-error-p t)eof-value &key (start 0) end
This function is a faster variant of read-line designed to place characters, read from a stream, into an existing string. It differs from read-line in (1) using an existing string rather than creating a new one, (2) reading only as many characters from a line as are needed, rather than reading a whole line, and (3) not returning the string where the characters are placed. Instead, filling the string is a side effect and two information values are returned:
nil
, then eof-value is returned
instead. An error is signaled if an eof is encountered immediately and
eof-error-p is non-nil
(its default is t
). If any characters are
read (including a newline character), no error will be signaled and
this first returned value will be an integer.
nil
indicates a newline was
encountered (as with read-line, reading will not continue after a
newline and the newline character will not be added to
string). The value :eof
means an end of file was encountered. The value
:short
means that character reading was
stopped because the end of the string (the actual end or the end
specified by the end keyword argument) was
reached.
Unexpected :short instead of nil. When the number of characters
in a line is exactly the numbers of characters specified by
start and end, this second
return value will be :short
instead of nil
. Characters are read until the portion of the
string specified by start and
end is filled. The character after the one read
which fills the substring is not read. If it is a newline, then in
fact the whole line will be copied into string (just as if
end was unspecified and the string was larger)
but the system will not know that to be the case. If further reading
is done when the next unread character is a newline, no characters
will be read and 0 and nil
will be the
return values.
A traditional way to fill a string with characters from a file is to read a line from the file with read-line and copy characters from the string read into the target string. But that process is costly in time and space, as new strings must be allocated by read-line, and characters are copied twice (from the stream to the new string and from the new string to the target string). This function is optimized for the specific purpose of copying characters from a stream into an existing string.
The characters are read from stream and placed into string, beginning at the position specified by start. Characters are continually read until
nil
for end is the same as
specifying (length
string
)
).
If the :short
situation occurs (i.e. the end
argument is satisfied without having encountered a newline) then
further processing can be done in subsequent calls without loss of
data. It should therefore be possible if desired to implement cl:read-line using excl:read-line-into.
nil
,
which is the same as specifying (length string)
.
nil
(the default) and an eof occurs before any
characters have been read, an end-of-file error is signalled. As with
cl:read-line,
eof-error-p has no effect on an eof encountered
after there have been characters read (even if
insufficent characters have been read to fill the target string).
nil
and an eof is encountered before any characters are read,
eof-value is returned (and
:eof
is returned as the second value).
The motivation for this function is to provide read-line functionality without an open-ended consing of result strings, and to allow for more control over line-oriented input.
Assume file is a stream open to a file with contents shown (there are no space characters, the blank line has just a newline character, and the last line ends with an eof, not a newline):
first line second line fourth line last line
Calls to excl:read-line-into have the following results:
;; Edit to have FILE be a stream open to the file specified above: ;; (setq file (open "myfile.cl" :direction :input) (setq string1 "0123456789" string2 "0123456789012345" string3 "012345678901234567890") (read-line-into string1 file) -> 10 :short string1 -> "first line" (read-line-into string2 file) -> 0 nil string2 -> "0123456789" ;; no characters read beause ;; a newline was encountered at once (read-line-into string2 file nil :eof-at-once :start 0 :end 5) -> 5 :short string2 -> "secon56789012345" (read-line-into string2 file nil :eof-at-once :start 5) -> 6 nil string2 -> "second line12345" (read-line-into string2 file nil :eof-at-once :start 10) -> 0 nil string2 -> "second line12345" ;; read blank line, no characters added (read-line-into string3 file nil :eof-at-once :start 3) -> 11 nil string3 -> "012fourth line4567890" (read-line-into string3 file) -> 9 :eof ;; If there is a newline at the end of the last line ;; (sometimes editors insert them without being asked to) ;; then this will return '9 nil' instead of '9 :eof' string3 -> "last line line4567890" (read-line-into string3 file nil :eof-at-once) -> :eof-at-once :eof string3 -> "last line line4567890" (read-line-into string3 file) -> ERROR ;; eof-error-p is T
See also simple-stream-read-line. That function is less space efficient than this one, but has a simpler interface.
Copyright (c) 1998-2019, Franz Inc. Oakland, CA., USA. All rights reserved.
This page was not revised from the 9.0 page.
Created 2015.5.21.
| Allegro CL version 10.0 Unrevised from 9.0 to 10.0. 9.0 version |