put-bytevector, write-bytevector - write a bytevector to a port
(import (rnrs)) ;R6RS
(import (rnrs io ports)) ;R6RS
(import (scheme base)) ;R7RS
(put-bytevector binary-port bytevector) ;R6RS
(put-bytevector binary-port bytevector start) ;R6RS
(put-bytevector binary-port bytevector start count) ;R6RS
(write-bytevector bytevector) ;R7RS
(write-bytevector bytevector port) ;R7RS
(write-bytevector bytevector port start) ;R7RS
(write-bytevector bytevector port start end) ;R7RS
Writes the selected bytes from bytevector to binary-port (or
port).
- R6RS
- The default value for start is 0. The default value for
count is (bytevector-length bytevector)
− start.
- R7RS
- R7RS does not specify any default values, so an implementation can
presumably treat any such calls as errors, but some reasonable assumptions
can be made. The default value for port is
(current-output-port). Normally the current output port is textual
and using it here would be an error. The default value for start is
0. The default value for end is (bytevector-length
bytevector).
- Chibi Scheme, GNU Guile
- Ports can be both binary and textual. It is possible to write bytes to the
default value of current-output-port(3scm). This is not portable.
standard-output-port(3scm) should be used to get a fresh binary
port.
These procedures return unspecified values.
(import (rnrs))
;; Write a TARGA header followed by pixels
(define (put-tga p width height bits/pixel pixel-data)
(let ((hdr (make-bytevector 18 0)))
(bytevector-u8-set! hdr 2 2)
(bytevector-u16-set! hdr 12 width (endianness little))
(bytevector-u16-set! hdr 14 height (endianness little))
(bytevector-u8-set! hdr 16 bits/pixel)
(put-bytevector p hdr)
(put-bytevector p pixel-data)))
(let ((pixel-data (make-bytevector (* 320 240 4))))
;; Generate some image data
(do ((y 0 (+ y 1)))
((= y 240))
(do ((x 0 (+ x 1)))
((= x 320))
(bytevector-u32-set! pixel-data (* 4 (+ x (* y 320)))
(+ #xff
(* (round (* y 255/240)) 256)
(* (round (* x 255/320)) 256 256))
(endianness big))))
;; Create an image file
(call-with-port (open-file-output-port "image.tga")
(lambda (p)
(put-tga p 320 240 32 pixel-data))))
The put-bytevector procedure is used in applications that write bulk data
to binary output ports. This can, for example, be code that works with binary
files or network streams.
It is sometimes used in conjunction with a port created by
open-bytevector-output-port(3scm), as a different method of
constructing a bytevector. The benefit is that the port will keep track of
the current byte position, and the size of the data does not need to be
known in advance.
If one were forced to remove either put-bytevector(3scm) or
put-u8(3scm) from the language, then the latter should be removed. The
first one is more general, more efficient and supports the writing of bulk
data to non-buffered ports.
There are trivial differences in the signatures from R6RS and R7RS.
This procedure can raise exceptions with the following condition types:
- &assertion (R6RS)
- The wrong number of arguments was passed or an argument was outside its
domain. This is also raised if start or count are negative,
or if the length of bytevector is not at least start+count.
This is also raised if the port is not an open binary port.
- &i/o-write (R6RS)
- There was a write error during an I/O operation.
- &i/o-port (R6RS)
- If this is included as part of an I/O condition then the port related to
the I/O error can be retrieved with i/o-error-port(3scm).
- R7RS
- The assertions described above are errors. Implementations may signal an
error, extend the procedure's domain of definition to include such
arguments, or fail catastrophically.
This procedure was not present in R5RS and earlier reports. It can be seen as
analogous to the fwrite(3) function from the C language, or similar to
the write(2) function from POSIX in the case of non-buffered ports.