@node Library modules - Gauche extensions, Library modules - R7RS standard libraries, Library modules - Overview, Top
@chapter Library modules - Gauche extensions
@c NODE ライブラリモジュール - Gauche拡張モジュール

@c ----------------------------------------------------------------------
@menu
* Arrays::                      gauche.array
* Importing gauche built-ins::  gauche.base
* Bitvector utilities::         gauche.bitvector
* Generating C code::           gauche.cgen
* Character code conversion::   gauche.charconv
* Collection framework::        gauche.collection
* Configuration parameters::    gauche.config
* Generating build files::      gauche.configure
* Connection framework::        gauche.connection
* Dictionary framework::        gauche.dictionary
* Low-level file operations::   gauche.fcntl
* Foreign function interface::  gauche.ffi
* Generators::                  gauche.generator
* Hooks::                       gauche.hook
* Interactive session::         gauche.interactive
* Lazy sequence utilities::     gauche.lazy
* Listener::                    gauche.listener
* User-level logging::          gauche.logger
* Instance pools::              gauche.mop.instance-pool
* Propagating slot access::     gauche.mop.propagate
* Singleton::                   gauche.mop.singleton
* Slot with validator::         gauche.mop.validator
* Native type utilities::       gauche.native-type
* Networking::                  gauche.net
* Package metainformation::     gauche.package
* Parameters (legacy)::         gauche.parameter
* Parsing command-line options::  gauche.parseopt
* Partial continuations::       gauche.partcont
* High-level process interface::  gauche.process
* Record types::                gauche.record
* Reloading modules::           gauche.reload
* Simple dispatcher::           gauche.selector
* Sequence framework::          gauche.sequence
* Syslog::                      gauche.syslog
* Terminal control::            gauche.termios
* Unit testing::                gauche.test
* Threads::                     gauche.threads
* Measure timings::             gauche.time
* Unicode utilities::           gauche.unicode
* Uniform vector library::      gauche.uvector
* Comparing version numbers::   gauche.version
* Virtual ports::               gauche.vport
@end menu

@node Arrays, Importing gauche built-ins, Library modules - Gauche extensions, Library modules - Gauche extensions
@section @code{gauche.array} - Arrays
@c NODE 配列, @code{gauche.array} - 配列

@deftp {Module} gauche.array
@mdindex gauche.array
@c EN
This module provides multi-dimensional array data type and operations.
The primitive API follows SRFI-25.
Besides a generic SRFI-25 array that can store any Scheme objects,
this module also provides array classes that stores numeric objects
efficiently, backed up by
homogeneous numeric vectors (@pxref{Uniform vectors}).

External representations of arrays, one with srfi-163 and
another using srfi-10, are also provided.
@c JP
このモジュールは多次元配列のデータタイプとそれに関する操作を提供します。
プリミティブなAPIはSRFI-25で定義されているものに従います。
任意のSchemeオブジェクトを保持できるSRFI-25の汎用配列の他に、
均一な数値ベクタ(@ref{Uniform vectors}参照)を使って
数値要素を効率良く保持する配列型も提供されます。

また、配列の外部表現も実装されます。ひとつはSRFI-163準拠のもの、
もうひとつはSRFI-10を利用したものです。
@c COMMON

@c EN
Each element of an @var{N}-dimensional array can be accessed
by @var{N} integer indices,
@code{[ @var{i_0} @var{i_1} @dots{} @var{i_N-1} ]}.
An array has associated @var{shape} that knows lower-bound @var{s_k} and
upper-bound @var{e_k} of index of each dimension, where
@var{s_k} <= @var{e_k}, and the index @var{i_k} must satisfy
@var{s_k} <= @var{i_k} < @var{e_k}.
(Note: it is allowed to have @var{s_k} == @var{e_k}, but such array can't
store any data.  It is also allowed to have zero-dimensional array,
that can store a single data.).
The shape itself is a [ @var{D} x 2 ] array, where @var{D} is the
dimension of the array which the shape represents.
@c JP
@var{N}次元の配列の各エレメントは@code{N}個の整数のインデックス
@code{[ @var{i_0} @var{i_1} @dots{} @var{i_N-1} ]}でアクセスされます。
配列は、各次元のインデックスの下限@var{s_k}および上限@var{e_k}を決める
@var{shape}を持っています。ここで、@var{s_k} <= @var{e_k}であり、
@var{k}次元目のインデックス@var{i_k}は
@var{s_k} <= @var{i_k} < @var{e_k} を満たすものとします。
(@var{s_k} == @var{e_k} であるような配列も作れますが、
その配列にはデータをストアすることはできません。
また、0次元の配列は作れます。それは一つだけデータを保持できます)。
Shapeはそれ自体が [ @var{D} x 2 ] の配列です。
ここで@var{D}はそのshapeが表現する配列の次元数です。
@c COMMON

@c EN
You can pass index(es) to array access primitives in a few ways;
each index can be passed as individual argument,
or can be 'packed' in a vector or one-dimensional array.
In the latter case, such a vector or an array is called an "index object".
Using a vector is efficient in Gauche when you iterate over the elements
by changing the vector elements, for it won't involve memory allocation.
@c JP
配列のプリミティブに対しインデックスを渡すにはいくつか方法があります。
各インデックスをばらばらの引数として渡すこともできますし、
ベクタや1次元の配列にパックして渡すこともできます。
後者においてインデックスがパックされたベクタや配列を「インデックスオブジェクト」
と呼ぶことがあります。Gaucheでは、配列の要素に次々とアクセスするような処理では
ベクタをインデックスオブジェクトとして使うと若干効率が良いでしょう。
@c COMMON

@c EN
Arrays can be compared by the @code{equal?} procedure.
@code{Equal?} returns @code{#t} if two arrays have the same
shape and class, and their corresponding elements are the same
in the sense of @code{equal?}.
@c JP
配列は@code{equal?}手続きで比較することが出来ます。
二つの配列のshapeとクラスが等しく、また対応する各要素が@code{equal?}の意味で
等しい場合に二つの配列は@code{equal?}であると見なされます。
@c COMMON

@c EN
Internally, an array consists of a backing storage and a mapping procedure.
A backing storage is an object of aggregate type that can be accessed
by an integer index.  A mapping procedure takes
multi-dimensional indices (or index object) and
returns a scalar index into the backing storage.
(Note that, unlike Common Lisp,
vectors and 1-dimensional arrays are disjoint types.)
@c JP
内部的には、配列は1次元のインデックスでアクセスされるバッキングストレージと、
多次元のインデックスをバッキングストレージへのインデックスにマップする手続きとから
構成されています。
(Common Lispと違って、ベクタと1次元配列は異なる型であることに注意してください)。
@c COMMON
@end deftp

@menu
* Array classes::
* Array literal syntax::
* Array predicate and constructors::
* Array accessors and modifiers::
* Whole array operations::
@end menu

@node Array classes, Array literal syntax, Arrays, Arrays
@subsection Array classes
@c NODE 配列クラス

@deftp {Class} <array-base>
@clindex array-base
@c MOD gauche.array
@c EN
An abstract base class of array types, that implements generic operations
on the array.   To create an array instance,
you should use one of the following concrete array classes.
@c JP
配列に関する汎用操作を実装している、抽象ベースクラスです。
実際に配列のインスタンスを作るには、以下のいずれかの具体クラスを使って下さい。
@c COMMON
@end deftp

@deftp {Class} <array>
@deftpx {Class} <u8array>
@deftpx {Class} <s8array>
@deftpx {Class} <u16array>
@deftpx {Class} <s16array>
@deftpx {Class} <u32array>
@deftpx {Class} <s32array>
@deftpx {Class} <u64array>
@deftpx {Class} <s64array>
@deftpx {Class} <f16array>
@deftpx {Class} <f32array>
@deftpx {Class} <f64array>
@deftpx {Class} <c32array>
@deftpx {Class} <c64array>
@deftpx {Class} <c128array>
@clindex array
@clindex u8array
@clindex s8array
@clindex u16array
@clindex s16array
@clindex u32array
@clindex s32array
@clindex u64array
@clindex s64array
@clindex f16array
@clindex f32array
@clindex f64array
@clindex c32array
@clindex c64array
@clindex c128array
@c MOD gauche.array
@c EN
Concrete array classes.  The @code{<array>} class implements SRFI-25
compatible array, i.e. an array that can store any Scheme objects.
The @code{<u8array>} class through @code{<c128array>} classes uses
a @code{<u8vector>} through @code{<c128vector>} as a backing storage,
and can only store a limited range of integers or inexact real numbers,
but they are space efficient.
@c JP
具体配列クラスです。@code{<array>}クラスはSRFI-25互換の配列、
すなわち、任意のSchemeオブジェクトを格納できる配列を実装します。
@code{<u8array>}から@code{<c128array>}までは、
それぞれ@code{<u8vector>}から@code{<c128vector>}をバッキングストレージとして
用いる配列を実装し、制限された範囲の整数もしくは非正確な実数のみを
効率良く格納することができます。
@c COMMON
@end deftp

@node Array literal syntax, Array predicate and constructors, Array classes, Arrays
@subsection Array literal syntax
@c NODE 配列のリテラル構文

@c EN
Gauche now supports array literals defined in srfi-163.  Its compact
representation begins with a hash sign, followed by the array's rank,
then a tag to specify the array's type (@code{a} for general array),
then a nested list of elements:
@c JP
Gaucheはsrfi-163で定義された配列リテラルをサポートするようになりました。
短い表記では、@code{#}の後に配列のランク、続いて配列の型を示すタグ
(一般配列の場合は@code{a})、その後に要素の入れ子になったリストが続きます。
@c COMMON

@example
;; A 3x2 general array
;;
;;   1 2 3
;;   4 5 6

#2a((1 2 3) (4 5 6))
@end example

@c EN
Array lengths for each dimension can be explicit:
@c JP
配列の各次元の長さを明示することもできます。
@c COMMON

@example
#2a:3:2((1 2 3) (4 5 6))
@end example

@c EN
Gauche used to read/write arrays using srfi-10 reader constructor
syntax.  For the backward compatibity, this syntax is also supported:
@c JP
以前のGaucheは、srfi-10のリーダ構築子構文を使って配列を書き出していました。
互換性のため、その構文もサポートされます。
@c COMMON

@example
#,(<array> (0 3 0 2) 1 2 3 4 5 6)
@end example

@c EN
When an array is printed, the write control parameter @code{array}
determines which format is used (@pxref{Output controls}).  It can take
one of the following symbols.

@table @code
@item compact
This is the default.
The srfi-163 representation without array lengths is used,
e.g. @code{#2a((0 1) (2 3) (4 5))}.
If the array has non-zero start index, it shows start indexes of
all dimensions, e.g. @code{#2a@@0@@-1((0 1) (2 3) (4 5))}.
@item dimensions
The srfi-163 representation with array lengths is used:
@code{#2a:3:2((0 1) (2 3) (4 5))}.
If the array has non-zero start index, it is shown in the dimension:
@code{#2a:3@@-1:2((0 1) (2 3) (4 5))}.
@item reader-ctor
The srfi-10 reader constructor is used:
@code{#,(<array> (0 3 0 2) 1 2 3 4 5 6)},
or @code{#,(<array> (0 3 -1 1) 1 2 3 4 5 6)}.
@end table
@c JP
配列が印字される時は、出力制御パラメータの@code{array}の値により
どの形式を使うかが決まります (@ref{Output controls}参照)。
この値は次の3つのシンボルのいずれかを取ります。

@table @code
@item compact
これがデフォルトです。
配列の長さを省略したsrfi-163表記が使われます。
例: @code{#2a((0 1) (2 3) (4 5))}。
ただし、配列にゼロ始点でない次元があれば、全ての始点が表示されます:
@code{#2a@@0@@-1((0 1) (2 3) (4 5))}。
@item dimensions
配列の長さを示すsrfi-163表記が使われます:
@code{#2a:3:2((0 1) (2 3) (4 5))}。
配列にゼロ始点でない次元があれば、その次元だけ始点も表示されます:
@code{#2a:3@@-1:2((0 1) (2 3) (4 5))}。
@item reader-ctor
srfi-10表記が使われます:
@code{#,(<array> (0 3 0 2) 1 2 3 4 5 6)}や、
@code{#,(<array> (0 3 -1 1) 1 2 3 4 5 6)}等。
@end table
@c COMMON

@c EN
See the following description for the precise specification of those
notations.
@c JP
これらの表記の正確な仕様については以下に説明します。
@c COMMON

@deftp {Reader Syntax} @code{# @var{rank} a @var{start/length}* (@var{elements} @dots{})}
@deftpx {Reader Syntax} @code{# @var{rank} s8 @var{start/length}* (@var{elements} @dots{})}
@deftpx {Reader Syntax} @code{# @var{rank} u8 @var{start/length}* (@var{elements} @dots{})}
@dots{}
@end deftp
@deftp {Reader Syntax} @code{# @var{rank} c64 @var{start/length}* (@var{elements} @dots{})}
@deftpx {Reader Syntax} @code{# @var{rank} c128 @var{start/length}* (@var{elements} @dots{})}
[SRFI-163]
@c EN
A literal array.  @var{Rank} is a decimal digit to specify the rank
of the array. What follows is a tag that specify arrays' type: @code{a} for
general array that can contain any Scheme values,
and @code{s8} @dots{} @code{c128} are uniform numeric arrays, corresponds
to uniform vectors (@pxref{Uniform vectors}).
@c JP
配列リテラルです。@var{rank}は配列のランク(次元数)を示す数値です。
その後に配列の型を示すタグが続きます。@code{a}が任意のSchemeオブジェクトを
要素に持てる一般配列で、その他に特定の数値型を格納する配列があります。
数値型の配列はユニフォームベクタ(@ref{Uniform vectors}参照)と同じ、
@code{s8} @dots{} @code{c128}のタグを使います。
@c COMMON

@c EN
Next come start/length specifications.  They're optional as long as the
info can be derived from the array elements.  If given, each start/length
spec takes one of the following form, to specify the array's start
index and length of the correponsing dimension.
@c JP
続いて、始点/長さの指定が来ます。これは要素のリストから推測可能な場合は
省略できます。与えられた場合、各次元に対する始点/長さ指定は以下の
いずれかの形式をとります。
@c COMMON

@table @code
@item @@@var{start}:@var{length}
@c EN
The index starts from @var{start} and runs for @var{length}.
@c JP
インデックスは@var{start}を始点とし、長さ@var{length}。
@c COMMON
@item :@var{length}
@c EN
The index starts from zero and runs for @var{length}.
@c JP
インデックスは0を始点とし、長さ@var{length}。
@c COMMON
@item @@@var{start}
@c EN
The index starts from @var{start}.  Length is determined by the given elements.
@c JP
インデックスは@var{start}を始点とし、長さは要素のリストで決定される。
@c COMMON
@end table

@c EN
If the array has non-zero start index, or a zero length dimension,
start/length specs can't be omitted.
@c JP
配列がゼロ以外の始点のインデックスを持つか、いずれかの次元の長さが0である
場合、始点/長さ指定は省略できません。
@c COMMON

@c EN
Lastly come the array elements, in the form of nested list.  Rank 1 array
has a flat list, rank 2 array has a list of lists, and so on.
(Note that a rank-1 array can hold lists in its elements, in that
case you see nested list in rank 1 array contens. That's why you need
rank to avoid ambiguity).
Each corresponding dimension must be uniform, e.g.
@code{#2a((1 2) (3))} isn't allowed b/c the second level list has different
lengths.  If the literal has start/length specs, they should match the
given elements as well.
@c JP
最後にネストしたリストで配列の要素を指定します。ランク1の配列はフラットなリスト、
ランク2の配列はリストのリスト、という具合です。
(ランク1の配列が要素にリストを持つことは可能で、
その場合はランク1配列の要素にネストしたリストが現れます。
ランクの数値が必要なのはこの曖昧姓を排除するためです。)
要素の、対応する次元の長さは一様でなければなりません。
例えば@code{#2a((1 2) (3))}は、二番目の次元の長さが異なるので許されません。
リテラルが始点/長さ指定を持っていた場合、要素リストもその指定と一致しなければなりません。
@c COMMON

@example
@c EN
; an array such that:
@c JP
; 次のような配列：
@c COMMON
;   8 3 4
;   1 5 9
;   6 7 2
#2a((8 3 4) (1 5 9) (6 7 2))
#2a:3:3((8 3 4) (1 5 9) (6 7 2))

@c EN
; a 4x4 identity matrix
@c JP
; 4x4の単位行列
@c COMMON
#2a((1 0 0 0) (0 1 0 0) (0 0 1 0) (0 0 0 1))
#2a:4:4((1 0 0 0) (0 1 0 0) (0 0 1 0) (0 0 0 1))

@c EN
; Arrays with non-zero start index
@c JP
; ゼロ始点でないインデックスを持つ配列
@c COMMON
; (array (shape -1 1 -2 0) 1 2 3 4)
 @result{}
#2a@@-1@@-2((1 2) (3 4))
#2a@@-1:2@@-2:2((1 2) (3 4))
@end example

@c EN
As a corner case, rank-0 array can contain one value.
The value is written after the array prefix (e.g. @code{#0a}) and
a whitespace.
@c JP
特殊なケースとして、ランク0の配列はひとつだけ値を保持できます。
値は、配列プレフィクス(例: @code{#0a})、およびひとつの空白の後に
表示されます。
@c COMMON

@example
@c EN
; Two rank-0 array, containing #f and (1), respectively
@c JP
; ランク0の二つの配列。それぞれ#fと(1)を値に持つ。
@c COMMON
#0a #f
#0a (1)
@end example
@end deftp


@deftp {Reader Syntax} @code{#,(<array> @var{shape} @var{obj} @dots{})}
@deftpx {Reader Syntax} @code{#,(<s8array> @var{shape} @var{obj} @dots{})}
@deftpx {Reader Syntax} @code{#,(<s8array> @var{shape} @var{obj} @dots{})}
@dots{}
@end deftp
@deftp {Reader Syntax} @code{#,(<c64array> @var{shape} @var{obj} @dots{})}
@deftpx {Reader Syntax} @code{#,(<c128array> @var{shape} @var{obj} @dots{})}
@c EN
This is an alternative array literal syntax.  Up to Gauche 0.9.15, this was
the only array external representation.  We can still read this format,
and you can print an array with this format by setting
@code{array} parameter of write controls to @code{reader-ctor}.

@var{shape} is a list
of even number of integers, and each 2@var{n}-th integer
and 2@var{n}+1-th integer specifies the
inclusive lower-bound and exclusive upper-bound of @var{n}-th dimension,
respectively.  The following @var{obj} @dots{} are the values in the array
listed in row-major order.
@c JP
これは配列のリテラル構文の別形式です。Gauche 0.9.15まではこれが唯一の
配列の外部表現でした。今のGaucheでもこの形式を読むことができ、
またwrite controlsの@code{array}パラメータを@code{reader-ctor}に
することで書き出すことができます。

@var{shape}は偶数個の整数のリストで、
2@var{n}番目の整数が@var{n}次元目のインデックスの下限を、2@var{n}+1番目の
整数が@var{n}次元目のインデックスの上限(+1)を表します。
その後に、配列の要素がrow-majorの順で書き出されます。
@c COMMON

@example
@c EN
; an array such that:
@c JP
; 次のような配列：
@c COMMON
;   8 3 4
;   1 5 9
;   6 7 2
#,(<array> (0 3 0 3) 8 3 4 1 5 9 6 7 2)

@c EN
; a 4x4 identity matrix
@c JP
; 4x4の単位行列
@c COMMON
#,(<array> (0 4 0 4) 1 0 0 0 0 1 0 0 0 0 1 0 0 0 0 1)

@c EN
; Arrays with non-zero start index
@c JP
; ゼロ始点でないインデックスを持つ配列
@c COMMON
#,(<array> (-1 1 -2 0) 1 2 3 4)

@c EN
; Rank-0 array
@c JP
; ランク0の配列
@c COMMON
#,(<array> () 3)
@end example
@end deftp

@node Array predicate and constructors, Array accessors and modifiers, Array literal syntax, Arrays
@subsection Array constructors and predicates
@c NODE 配列の述語とコンストラクタ

@defun array? obj
[SRFI-25]
@c MOD gauche.array
@c EN
Returns @code{#t} if @var{obj} is an array, @code{#f} otherwise.
It is equivalent to @code{(is-a? obj <array-base>)}.
@c JP
@var{obj}が配列であれば@code{#t}が、そうでなければ@code{#f}が返されます。
@code{(is-a? obj <array-base>)}と等価です。
@c COMMON
@end defun

@defun make-array shape :optional init
[SRFI-25]
@c MOD gauche.array
@c EN
Creates an array of shape @var{shape}.
@var{Shape} must be a [ @var{D} x 2 ] array, and for each @var{k}
(0 <= @var{k} < @var{D}), the [ @var{k} 0 ] element must be less than or
equal to the [ @var{k} 1] element.
If @var{init} is given, all the elements are initialized by it.
Otherwise, the initial value of the elements are undefined.
@c JP
Shapeが@var{shape}である配列を作成します。
@var{Shape}は [ @var{D} x 2 ] の配列で、
0 <= @var{k} < @var{D} なる各@var{k}に対して要素 [ @var{k} 0 ] は
要素[ @var{k} 1 ]以下でなければなりません。
@var{init}が与えられた場合は、配列の各要素が@var{init}で初期化されます。
@var{init}が与えられなかった場合の配列の要素の初期値は不定です。
@c COMMON

@example
(make-array (shape 0 2 0 2 0 2) 5)
 @result{} #3a(((5 5) (5 5)) ((5 5) (5 5)))
@end example
@end defun

@defun make-u8array shape :optional init
@defunx make-s8array shape :optional init
@findex make-u16array
@findex make-s16array
@findex make-u32array
@findex make-s32array
@findex make-u64array
@findex make-s64array
@findex make-f16array
@findex make-f32array
@findex make-f64array
@findex make-c32array
@dots{}
@end defun
@defun make-c64array shape :optional init
@defunx make-c128array shape :optional init
@c MOD gauche.array
@c EN
Like @code{make-array}, but creates and returns an uniform numeric array.
@c JP
@code{make-array}と似ていますが、均一な数値配列を返します。
@c COMMON
@end defun

@defun array-copy array
@c MOD gauche.array
@c EN
Returns a copy of @var{array}, with the same class, shape and
content.
@c JP
@var{array}と同じクラス、shape、内容を持つコピーを返します。
@c COMMON
@end defun

@defun shape bound @dots{}
[SRFI-25]
@c MOD gauche.array
@c EN
Takes even number of exact integer arguments, and returns
a two-dimensional array that is suitable for representing the shape
of an array.
@c JP
偶数個の正確な整数を引数に取り、配列のshapeとして使える2次元の配列を返します。
@c COMMON

@example
(shape 0 2 1 3 3 5)
 @result{} #2a((0 2) (1 3) (3 5))

(shape)
 @result{} #2a()
@end example
@end defun

@defun array shape init @dots{}
[SRFI-25]
@c MOD gauche.array
@c EN
Creates an array of shape @var{shape}, initializing its elements by
@var{init} @dots{}.
@c JP
Shapeが@var{shape}であるような配列を作成し、
その要素を@var{init} @dots{}で初期化します。
@c COMMON

@example
(array (shape 0 2 1 3) 'a 'b 'c 'd)
 @result{} #2a@@0@@1((a b) (c d))
@end example
@end defun

@defun u8array shape init @dots{}
@defunx s8array shape init @dots{}
@findex u16array
@findex s16array
@findex u32array
@findex s32array
@findex u64array
@findex s64array
@findex f16array
@findex f32array
@findex f64array
@findex c32array
@dots{}
@end defun
@defun c64array shape init @dots{}
@defunx c128array shape init @dots{}
@c MOD gauche.array
@c EN
Like @code{array}, but creates and returns an uniform numeric array
initialized by @var{init} @dots{}.
@c JP
@code{array}と同様ですが、@var{init} @dots{}で初期化された
均一な数値配列を返します。
@c COMMON

@example
(u8array (shape 0 2 0 2) 1 2 3 4)
 @result{} #2u8((1 2) (3 4))
@end example
@end defun

@defun share-array array shape proc
[SRFI-25]
@c MOD gauche.array
@c EN
Creates and returns a new array of shape @var{shape}, that shares
the backing storage with the given array @var{array}.
The procedure @var{proc} maps the indices of the new array to
the indices to the original array, i.e. @var{proc} must be a @var{n}-ary
procedure that returns @var{m} values, where @var{n} is the dimension
of the new array and @var{m} is the one of the original array.
Furthermore, @var{proc} must be an affine function; each mapping
has to be a linear combination of input arguments plus optional constant.
(@code{Share-array} optimizes the mapping function based on the affinity
assumption, so @var{proc} won't be called every time the new array
is accessed).
@c JP
Shapeが@var{shape}であり、与えられた配列@var{array}とバッキングストレージを
共有する新しい配列を作成して返します。
@var{proc}は、新しい配列へのインデックスを古い配列へのインデックスへ
マップする手続きです。新しい配列の次元数を@var{n}、古い配列の次元数を@var{m}と
した時、@var{proc}は@var{n}個の引数を取り@var{m}個の値を返す手続きでなければ
なりません。さらに、各マッピングはaffineマッピング、すなわち、
出力は入力の線形合成(プラス定数)でなければなりません。
(@code{share-array}は@var{proc}がaffineマッピングであるという事実に基づいた
最適化を行います。新しい配列にアクセスする度に@var{proc}が呼ばれるというわけでは
ありません)。
@c COMMON
@end defun

@defun tabulate-array shape proc :optional index
@c MOD gauche.array
@c EN
Calls @var{proc} over each index represented by the shape @var{shape},
and creates an array from the result of @var{proc}.  The optional
index object can be used in the same way as @code{array-for-each-index}.
The following example creates an identity matrix of the given shape:
@c JP
@var{shape}が表現する各インデックスについて@var{proc}を呼び出し、
その戻り値から配列を構築して返します。省略可能なインデックスオブジェクトの用途は
@code{array-for-each-index}と同じです。
次の例は与えられたシェイプに対する単位行列を生成します:
@c COMMON

@example
(tabulate-array (shape 0 3 0 3) (^(i j) (if (= i j) 1 0)))
  @result{} #2a((1 0 0) (0 1 0) (0 0 1))
@end example
@end defun

@defun identity-array dimension :optional class
@c MOD gauche.array
@c EN
Returns a fresh identity array of rank 2, with the given dimension.
You can pass one of array classes to @var{class} to make the result
the instance of the class; the default class is @code{<array>}.
@c JP
ランク2で行列ともに@var{dimension}である単位行列を作って返します。
配列のクラスを@var{class}に渡せば、結果はそのインスタンスになります。
デフォルトは@code{<array>}クラスです。
@c COMMON

@example
(identity-array 3)
 @result{} #2a((1 0 0) (0 1 0) (0 0 1))

(identity-array 3 <f32array>)
 @result{} #2f32((1.0 0.0 0.0) (0.0 1.0 0.0) (0.0 0.0 1.0))
@end example
@end defun


@node Array accessors and modifiers, Whole array operations, Array predicate and constructors, Arrays
@subsection Array accessors and modifiers
@c NODE 配列のアクセサと変更

@defun array-rank array
[SRFI-25]
@c MOD gauche.array
@c EN
Returns the number of dimensions of an array @var{array}.
@c JP
配列@var{array}の次元数を返します。
@c COMMON

@example
(array-rank (make-array (shape 0 2 0 2 0 2))) @result{} 3
(array-rank (make-array (shape))) @result{} 0
@end example
@end defun

@defun array-shape array
@c MOD gauche.array
@c EN
Returns a shape array of @var{array}.
@c JP
配列@var{array}のshapeを表す配列を返します。
@c COMMON
@end defun

@defun array-start array dim
@defunx array-end array dim
@defunx array-length array dim
[SRFI-25+]
@c MOD gauche.array
@c EN
@code{Array-start} returns the inclusive lower bound of index of
@var{dim}-th dimension of an array @var{array}.
@code{Array-end} returns the exclusive upper bound.
And @code{array-length} returns the difference between two.
@code{Array-start} and @code{array-end} are defined in SRFI-25.
@c JP
@code{array-start}は配列@var{array}の@var{dim}番目の次元の
インデックスの下限を返します。
@code{array-end}は上限+1を、そして@code{array-length}は両者の差を返します。
@code{array-start}と@code{array-end}はSRFI-25で定義されています。
@c COMMON

@example
(define a (make-array (shape 1 5 0 2)))

(array-start a 0)  @result{} 1
(array-end a 0)    @result{} 5
(array-length a 0) @result{} 4
(array-start a 1)  @result{} 0
(array-end a 1)    @result{} 2
(array-length a 1) @result{} 2
@end example
@end defun

@defun array-size array
@c MOD gauche.array
@c EN
Returns the total number of elements in the array @var{array}.
@c JP
配列@var{array}の全要素数を返します。
@c COMMON

@example
(array-size (make-array (shape 5 9 1 3))) @result{} 8
(array-size (make-array (shape))) @result{} 1
(array-size (make-array (shape 0 0 0 2))) @result{} 0
@end example
@end defun

@defun array-ref array k @dots{}
@defunx array-ref array index
[SRFI-25]
@c MOD gauche.array
@c EN
Gets the element of array @code{array}.  In the first form,
the element is specified by indices @var{k} @dots{}.
In the second form, the element is specified by an index object
@var{index}, which must be a vector or an one-dimensional array.
@c JP
配列@var{array}の要素を取り出します。最初の形式では、
要素は整数のインデックス@var{k} @dots{}で指定されます。
2番目の形式では、要素はベクタまたは1次元配列のインデックスオブジェクト@var{index}
で指定されます。
@c COMMON
@end defun

@defun array-set! array k @dots{} value
@defunx array-set! array index value
[SRFI-25]
@c MOD gauche.array
@c EN
Sets the element of array @var{array} to @var{value}.  In the first form,
the element is specified by indices @var{k} @dots{}.
In the second form, the element is specified by an index object
@var{index}, which must be a vector or an one-dimensional array.
@c JP
配列@var{array}の要素に@var{value}をセットします。
最初の形式では、
要素は整数のインデックス@var{k} @dots{}で指定されます。
2番目の形式では、要素はベクタまたは1次元配列のインデックスオブジェクト@var{index}
で指定されます。
@c COMMON
@end defun

@node Whole array operations,  , Array accessors and modifiers, Arrays
@subsection Whole array operations
@c NODE 配列全体に対する操作

@defun array-for-each-index array proc :optional index
@c MOD gauche.array
@c EN
Calls @var{proc} with every index of @var{array}.
If no @var{index} argument is provided, @var{proc} is called
as @code{(@var{proc} @var{i} @var{j} @var{k} @dots{})}, in which
(@var{i},@var{j},@var{k},@dots{}) walks over the index.
It begins from the least index value of each dimension, and
latter dimension is incremented faster.
@c JP
@var{array}の各インデックスに対して@var{proc}を呼びます。
@var{index}引数が省略された場合は、
@var{proc}はインデックス (@var{i}, @var{j},@var{k},@dots{}) に対して
@code{(@var{proc} @var{i} @var{j} @var{k} @dots{})} のように呼ばれます。
最初は各次元のインデックスの最小値から始まり、後の方の次元が優先的にインクリメントされます。
@c COMMON

@example
gosh> (define a (array (shape 0 2 0 2) 1 2 3 4))
a
gosh> a
#2a((1 2) (3 4))
gosh> (array-for-each-index a (^(i j) (print i","j)))
0,0
0,1
1,0
1,1
@end example

@c EN
This form of passing indexes is simple but not very efficient, though.
For better performance,
you can pass an index object to an optional
argument @var{index},
which is modified for each index and passed to @var{proc}.
The index object must be mutable, and
either a vector, an one-dimensional array, an s8vector, an s16vector
or an s32vector.  The length of the index object must match the
rank of the array.  Using index object is efficient since the loop
won't allocate.  Don't forget that the index object is destructively
modified within the loop.
@c JP
この形式の呼び出しは簡単なのですが、あまり効率が良くありません。
インデックスオブジェクトを省略可能引数@var{index}に渡すことで、
より良い性能を引き出すことができます。
インデックスオブジェクトはループの度に、各インデックスを表す値に書き換えられます。
インデックスオブジェクトに使えるのは、変更可能な、ベクタ・1次元の配列・
s8vector・s16vectorあるいはs32vectorで、その長さは配列@var{array}の
ランクと一致していなければなりません。インデックスオブジェクトを使うと、
ループ中に一切アロケーションが行われないため速度的に有利です。
ただし、ループの度にインデックスオブジェクトの内容が書き換えられることに
注意する必要があります。
@c COMMON

@example
gosh> (array-for-each-index a (cut format #t "~s\n" <>) (vector 0 0))
#(0 0)
#(0 1)
#(1 0)
#(1 1)

gosh> (array-for-each-index a (cut format #t "~s\n" <>) (s8vector 0 0))
#s8(0 0)
#s8(0 1)
#s8(1 0)
#s8(1 1)
@end example

@c EN
The procedure returns an unspecified value.
@c JP
戻り値は未定義です。
@c COMMON
@end defun

@defun shape-for-each shape proc :optional index
@c MOD gauche.array
@c EN
Calls @var{proc} with all possible indexes represented by the shape
@var{shape}.
The optional @var{index} argument works the same
way as @code{array-for-each-index}.  Returns an unspecified value.
@c JP
シェイプ@var{shape}が表現する全ての可能なインデックスに対して@var{proc}を呼びます。
省略可能な@var{index}引数の動作は@code{array-for-each-index}と同様です。
戻り値は未定義です。
@c COMMON

@example
gosh> (shape-for-each (shape 0 2 0 2) (^(i j) (print i","j)))
0,0
0,1
1,0
1,1
@end example
@end defun

@defun array-retabulate! array proc :optional index
@defunx array-retabulate! array shape proc :optional index
@c MOD gauche.array
@c EN
Calls @var{proc} over each index of the given @var{array}, and
modifies the array's element by the returned value of @var{proc}.
The optional index object can be used in
the same way as @code{array-for-each-index}.
The second form takes a shape; it must match
the @var{array}'s shape.  It is redundant, but may allow some
optimization in future in case @var{shape} is a literal.
Returns an unspecified value.
@c JP
配列@var{array}の各インデックスに対して@var{proc}を呼び、その戻り値で
@var{array}の要素を置き換えます。
省略可能なインデックスオブジェクトの用途は
@code{array-for-each-index}と同じです。
二番目の呼び出し形式は第二引数にシェイプを取ります。
それは@var{array}のシェイプと一致しなければなりません。
意味的には冗長ですが、@var{shape}がリテラルである場合、
何らかの最適化がなされる可能性があります。
戻り値は未定義です。
@c COMMON
@end defun

@defun array-map proc array0 array1 @dots{}
@defunx array-map shape proc array0 array1 @dots{}
@c MOD gauche.array
@c EN
The arguments @var{array0}, @var{array1}, @dots{} must be arrays
with the same shape.  For each set of corresponding elements of
the input arrays, @var{proc} is called, and a new array of the
same shape is created by the returned values.
The second form takes a shape argument, which must match the
shape of input array(s).  It is redundant, but may allow some
optimization in future in case @var{shape} is a literal.
@c JP
引数@var{array0}, @var{array1}, @dots{}は同じシェイプを持つ
配列でなければなりません。各入力配列の対応する要素について、
それらを引数として@var{proc}が呼ばれ、その戻り値から
新たな配列が作られて返されます。
二番目の呼び出し形式は第二引数にシェイプを取ります。
それは入力配列のシェイプと一致しなければなりません。
意味的には冗長ですが、@var{shape}がリテラルである場合、
何らかの最適化がなされる可能性があります。
@c COMMON

@example
(array-map - (array (shape 0 2 0 2) 1 2 3 4))
  @result{} #2a((-1 -2) (-3 -4))
@end example
@end defun

@defun array-map! array proc array0 array1 @dots{}
@defunx array-map! array shape proc array0 array1 @dots{}
@c MOD gauche.array
@c EN
Like @code{array-map}, but the results of @var{proc} are stored by the
given @var{array}, whose shape must match the shape of input array(s).
Returns unspecified value.
@c JP
@code{array-map}と似ていますが、@var{proc}の結果は
与えられた@var{array}に格納されます。@var{array}のシェイプは
入力配列のシェイプと同じでなければなりません。
戻り値は未定義です。
@c COMMON
@end defun

@defun array->vector array
@defunx array->list array
@c MOD gauche.array
@c EN
Returns a fresh vector or a fresh list of all elements in @var{array}.
@c JP
@var{array}の全要素を並べたベクタもしくはリストを作って返します。
@c COMMON

@example
(array->vector
 (tabulate-array (shape 1 3 1 4)
                 (^(i j) (+ (* 10 i) j))))
 @result{} #(11 12 13 21 22 23)
@end example
@end defun

@defun array-concatenate a b :optional dimension
@c MOD gauche.array
@c EN
Concatenates arrays at the specified dimension.  The sizes of the
specified dimension of two arrays must match, although the shapes
can be different.   Arrays can be of any ranks, but two ranks must
match.
@c JP
指定の次元で配列を結合します。指定の次元の大きさは一致していなければなりません。
それ以外のシェイプは異なっていても構いません。配列のランクはいくつであっても
構いませんが、両配列のランクは同じでなければなりません。
@c COMMON

@example
;;  [a b]              [a b]
;;  [c d] (+)       => [c d]
;;            [e f]    [e f]
(array-concatenate '#2a((a b) (c d))
                   '#2a((e f)))
 @result{} #2a((a b) (c d) (e f))

;;  [a b]     [e]    [a b e]
;;  [c d] (+) [f] => [c d f]
(array-concatenate '#2a((a b) (c d))
                   '#2a((e) (f))
                    1)
 @result{} #2a((a b e) (c d f))

@c EN
;; The index range can differ, as far as the sizes match
@c JP
;; 結合次元の大きさが同じであればインデックスの範囲は異なっていてもよい
@c COMMON
(array-concatenate '#2a((a b) (c d))
                   '#2a@@1@@0((e) (f))
                   1)
 @result{} #2a((a b e) (c d f))
@end example
@end defun

@defun array-transpose array :optional dim1 dim2
@c MOD gauche.array
@c EN
The given array must have a rank greater than or equal to 2.
Transpose the array's @var{dim1}-th dimension and
@var{dim2}-th dimension.  The default is 0 and 1.
@c JP
@var{array}はランク2以上の配列でなければなりません。
配列の@var{dim1}番目の次元と@var{dim2}番目の次元を転置します。
デフォルトは0番目と1番目です。
@c COMMON
@end defun

@defun array-rotate-90 array :optional dim1 dim2
@c MOD gauche.array
@c EN
The given array must have a rank greater than or equal to 2.
We regard the array as a matrix with @var{dim1}-th dimension
as rows and @var{dim2}-th dimension as columns, and returns
a fresh array whose content is filled by @emph{rotating}
@var{array} 90 degree clockwise.   The defaults of
@var{dim1} and @var{dim2} are 0 and 1, respectively.
@c JP
@var{array}はランク2以上の配列でなければなりません。
配列の@var{dim1}番目の次元と@var{dim2}番目の次元をそれぞれ行と列とみなした行列を
考え、その行列を時計まわりに90度回転した新たな配列を作って返します。
@c COMMON

@example
;; [1 2 3]      [4 1]
;; [4 5 6]  =>  [5 2]
;;              [6 3]
(array-rotate-90 '#2a((1 2 3) (4 5 6)))
 @result{} #2a((4 1) (5 2) (6 3))
@end example

@c EN
If @var{array} has a rank greater than 2, the array is
treated as a matrix of subarrays.
@c JP
@var{array}のランクが2より大きい場合は、@var{array}は「部分配列の行列」
と考えられます。
@c COMMON
@end defun

@defun array-flip array :optional dimension
@defunx array-flip! array :optional dimension
@c MOD gauche.array
@c EN
Flips the content of the array across the @var{dimension}-th dimension.
(default is 0).   @code{array-flip!} modifies the content of @var{array}
and return it.  @code{array-flip} doesn't modify @var{array} but creates
a fresh array with the flipped content and returns it.
@c JP
配列の内容を、指定番目の次元 (デフォルトは0) で裏返しにします。
@code{array-flip!}は@var{array}を直接変更してそれを返します。
@code{array-flip}は@var{array}には触らず、裏返した内容で新たな配列を作って返します。
@c COMMON

@example
;; [1 2 3]  =>  [4 5 6]
;; [4 5 6]      [1 2 3]
(array-flip '#2a((1 2 3) (4 5 6)))
 @result{} #2a((4 5 6) (1 2 3))

;; [1 2 3]  =>  [3 2 1]
;; [4 5 6]      [6 5 4]
(array-flip '#2a((1 2 3) (4 5 6)) 1)
 @result{} #2a((3 2 1) (6 5 4))
@end example
@end defun

@defun array-inverse array
@c MOD gauche.array
@c EN
Regards the @var{array} as a matrix, and returns its inverse matrix;
@var{array} must be 2-dimensional, and must have square shape.  If
@var{array} doesn't satisfy these conditions, an error is thrown.

If @var{array} isn't a regular matrix, @code{#f} is returned.
@c JP
@var{array}を行列とみなし、その逆行列を返します。
@var{array}は2次元で、正方行列となるシェイプを持っていなければなりません。
そうでない場合はエラーが投げられます。

@var{array}が正則行列でない場合は@code{#f}が返されます。
@c COMMON
@end defun

@defun determinant array
@defunx determinant! array
@c MOD gauche.array
@c EN
Regards the @var{array} as a matrix, and calculates its determinant;
@var{array} must be 2-dimensional, and must have square shape.  If
@var{array} doesn't satisfy these conditions, an error is thrown.

@code{determinant!} destructively modifies the given array during
calculation.  It is faster than @code{determinant}, which copies
@var{array} before calculation to preserve it.
@c JP
@var{array}を行列とみなし、その行列式を計算します。
@var{array}は2次元で、正方行列となるシェイプを持っていなければなりません。
そうでない場合はエラーが投げられます。

また、@code{determinant!}は計算過程で@var{array}の内容を破壊します。
@code{determinant}は計算の前に@var{array}をコピーするオーバヘッドが
ありますが、@var{array}は変更されません。
@c COMMON
@end defun

@defun array-trace array
@c MOD gauche.array
@c EN
Regards the @var{array} as a matrix, and calculates its trace;
@var{array} must be 2-dimensional, and must have square shape.  If
@var{array} doesn't satisfy these conditions, an error is thrown.
@c JP
@var{array}を行列とみなし、そのトレースを計算します。
@var{array}は2次元で、正方行列となるシェイプを持っていなければなりません。
そうでない場合はエラーが投げられます。
@c COMMON
@end defun

@defun array-mul a b
@c MOD gauche.array
@c EN
Arrays @var{a} and @var{b} must be rank 2.   Regarding them
as matrices, multiply them together.  The number of rows of @var{a}
and the number of columns of @var{b} must match.
@c JP
配列@var{a}と@var{b}はともに2次元でなければなりません。
それらを行列とみなして乗算を行います。@var{a}の行数と@var{b}の列数は
一致していなければなりません。
@c COMMON

@example
;;           [6 5]
;; [1 2 3] x [4 3] => [20 14]
;; [4 5 6]   [2 1]    [56 41]

(array-mul '#2a((1 2 3) (4 5 6))
           '#2a((6 5) (4 3) (2 1)))
 @result{} #2a((20 14) (56 41))
@end example
@end defun

@defun array-expt array pow
@c MOD gauche.array
@c EN
Raises @var{array} to the power of @var{pow}; @var{array} must be
a square matrix, and @var{pow} must be a nonnegative exact integer.
@c JP
@var{array}の@var{pow}乗を返します。@var{array}は正方行列、
@var{pow}は非負の正確な整数でなければなりません。
@c COMMON
@end defun

@defun array-div-left a b
@defunx array-div-right a b
@c MOD gauche.array
@c EN
Inverse of @code{array-mul}; @code{array-div-left}
returns a matrix @code{M} such that @code{(array-mul B M)}
equals to @code{A}, and @code{array-div-right} returns
a matrix @code{M} such that @code{(array-mul M B)} equals to @code{A}.
@var{A} and @var{B} must be a 2-dimensional square matrix.
If @code{B} isn't regular, an error is thrown.
@c JP
@code{array-mul}の逆を行います。
@code{array-div-left}は@code{(array-mul B M)}が@code{A}と
等しくなるような行列@code{M}を、
@code{array-div-right}は@code{(array-mul M B)}が@code{A}と
等しくなるような行列@code{M}を返します。
@var{A}と@var{B}は2次元の正方行列でなければなりません。
@var{B}が正則行列でない場合はエラーが通知されます。
@c COMMON
@end defun

@defun array-add-elements array array-or-scalar @dots{}
@defunx array-add-elements! array array-or-scalar @dots{}
@defunx array-sub-elements array array-or-scalar @dots{}
@defunx array-sub-elements! array array-or-scalar @dots{}
@defunx array-mul-elements array array-or-scalar @dots{}
@defunx array-mul-elements! array array-or-scalar @dots{}
@defunx array-div-elements array array-or-scalar @dots{}
@defunx array-div-elements! array array-or-scalar @dots{}
@c MOD gauche.array
@c EN
Element-wise arithmetics.  The second argument and after must
be an array of the same shape of the first argument, or a number;
if it is a number, it is interpreted as an array of the same shape
of the first argument, and each element of which is the given number.

Returns an array of the same shape of the first argument,
where each element is the result of addition, subtraction, multiplication
or division of the corresponding elements of the arguments.

The linear-update version (procedures whose name ends with @code{!})
may reuse the storage of the first array to calculate the result.
The first array must be mutable.  The caller must still use the returned
value instead of counting on the side effects.
@c JP
要素ごとの計算をする手続きです。2つ目以降の引数は、
最初の引数の配列と同じ形の配列か、数値でなければなりません。
数値の場合は、要素が全てその数値である、最初の引数の配列と同じ形の配列だと解釈されます。

要素ごとに加算、減算、乗算、除算を行い、結果を最初の引数の配列と同じ形の配列で返します。

@code{!}で終わっている手続きは、最初の配列を結果を作るために再利用するかもしれません。
したがって最初の配列は変更可能である必要があります。ただし、必ず再利用されるとは
限らないので、呼び出し側は常に戻り値を使う必要があります。
@c COMMON

@example
(array-add-elements '#2a((1 2) (3 4))
                    '#2a((5 6) (7 8))
                    10)
 @result{} #2a((16 18) (20 22))

(array-div-elements '#2a((1 3) (5 7))
                    100
                    '#2a((2 4) (6 8)))
 @result{} #2a((1/200 3/400) (1/120 7/800))
@end example

@c EN
If only one argument is passed, these procedures
returns the argument itself.
@c JP
ひとつだけ引数が渡された場合は、これらの手続きはその引数をそのまま返します。
@c COMMON

@c EN
You can mix different types of arrays as long as their shapes are
the same.  The result is the same type as the first argument.
@c JP
形が同じであれば、異なる型の配列同士での演算もできます。
結果は最初の引数の配列の型になります。
@c COMMON

@example
(array-mul-elements (make-u8array (shape 0 2 0 2) 3)
                    '#2a((1 3) (5 7)))
 @result{} #2u8((3 9) (15 21))
@end example
@end defun


@defun array-negate-elements array
@defunx array-negate-elements! array
@c EN
Returns an array with the same type of the shape of @var{array},
but each element is a negation of the corresponding
elements in the original array.
@c JP
@var{array}と同じ型、shapeだけれども各要素の符号が元の配列から反転されているような
配列を返します。
@c COMMON

@example
(array-negate-elements '#2a((1 2) (3 4)))
  @result{} #2a((-1 -2) (-3 -4))
@end example
@end defun

@defun array-reciprocate-elements array
@defunx array-reciprocate-elements! array
@c EN
Returns an array with the same type of the shape of @var{array},
but each element is a reciprocal of the corresponding
elements in the original array.
@c JP
@var{array}と同じ型、shapeだけれども各要素が元の配列の要素の逆数になっているような
配列を返します。
@c COMMON

@example
(array-reciprocate-elements '#2a((1 2) (3 4)))
  @result{} #2a((1 1/2) (1/3 1/4))
@end example
@end defun

@c ----------------------------------------------------------------------
@node Importing gauche built-ins, Bitvector utilities, Arrays, Library modules - Gauche extensions
@section @code{gauche.base} - Importing gauche built-ins
@c NODE Gauche組み込み関数のインポート, @code{gauche.base} - Gauche組み込み関数のインポート

@deftp {Module} gauche.base
@mdindex gauche.base
@c EN
This module exports Gauche built-in procedures and syntaxes, so that
they can be imported to other modules that don't inherit @code{gauche} module.

All the bindings available in the @code{gauche} module are exported,
except @code{import}, which is renamed to @code{gauche:import} to
avoid conflict with R7RS @code{import}.

The module extends @code{gauche.keyword}, so
also exports all the keywords---the bindings from @code{gauche.keyword}---
so that the code imports @code{gauche.base} can access to self-bound keywords
without inheriting the keyword module.
@c JP
このモジュールはGaucheの組み込み手続きと構文をexportし、
@code{gauche}モジュールを継承しない他のモジュールからもimportして
Gaucheの組み込み機能を使えるようにします。

@code{gauche}モジュールで見えるすべての束縛のうち、@code{import}を除いたものは
そのままexportされます。@code{import}はR7RSの@code{import}との
衝突を避けるため@code{gauche:import}としてexportされます。

このモジュールはまた、
全てのキーワード(@code{gauche.keyword}モジュールにある
束縛)もexportします。これで、Gauche関連のモジュールを継承しなくても
@code{gauche.base}をimportすれば自己束縛したキーワードを使えます。
@c COMMON
@end deftp

@c EN
Typical Gauche code doesn't need this module, for built-ins are available
by default through inheritance.
A newly created module @emph{inherits} the @code{gauche} module by default.
(@xref{Module inheritance}, for the details.)
@c JP
通常のGaucheコードはこのモジュールを必要としません。組み込み関数はモジュール継承によって、
何もしなくても使えるようになっています。
新たに作られるモジュールは、何も指定しなければ@code{gauche}モジュールを
継承するからです (詳しくは@ref{Module inheritance}参照)。
@c COMMON

@c EN
Sometimes you need a module that doesn't inherit the @code{gauche} module,
yet you want to use Gauche built-in features.  Particularly, R7RS libraries
and programs require any bindings to be explicitly imported,
so R7RS's @code{import} and @code{define-library} sets up the module not
to inherit the @code{gauche} module.   In R7RS code, you need
@code{(import (gauche base))} to use Gauche's built-in features.
@c JP
しばしば、@code{gauche}モジュールを継承しないけれどGaucheの組み込み関数を使いたい
という場合があります。特にR7RSライブラリとプログラムは、そこで使う束縛をすべて
陽にimportする必要があります。従ってGaucheでも、R7RSの@code{import}と
@code{define-library}は@code{gauche}モジュールを継承しないモジュールを設定します。
R7RSコードでGaucheの組み込み機能を使うには、
@code{(import (gauche base))}とする必要があります。
@c COMMON

@c EN
Another use case is to eliminate some built-in bindings, yet
keep the rest of bindings accessible, in your module.
For example, the following setup creates @code{almost-gauche} module
that has almost all default bindings except @code{string-scan}
and @code{string-split}:
@c JP
別の用途としては、自分のモジュールで、Gaucheの組み込み機能のうちいくつかを隠したい、
といった場合があります。例えば次のコードは、Gaucheの組み込み機能のうち
@code{string-scan}と@code{string-split}だけが見えない
@code{almost-gauche}というモジュールを作ります。
@c COMMON

@example
(define-module almost-gauche
  (use scheme.r5rs)
  (use gauche.base :except (string-scan string-split)
                   :rename ((gauche:import import)))
  (extend)
  )
(select-module almost-gauche)

;; your code here
@end example

@c EN
Note the empty @code{extend}; it empties the module's inheritance.
(The @code{:rename} option of @code{gauche.base} is just to get
the original name of @code{import} back in @code{almost-gauche} module;
if you don't use @code{import} directly, you won't need it.)
@c JP
空の@code{extend}フォームに注目してください。このフォームで、
モジュールの継承リストを空にします。
(@code{gauche.base}の@code{:rename}オプションは、@code{almost-gauche}内で
元の@code{import}の名前を使えるようにするためのものです。@code{import}を直接
使わないのならこの@code{:rename}オプションは不要です。)
@c COMMON

@c ----------------------------------------------------------------------
@node Bitvector utilities, Generating C code, Importing gauche built-ins, Library modules - Gauche extensions
@section @code{gauche.bitvector} - Bitvector utilities
@c NODE ビットベクタユーティリティ, @code{gauche.bitvector} - ビットベクタユーティリティ

@c EN
This module adds more operations on bitvectors.
This module and built-in bitvector procedures covers SRFI-178
Bitvector library interface (@pxref{Bitvector library})
@c JP
このモジュールは、ビットベクタを扱う多くの操作を提供します。
このモジュールの手続きと組み込みのビットベクタ手続きは、SRFI-178のスーパーセットに
なっています (@ref{Bitvector library}参照)。
@c COMMON

@deftp {Module} gauche.bitvector
@mdindex gauche.bitvector
@c EN
Gauche supports bitvectors as a native type, but the core library only
offers a handful of primitives (@pxref{Bitvectors}).
This module provides the comprehensive
operations on bitvectors.
@c JP
Gaucheはビットベクタを組み込みでサポートしていますが、コアで提供されるのは
ごく基本的な手続きのみです(@ref{Bitvectors}参照)。
このモジュールではビットベクタに対する包括的な操作を提供します。
@c COMMON
@end deftp

@c EN
@subheading Constructors
@c JP
@subheading コンストラクタ
@c COMMON

@defun bitvector-unfold f length seed @dots{}
@defunx bitvector-unfold-right f length seed @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Creates a bitvector of length @var{length}, and fill its contents by
repeatedly applying @var{f}.  The procedure @var{f} must take one more
than the number of seeds, and must return the same number
of values.  First, @var{f} is applied to the index and @var{seed} @dots{},
then its first return value (which must be a bit, i.e. 0, 1 or a boolean
value) is used to initialize the index-th element of the bitvector,
and the rest of the return value is used as the next argument to @var{f}.
It is repeated @var{length} times.
@c JP
長さ@var{length}のビットベクタを作り、その内容を@var{f}を繰り返し呼ぶことで
埋めて行きます。@var{f}は@var{seed} @dots{}に与えられた引数の数よりひとつ多い
引数を取り、同じ数の戻り値を返します。まず、@var{f}はインデックスおよび@var{seed} @dots{}
を引数として呼び出され、戻り値の最初の値(それはビット、すなわち0, 1, 真偽値のいずれかでなければなりません)がビットベクタのインデックス位置の値にセットされます。
次の@var{f}は、新たなインデックスおよび残りの戻り値を引数として呼び出されます。
これが@var{length}回繰り返されます。
@c COMMON

@c EN
While @code{bitvector-unfold} fills the bits from left to right,
@code{bitvector-unfold-right} does from right to left.
@c JP
@code{bitvector-unfold}はビットを左から右に、
@code{bitvector-unfold-right}は右から左に埋めて行きます。
@c COMMON

@example
(use math.prime)
(bitvector-unfold (^[index n]
                    (values (small-prime? n) (+ n 1)))
                  20 0)
  @result{} #*00110101000101000101
(bitvector-unfold-right (^[index n]
                          (values (small-prime? n) (+ n 1)))
                        20 0)
  @result{} #*10100010100010101100
@end example

@c EN
Note: This procedure follows the protocol of @code{vector-unfold}
(@pxref{R7RS vectors}), and has a different protocol from other
@code{unfold} procedures (@pxref{R7RS lists}).
@c JP
註: この手続きは@code{vector-unfold}のプロトコルに準じています (@ref{R7RS vectors}参照)。
他の@code{unfold}のプロトコルとは異なることに注意してください (@ref{R7RS lists}参照)。
@c COMMON
@end defun

@defun bitvector-reverse-copy bv :optional start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Copies a bitvector @var{bv} in reverse order.  Optional @var{start}
and @var{end} arguments limits the range of the input.
@c JP
ビットベクタ@var{bv}の、順序を逆にしたものを新に作って返します。
省略可能な@var{start}と@var{end}引数は入力の範囲を制限します。
@c COMMON

@example
(bitvector-reverse-copy #*10110011100011110000 4 16)
  @result{} #*111100011100
@end example
@end defun

@defun bitvector-append bv @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
All arguments must be bytevectors.  Returns a fresh bytevector
which is concatenation of all arguments.
@c JP
全ての引数はビットベクタでなければなりません。全てのビットベクタをつなげたビットベクタを
新たに作って返します。
@c COMMON
@end defun

@defun bitvector-concatenate bvs
[SRFI-178]
@c MOD gauche.bitvector
@c EN
The argument must be a list of bitvectors.  Returns a fresh bytevector
which is concatenation of all bitvectors.
@c JP
引数はビットベクタのリストでなければなりません。
その全てのビットベクタをつなげたビットベクタを新にたに作って返します。
@c COMMON
@end defun

@defun bitvector-append-subbitvectors bv start end @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
The number of arguments must be a multiple of 3.  Each triplet of
the arguments is a bytevector followed by start and end index,
specifying the input bytevector range.  Returns a fresh bytevector
which is concatenation of all the subvectors.
@c JP
引数の総数は3の倍数でなければなりません。それぞれの三つ組は、
ビットベクタと、そのビットベクタに対する開始インデックス、終了インデックスです。
それぞれのビットベクタの、インデックスで指定される範囲を抜き出したものを
つなげたビットベクタを新たに作って返します。
@c COMMON

@example
(bitvector-append-subbitvectors
  #*11100011 2 6
  #*01010101 3 8)
 @result{} #*100010101
@end example
@end defun

@c EN
@subheading Predicates
@c JP
@subheading 述語
@c COMMON

@defun bitvector-empty? bv
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns @code{#t} if @var{bv} is an empty bytevector,
@code{#f} if it is a non-empty bitvector.
An error is thrown if @var{bv} is not a bitvector.
@c JP
@var{bv}が空のビットベクタなら@code{#t}を、空でないビットベクタなら@code{#f}を返します。
@var{bv}がビットベクタでなければエラーが投げられます。
@c COMMON
@end defun

@defun bitvector=? bv @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
All arguments must be bitvectors.
Returns @code{#t} iff all the bitvectors have the same length and content.
If there's zero or one argument, it returns @code{#t}.
@c JP
全ての引数はビットベクタでなければなりません。
全てのビットベクタが同じ長さ、同じ内容なら@code{#t}を、そうでなければ@code{#f}を返します。
引数が0個もしくは1個の場合は@code{#t}を返します。
@c COMMON
@end defun

@c EN
@subheading Iteration
@c JP
@subheading 繰り返し
@c COMMON

@defun bitvector-take bv n
@defunx bitvector-take-right bv n
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a new bitvector with the first/last @var{n} bits of a bitvector @var{bv}.
An error is thrown if length of @var{bv} is less than @var{n}.
@c JP
ビットベクタ@var{bv}の最初から/終わりの@var{n}ビットを切り出した新たなビットベクタを
返します。@var{bv}の長さが@var{n}より小さければエラーが投げられます。
@c COMMON

@c EN
In Gauche, you can also use generic @code{(subseq bv 0 n)} to take the
first @var{n} bits.  @xref{Sequence framework}.
@c JP
Gaucheではジェネリックな@code{(subseq bv 0 n)}で最初の@var{n}ビットを
切り出すこともできます (@ref{Sequence framework}参照)。
@c COMMON
@end defun

@defun bitvector-drop bv n
@defunx bitvector-drop-right bv n
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a new bitvector with bits except first/last @var{n} bits of
a bitvector @var{bv}.
An error is thrown if length of @var{bv} is less than @var{n}.
@c JP
ビットベクタ@var{bv}の最初から/終わりの@var{n}ビットを取り除いた新たなビットベクタを
返します。@var{bv}の長さが@var{n}より小さければエラーが投げられます。
@c COMMON

@c EN
In Gauche, you can also use generic @code{(subseq bv n)}
to drop the first @var{n} bits.  @xref{Sequence framework}.
@c JP
Gaucheではジェネリックな@code{(subseq bv n)}で最初の@var{n}ビットを
取り除いたビットベクタを得ることもできます (@ref{Sequence framework}参照)。
@c COMMON
@end defun

@defun bitvector-segment bv n
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Slices a bitvector @var{bv} with @var{n}-bits each, and returns
a list of bitvectors.  If the length of @var{bv} isn't a multiple
of @var{n}, the last bitvector may be shorter.
@c JP
ビットベクタ@var{bv}を@var{n}ビットごとの切片に切り分け、
それぞれを新たなビットベクタにしたもののリストを返します。
@var{bv}が@var{n}の倍数でなければ、最後のビットベクタは@var{n}ビット未満になります。
@c COMMON
@end defun

@defun bitvector-fold/int kons knil bv1 bv2 @dots{}
@defunx bitvector-fold/bool kons knil bv1 bv2 @dots{}
@defunx bitvector-fold-right/int kons knil bv1 bv2 @dots{}
@defunx bitvector-fold-right/bool kons knil bv1 bv2 @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Fold @var{kons} over the elements of bitvectors with @var{knil} as
the initial state value.
@c JP
状態値を受け渡しながら、@var{kons}をビットベクタの各要素に適用してゆきます。
@var{knil}は最初の状態値です。
@c COMMON

@c EN
The @var{kons} procedure is always called as
@code{(kons state e1 e2 @dots{})}, where @var{e1} @var{e2} @dots{}
are elements from each bitvectors, as integer 0/1 (for @code{/int} procdures)
or boolean @code{#f}/@code{#t} (for @code{/bool} procedures).
This is the same order as @code{vector-fold} in
@code{scheme.vector} module (@pxref{R7RS vectors}).
(Note that list @code{fold} procedure calls the @var{kons} procedure
with different order; @pxref{Walking over lists}).
@c JP
@var{kons}は@code{(kons state e1 e2 @dots{})}のように
呼び出されます。ここで@var{e1} @var{e2} @dots{} は引数の各ビットベクタの対応する
要素を取り出したものです (@code{/int}の手続きでは0/1、@code{/bool}の手続きでは
@code{#f}/@code{#t})。
これは@code{scheme.vector}モジュールの@code{vector-fold}と同じ引数順です
(@ref{R7RS vectors})。
(リストについての@code{fold}手続きでは@var{kons}手続きの最後の引数として
状態値が渡されることに注意してください。@ref{Walking over lists}参照)。
@c COMMON

@c EN
All bitvectors must have the same length; otherwise, an error is thrown.
@c JP
引数の全てのビットベクタは同じ長さでなければなりません。
そうでなければエラーが投げられます。
@c COMMON
@end defun

@defun bitvector-map/int f bv1 bv2 @dots{}
@defunx bitvector-map/bool f bv1 bv2 @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Apply a procedure @var{f} over each element taken from given bitvectors.
The result of the procedure is gathered as a fresh bitvector and returned.
@c JP
手続き@var{f}を与えられたビットベクタから取り出したビットに対して適用し、
その結果を新たなビットベクタにまとめて返します。
@c COMMON

@example
(bitvector-map/int logand #*10101 #*00111)
  @result{} #*00101
@end example

@c EN
All bitvectors must have the same length; otherwise, an error is thrown.
@c JP
引数の全てのビットベクタは同じ長さでなければなりません。
そうでなければエラーが投げられます。
@c COMMON
@end defun

@defun bitvector-map!/int f bv1 bv2 @dots{}
@defunx bitvector-map!/bool f bv1 bv2 @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Apply a procedure @var{f} over each element taken from given bitvectors.
The result of the procedure is set into @var{bv1}.
@c JP
手続き@var{f}を与えられたビットベクタから取り出したビットに対して適用し、
その結果を@var{bv1}に破壊的代入します。
@c COMMON

@c EN
These procedure returns undefined value; you should count on the
side effect onto @var{bv1}.  In other words, they are not
linear-updating procedures.
@c JP
これらの手続きは未定義値を返します。呼び出し側は@var{bv1}への副作用を使わなければ
なりません。言い換えれば、これらの手続きは線形更新手続きではありません。
@c COMMON

@c EN
All bitvectors must have the same length; otherwise, an error is thrown.
@c JP
引数の全てのビットベクタは同じ長さでなければなりません。
そうでなければエラーが投げられます。
@c COMMON
@end defun

@defun bitvector-map->list/int f bv1 bv2 @dots{}
@defunx bitvector-map->list/bool f bv1 bv2 @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Apply a procedure @var{f} over each element taken from given bitvectors.
The result of the procedure is gathered as a list and returned.
@c JP
手続き@var{f}を与えられたビットベクタから取り出したビットに対して適用し、
その結果をリストに集めて返します。
@c COMMON

@c EN
All bitvectors must have the same length; otherwise, an error is thrown.
@c JP
引数の全てのビットベクタは同じ長さでなければなりません。
そうでなければエラーが投げられます。
@c COMMON
@end defun

@defun bitvector-value-map-index->list f bv val
@c MOD gauche.bitvector
@c EN
Apply a procedure @var{f} over each index such that the index-th element
of @var{bv} is @var{val}, which must be either a boolean value or @code{0}
or @code{1}.  The result of applications are gathered into a list,
from smaller index.
@c JP
ビットベクタ@var{bv}の要素のうち、それが@var{val}とビットとして
一致するもの (@code{#t}か@code{1}なら真と一致、@code{#f}か@code{0}なら偽と一致)
について、それぞれそのインデックスを引数に手続き@var{f}を呼びます。結果は
インデックスの小さい順にリストに集められて返されます。
@c COMMON

@c EN
For example, the following returns a list of indices where the
bit is true.
@c JP
下の例はビットベクタのビットが真であるインデックスのリストを返します。
@c COMMON

@example
(bitvector-value-map-index->list identity #*10011 #t)
  @result{} (0 3 4)
@end example
@end defun

@defun bitvector-for-each/int f bv1 bv2 @dots{}
@defunx bitvector-for-each/bool f bv1 bv2 @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Apply a procedure @var{f} over each element taken from given bitvectors.
The result of the procedure is discarded.
@c JP
与えられたビットベクタの各ビットに対して@var{f}を適用します。@var{f}の結果は捨てられます。
@c COMMON

@c EN
All bitvectors must have the same length; otherwise, an error is thrown.
@c JP
引数の全てのビットベクタは同じ長さでなければなりません。
そうでなければエラーが投げられます。
@c COMMON

@example
(bitvector-for-each/int print #*11100 #*01110 #00111)
  @result{} @r{prints}
100
110
111
011
001
@end example
@end defun

@defun bitvector-value-for-each-index f bv val
@c MOD gauche.bitvector
@c EN
Apply a procedure @var{f} over each index such that the index-th element
of @var{bv} is @var{val}, which must be either a boolean value or @code{0}
or @code{1}.  The result of @var{f} is discarded.
@c JP
@var{bv}の各ビットを最初から走査し、そのビットが@var{val}とビットとして一致したものについて、
そのインデックスを引数に@var{f}を呼び出します。@var{f}の結果は捨てられます。
@c COMMON

@example
(bitvector-value-for-each-index print #*1101111010 #f)
 @result{} @r{prints}
2
7
9
@end example

@c EN
See also @code{bitvector-value-map-index->list} above.
@c JP
上の@code{bitvector-value-map-index->list}も参照。
@c COMMON
@end defun

@c EN
@subheading Prefixes, suffixes, trimming and padding
@c JP
@subheading プレフィクス、サフィックス、トリム、パディング
@c COMMON

@defun bitvector-prefix-length bv1 bv2
@defunx bitvector-suffix-length bv1 bv2
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns the length of common prefix/suffix of two bitvectors
@var{bv1} and @var{bv2}.
@c JP
二つのビットベクタ@var{bv1}、@var{bv2}に共通するプレフィクスまたはサフィックスの
長さを返します。
@c COMMON

@example
(bitvector-prefix-length #*1100101001 #*110001101) @result{} 4
(bitvector-suffix-length #*1100101001 #*110001101) @result{} 2
@end example
@end defun

@defun bitvector-prefix? needle haystack
@defunx bitvector-suffix? needle haystack
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Both arguments must be bitvectors.  Returns @code{#t}
iff  @var{needle} is a prefix/suffix of @var{haystack}.
@c JP
引数はどちらもビットベクタでなければなりません。
@var{needle}が@var{haystack}のプレフィックスまたはサフィックスになっている時に
@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON

@example
(bitvector-prefix? #*101 #*1010100) @result{} #t
(bitvector-prefix? #*101 #*1000110) @result{} #f
(bitvector-suffix? #*110 #*1000110) @result{} #t
(bitvector-suffix? #*110 #*1010100) @result{} #f
@end example
@end defun

@defun bitvector-pad bit bv len
@defunx bitvector-pad-right bit bv len
[SRFI-178]
@c MOD gauche.bitvector
@c EN
If the length of a bitvector @var{bv} is smaller than @var{len},
returns a bitvector of length @var{len} by adding @var{bit} before/after
@var{bv}.  If the length of @var{bv} is greater than @var{len},
returns a bitvector of length @var{len} such that
@var{bv} left/right bits of @var{bv} are trimmed.
If the length of @var{bv} is equal to @var{len},
a copy of @var{bv} is returned as is.
@c JP
ビットベクタ@var{bv}の長さが@var{len}未満であれば、
長さが@var{len}になるまで@var{bv}の先頭もしくは末尾に@var{bit}を付加した
ビットベクタを作って返します。@var{bv}の長さが@var{len}より大きな場合は
長さ@var{len}になるまで@var{bv}の先頭もしくは末尾のビットを削ったビットベクタを
作って返します。@var{len}が@var{bv}の長さと同じなら、@var{bv}のコピーが
返されます。
@c COMMON

@example
(bitvector-pad 1 #*00010 10) @result{} #*1111100010
(bitvector-pad-right 1 #*00010 10) @result{} #*0001011111

(bitvector-pad 1 #*0100011 3) @result{} #*011
(bitvector-pad-right 1 #*0100011 3) @result{} #*010
@end example
@end defun

@defun bitvector-trim bit bv
@defunx bitvector-trim-right bit bv
@defunx bitvector-trim-both bit bv
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a fresh bitvector without preceding and/or trailing consecutive
@var{bit} from @var{bv}.
@c JP
ビットベクタ@var{bv}の先頭、末尾、あるいは両方から、連続する@var{bit}をできる限り
除いたビットベクタを新たに作って返します。
@c COMMON

@example
(bitvector-trim 0 #*000101000) @result{} #*101000
(bitvector-trim-right 0 #*000101000) @result{} #*000101
(bitvector-trim-both 0 #*000101000) @result{} #*101
@end example
@end defun

@c EN
@subheading Mutators
@c JP
@subheading 破壊的変更
@c COMMON

@defun bitvector-swap! bv i j
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Swap the @var{i}-th value and @var{j}-th value of a bitvector @var{bv}.
Returns an undefined value.
If the index is out of range, an error is thrown.
@c JP
ビットベクタ@var{bv}の@var{i}番目と@var{j}番目のビットを入れ替えます。
戻り値は未定義です。
インデックスが範囲外であればエラーが投げられます。
@c COMMON
@end defun

@defun bitvector-reverse! bv :optional start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Reverse the order of the content of a bitvector @var{bv} destructively.
The optional @var{start}/@var{end} indexes limit the range of the operation;
elements outside of the range won't be affected.
Returns an undefined value.
@c JP
ビットベクタ@var{bv}のビット順を破壊的に反転します。
省略可能な@var{start}/@var{end}が与えられた場合は、
それらのインデックスで指定される範囲内だけが変更対象となります。
戻り値は未定義です。
@c COMMON
@end defun

@defun bitvector-reverse-copy! to tstart from :optional start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Same as @code{(bitvector-copy! to start (bitvector-reverse-copy from start end))},
but potentially more efficient.
Returns an undefined value.
@c JP
@code{(bitvector-copy! to start (bitvector-reverse-copy from start end))}
と意味的に同じですが、より効率が良いかもしれません。
戻り値は未定義です。
@c COMMON
@end defun

@c EN
@subheading Conversion
@c JP
@subheading 変換
@c COMMON

@defun bitvector->list/int bv :optional start end
@defunx bitvector->list/bool bv :optional start end
@defunx reverse-bitvector->list/int bv :optional start end
@defunx reverse-bitvector->list/bool bv :optional start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a list of integers (0 or 1) or boolean values of bitvector
@var{bv}.  The first two procedures returns the leftmost bit first,
while the @code{reverse-} variations returns the rightmost bit first.
The optional @var{start}/@var{end} arguments limit the range of @var{bv}
to be extracted.
@c JP
ビットベクタ@var{bv}の内容を整数0または1のリスト、あるいは真偽値のリストとして
返します。最初の2つの手続きは左から、@code{reverse-}のつく2つの手続きは
右からビットを取ります。省略可能な@var{start}/@var{end}引数は
取り出すビットの範囲を指定します。
@c COMMON

@example
(bitvector->list/int #*010011000111 2 10)
 @result{} (0 0 1 1 0 0 0 1)
(reverse-bitvector->list/int #*010011000111 2 10)
 @result{} (1 0 0 0 1 1 0 0)
@end example
@end defun

@defun reverse-list->bitvector lis
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Like @code{list->bitvector} (@pxref{Bitvectors}), but pack bits
from right to left.
@c JP
@code{list->bitvector}(@ref{Bitvectors}参照)と似ていますが、
ビットを右から左に詰めてゆきます。
@c COMMON

@example
(reverse-list->bitvector '(1 0 #f #f #t #t))
 @result{} #*110001
@end example
@end defun

@defun bitvector->vector/int bv :optional start end
@defunx bitvector->vector/bool bv :optional start end
@defunx revrese-bitvector->vector/int bv :optional start end
@defunx reverse-bitvector->vector/bool bv :optional start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a vector of integers (0 or 1) or boolean values of
bitvector @var{bv}.  The first two procedures returns the leftmost bit first,
while the @code{reverse-} variations returns the rightmost bit first.
The optional @var{start}/@var{end} arguments limit the range of @var{bv}
to be extracted.
@c JP
ビットベクタ@var{bv}の内容を整数0または1のベクタ、あるいは真偽値のベクタとして
返します。最初の2つの手続きは左から、@code{reverse-}のつく2つの手続きは
右からビットを取ります。省略可能な@var{start}/@var{end}引数は
取り出すビットの範囲を指定します。
@c COMMON
@end defun

@defun vector->bitvetor vec :optional start end
@defunx reverse-vector->bitvector vec :optional start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Converts @var{vec} to a fresh bitvector;
@var{vec} must be a vector of 0/1 or boolean values.
The first procedure packs bits in the same left to right order,
while the @code{reverse-} version reverses the order.
The optional @var{start}/@var{end} arguments limit the range of @var{vec}
to be extracted.
@c JP
ベクタ@var{vec}を新たなビットベクタに変換します。@var{vec}の要素は
0、1、あるいは真偽値でなければなりません。
最初の手続きはビットを左から右に同じ順で、@code{reverse-}のつく手続きは
逆順で詰めてゆきます。
省略可能な@var{start}/@var{end}引数は@var{vec}から取り出すビットの範囲を指定します。
@c COMMON

@example
(vector->bitvector #(0 0 1 1 #t #f #t #t) 2 7)
  @result{} #*11101
(reverse-vector->bitvector #(0 0 1 1 #t #f #t #t) 2 7)
  @result{} #*10111
@end example
@end defun

@defun bitvector->integer bv
@defunx integer->bitvector n :optional len
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Convert between bitvectors and exact nonnegative integers.
Note that the leftmost bit of
@var{bv} corresponds to the least significant bit.
@c JP
ビットベクタと正確な非負整数とを相互変換します。
@var{bv}の最初(最左)のビットは、整数の最下位のビットに対応することに注意してください。
@c COMMON

@example
(bitvector->integer #*1000) @result{} 1
(bitvector->integer #*0001) @result{} 8
@end example

@c EN
This is consistent with @code{bits->list} etc. of SRFI-151
(@pxref{R7RS bitwise operations}), where least significant bit
corresponts to the first element of the list.
@c JP
SRFI-151の@code{bits->list}等は最下位ビットから順にビットをリストにするので、
それと一貫性があります(@ref{R7RS bitwise operations}参照)。
@c COMMON

@c EN
@code{integer->bitvector} takes an optional argument @var{len} to
specify the number of bits in @var{n} (count from the least siginificant
bit) to be taken.  When omitted, @code{(integer-length n)} is used
(@pxref{Basic bitwise operations}).
@c JP
@code{integer->bitvector}はさらに省略可能な@var{len}引数で、
引数の整数@var{n}の最下位から何ビット目までを取るかを指定できます。
省略時は@code{(integer-length n)}の値が使われます
(@ref{Basic bitwise operations}参照)。
@c COMMON

@example
(integer->bitvector 11)   @result{} #*1101
(integer->bitvector 11 8) @result{} #*11010000
@end example
@end defun

@c EN
@subheading Generators
@c JP
@subheading ジェネレータ
@c COMMON

@defun bitvector->int-generator bv :optional start end
@defunx bitvector->bool-generator bv :optional start end
@c MOD gauche.bitvector
@c EN
Returns a generator of integers (0 or 1) and boolean values, respectively.
The value is taken from a bitvector @var{bv} from left to right.
The optional @var{start}/@var{end} arguments limits the range of
the bitvector to be used.
@c JP
それぞれ、整数0か1を生成するジェネレータと真偽値を生成するジェネレータを返します。
値はビットベクタ@var{bv}の左から右へと取られます。
省略可能な@var{start}/@var{end}引数は@var{vec}から取り出すビットの範囲を指定します。
@c COMMON

@example
(generator->list (bitvector->int-generator #*10111000))
 @result{} (1 0 1 1 1 0 0 0)
@end example

@c EN
The names are consistent with Gauche convention.
SRFI-178 defines these procedures with the name
@code{make-bitvector/int-generator} and @code{make-bitvector/bool-generator}.
@c JP
これらの名前はGaucheの名前付けと一貫性があります。
SRFI-178ではこれらを
@code{make-bitvector/int-generator}および@code{make-bitvector/bool-generator}
と呼んでいます。
@c COMMON

@c EN
@xref{Generators}, for the details of generators.
@c JP
ジェネレータについて詳しくは@ref{Generators}を参照してください。
@c COMMON
@end defun


@defun make-bitvector/int-generator bv
@defunx make-bitvector/bool-generator bv
[SRFI-178]
@c MOD gauche.bitvector
@c EN
These are same as @code{bitvector->int-generator} and
@code{bitvector->bool-generator} except the optional arguments,
and defined in SRFI-178.
@c JP
これらは省略可能引数を取らないことを除いて、
それぞれ@code{bitvector->int-generator}および@code{bitvector->bool-generator}
と同じです。SRFI-178で定義されました。
@c COMMON
@end defun

@defun bitvector->index-generator bv val :optional start end
@c MOD gauche.bitvector
@c EN
Returns a generator that generates indexes of @var{bv} such that
the index-th value of @var{bv} matches @var{val}, which must
be either 0, 1 or a boolean value.  The bitvector is scanned from
left to right.
The optional @var{start}/@var{end} arguments limits the range of
the bitvector to be used.
@c JP
ビットベクタ@var{bv}のうち、値が@var{val}と一致するビットのインデックスを
左から右への順番で生成するジェネレータを返します。
@var{val}は0, 1, @code{#f}, @code{#t}のいずれかでなければなりません。
省略可能な@var{start}/@var{end}引数は@var{vec}から取り出すビットの範囲を指定します。
@c COMMON

@c EN
This is handy when you have a bitvector as a bitmap, and want to
process something where bit is set (or reset).
@c JP
これは、ビットベクタをビットマップとして使い、
ビットがセットされている/されていない要素について何かする、といった場合に便利です。
@c COMMON

@example
(generator->list (bitvector->index-generator #*101110001 1))
 @result{} (0 2 3 4 8)
@end example
@end defun

@defun make-bitvector-accumulator
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns an accumulator that collects given bits, and returns
a bitvector at the end of accumulation.
@c JP
与えられたビットを蓄積し、最後にビットベクタを作って返すアキュムレータを返します。
@c COMMON

@example
(let ((a (make-bitvector-accumulator)))
  (a 1)
  (a 0)
  (a 0)
  (a 1)
  (a 1)
  (a (eof-object)))
  @result{} #*10011
@end example

@c EN
@xref{R7RS generators}, for the details of accumulators.
@c JP
アキュムレータについて詳しくは@ref{R7RS generators}を参照してください。
@c COMMON
@end defun

@c EN
@subheading Bitwise operations
@c JP
@subheading ビット演算
@c COMMON

@defun bitvector-not bv
@defunx bitvector-not! bv
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector whose bits are logical negation of @var{bv}.
The linear updating version @code{bitvector-not!} may reuse @var{bv} to
produce the result.
@c JP
ビットベクタ@var{bv}の各ビットを反転したビットベクタを返します。
線形更新版の@code{bitvector-not!}は、結果を作るために
@var{bv}を破壊的に変更するかもしれません。
@c COMMON

@example
(bitvector-not #*10100) @result{} #*01011
@end example
@end defun

@defun bitvector-and bv1 bv2 bv @dots{}
@defunx bitvector-and! bv1 bv2 bv @dots{}
@defunx bitvector-ior bv1 bv2 bv @dots{}
@defunx bitvector-ior! bv1 bv2 bv @dots{}
@defunx bitvector-xor bv1 bv2 bv @dots{}
@defunx bitvector-xor! bv1 bv2 bv @dots{}
@defunx bitvector-eqv bv1 bv2 bv @dots{}
@defunx bitvector-eqv! bv1 bv2 bv @dots{}
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector whose bits are the result of logical operaion of
corresponding bits of the given bitvectors.  All bitvectors must be
the same length.
The linear updating version (procedures with @code{!}) may reuse @var{bv1} to
produce the result.
@c JP
与えられたビットベクタの各ビット間に指定の演算を施した結果を要素とするビットベクタを
返します。引数のビットベクタは全て同じ長さでなければなりません。
線形更新版(名前に@code{!}がついているもの)は、
結果を作るために@var{bv1}を破壊的に変更するかもしれません。
@c COMMON

@c EN
When more than two bitvectors are given to xor and eqv operation,
it works left-associatively, that is,
@c JP
3つ以上のビットベクタが与えられた場合、xorとeqv操作は左結合的に行われます。すなわち:
@c COMMON

@example
(bitvector-xor a b c)
 @equiv{} (bitvector-xor (bitvector-xor a b) c)
(bitvector-eqv a b c)
 @equiv{} (bitvector-eqv (bitvector-eqv a b) c)
@end example
@end defun

@defun bitvector-nand bv1 bv2
@defunx bitvector-nand! bv1 bv2
@defunx bitvector-nor bv1 bv2
@defunx bitvector-nor! bv1 bv2
@defunx bitvector-andc1 bv1 bv2
@defunx bitvector-andc1! bv1 bv2
@defunx bitvector-andc2 bv1 bv2
@defunx bitvector-andc2! bv1 bv2
@defunx bitvector-orc1 bv1 bv2
@defunx bitvector-orc1! bv1 bv2
@defunx bitvector-orc2 bv1 bv2
@defunx bitvector-orc2! bv1 bv2
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector, where each bit is the result of
logical operation of corresponding bits of @var{bv1} and @var{bv2}.
Two bitvectors must be the same length.
@c JP
@var{bv1}と@var{bv2}の対応する各ビットに演算を施した結果をビットベクタにして返します。
@var{bv1}と@var{bv2}は同じ長さでなければなりません。
@c COMMON

@example
nand  : (not (and bv1 bv2))
nor   : (not (or bv1 bv2)
andc1 : (and (not bv1) bv2)
andc2 : (and bv1 (not bv2))
orc1  : (or (not bv1) bv2)
orc2  : (or bv1 (not bv2))
@end example

@c EN
The linear updating version (procedures with @code{!}) may reuse @var{bv1} to
produce the result.
@c JP
線形更新版(名前に@code{!}がついているもの)は、
結果を作るために@var{bv1}を破壊的に変更するかもしれません。
@c COMMON
@end defun

@c EN
@subheading Quasi-integer operations
@c JP
@subheading 整数に準ずる演算
@c COMMON

@defun bitvector-logical-shift bv count bit
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector with the same length of @var{bv}, but the
content is shifted @var{count} bits to the left (when @var{count} >= 0)
or @var{-count} bits to the right (when @var{count} < 0).
The spilled bits are discarded.
The vacated bits are filled with @var{bit}.
@c JP
@var{bv}を左に@var{count}ビットシフトした、@var{bv}と同じ長さのビットベクタを
返します。@var{count}が負の場合は@var{-count}ビット右にシフトします。
あふれたビットは捨てられます。空き部分のビットは@var{bit}で埋められます。
@c COMMON

@example
(bitvector-logical-shift #*101100111000 4 1)
  @result{} #*001110001111
(bitvector-logical-shift #*101100111000 -4 0)
  @result{} #*000010110011
@end example
@end defun

@defun bitvector-count bit bv
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns the number of @var{bit} values in @var{bv}.
@c JP
@var{bv}中のビットで、@var{bit}と一致するものの数を返します。
@c COMMON
@end defun

@defun bitvector-count-run bit bv start
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns the number of consecutive @var{bit} values in @var{bv}, starting
from index @var{i}.
@c JP
@var{bv}中の、@var{i}ビット目から@var{bit}がいくつ連続しているか、その数を返します。
@c COMMON

@example
(bitvector-count-run 1 #*11111111100 0)
 @result{} 9
@end example
@end defun

@defun bitvector-if bv-if bv-then bv-else
[SRFI-178]
@c MOD gauche.bitvector
@c EN
All bitvectors must be the same length.
Returns a new bitvector with the same length, composed as follows.

The @var{k}-th bit of resulting vector is the same as @var{k}-th bit
of @var{bv-then} if @var{k}-th bit of @var{bv-if} is @code{#t} (1),
otherwise the same as @var{k}-th bit of @var{bv-else}
@c JP
各ビットベクタは同じ長さでなければなりません。
同じ長さのビットベクタを次のように構成して返します。

結果の@var{k}ビット目は、@var{bv-if}の@var{k}ビット目が@code{#t}(1)であれば
@var{bv-then}の@var{k}ビット目、そうでなければ@var{bv-else}の@var{k}ビット目と
同じになります。
@c COMMON
@end defun

@defun bitvector-first-bit bit bv
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns the index of the leftmost @var{bit} in @var{bv}.
If @var{bv} doesn't have @var{bit}, returns @code{-1}.
@c JP
@var{bv}中で一番左にある@var{bit}のインデックスを返します。
@var{bv}中に@var{bit}が無ければ@code{-1}を返します。
@c COMMON

@example
(bitvector-first-bit 1 #*0010011) @result{} 2
(bitvector-first-bit 0 #*1111111) @result{} -1
@end example
@end defun

@defun bitvector-last-bit bit bv
@c MOD gauche.bitvector
@c EN
Returns the index of the rightmost @var{bit} in @var{bv}.
If @var{bv} doesn't have @var{bit}, returns @code{-1}.
(NB: This is not in SRFI-178).
@c JP
@var{bv}中で一番右にある@var{bit}のインデックスを返します。
@var{bv}中に@var{bit}が無ければ@code{-1}を返します。
(これはSRFI-178には含まれていません)。
@c COMMON

@example
(bitvector-last-bit 1 #*00100110) @result{} 6
(bitvector-last-bit 0 #*11111111) @result{} -1
@end example
@end defun

@c EN
@subheading Bit field operations
@c JP
@subheading ビットフィールド操作
@c COMMON

@c EN
Those procedures operates on a partial field of a bitvector,
between @var{start}-th bit (inclusive) and @var{end}-th bit (exclusive).
@c JP
以下の手続きは、ビットベクタの
@var{start}ビット目(含む)から@var{end}ビット目(含まない)までの部分について
操作するものです。
@c COMMON

@defun bitvector-field-any? bv start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns @code{#t} iff at least one bit between @var{start} and @var{end}
in @var{bv} is 1.
@c JP
ビットベクタ@var{bv}の@var{start}ビット目から@var{end}ビット目までのいずれかに
1のビットがあれば@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON

@c EN
This is equivalent to @code{(bitvector-any-value? bv 1 start end)},
using Gauche's built-in procedure (@pxref{Bitvectors}).
@c JP
Gaucheの組み込み手続きを使って
@code{(bitvector-any-value? bv 1 start end)}とした場合と同じです
(@ref{Bitvectors}参照)。
@c COMMON
@end defun

@defun bitvector-field-every? bv start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns @code{#t} iff every bit between @var{start} and @var{end}
in @var{bv} is 1.
@c JP
ビットベクタ@var{bv}の@var{start}ビット目から@var{end}ビット目までのすべてが
1であれば@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON

@c EN
This is equivalent to @code{(bitvector-every-value? bv 1 start end)},
using Gauche's built-in procedure (@pxref{Bitvectors}).
@c JP
Gaucheの組み込み手続きを使って
@code{(bitvector-every-value? bv 1 start end)}とした場合と同じです
(@ref{Bitvectors}参照)。
@c COMMON
@end defun

@defun bitvector-field-clear bv start end
@defunx bitvector-field-clear! bv start end
@defunx bitvector-field-set bv start end
@defunx bitvector-field-set! bv start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector with the same content as @var{bv}, except
the bits between @var{start} (inclusive) and @var{end} (exclusive)
are cleared or set, respectively.
@c JP
ビットベクタ@var{bv}の内容のうち、
@var{start}ビット目から@var{end}ビット目までのすべてがクリアされた、
あるいはセットされたビットベクタをそれぞれ返します。
@c COMMON

@c EN
The liner-updating version may mutate @var{bv} to produce the result.
@c JP
線形更新版は結果を作るために@var{bv}を破壊的に変更するかもしれません。
@c COMMON

@example
(bitvector-field-clear #*10010010101001 2 7)
 @result{} #*10000000101001
(bitvector-field-set #*10010010101001 2 7)
 @result{} #*10111110101001
@end example
@end defun

@defun bitvector-field-replace to from start end
@defunx bitvector-field-replace! to from start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector with the same content as @var{to-bv}, except
its bits between @var{start} (inclusive) and @var{end} (exclusive)
are replaced with the content of @var{from-bv}.
@c JP
ビットベクタ@var{bv}の内容のうち、
@var{start}ビット目から@var{end}ビット目までを、
@var{from-bv}の内容で置き換えたビットベクタを返します。
@c COMMON

@c EN
The length of @var{from-bv} must be at least @var{end}-@var{start}.
If it is longer, the exceeding bits are ignored.
@c JP
@var{from-bv}の長さは少なくとも@var{end}-@var{start}だけなければなりません。
@var{from-bv}がそれより長い場合、余分なビットは無視されます。
@c COMMON

@c EN
The liner-updating version may mutate @var{to-bv} to produce the result.
@c JP
線形更新版は結果を作るために@var{bv}を破壊的に変更するかもしれません。
@c COMMON

@example
(bitvector-field-replace #*10010010101001 #*110011 2 8)
 @result{} #*10110011101001
@end example

@c EN
See also @code{bitvector-field-replace-same} below.
@c JP
下の@code{bitvector-field-replace-same}も参照のこと。
@c COMMON
@end defun

@defun bitvector-field-replace-same to-bv from-bv start end
@defunx bitvector-field-replace-same! to-bv from-bv start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector with the same content as @var{to-bv}, except
its bits between @var{start} (inclusive) and @var{end} (exclusive)
are replaced with the content of @var{from-bv} between @var{start} and
@var{end}.
@c JP
ビットベクタ@var{bv}の内容のうち、@var{start}ビット目から@var{end}ビット目までを、
@var{from-bv}の@var{start}ビット目から@var{end}ビット目までで置き換えたものを返します。
@c COMMON

@c EN
The length of @var{from-bv} must be greater than or equal to @var{end}.
@c JP
@var{from-bv}の長さは@var{end}より大きくなければなりません。
@c COMMON

@c EN
The liner-updating version may mutate @var{to-bv} to produce the result.
@c JP
線形更新版は結果を作るために@var{bv}を破壊的に変更するかもしれません。
@c COMMON

@example
(bitvector-field-replace-same #*10010010101001 #*11001100 2 8)
 @result{} #*10001100101001
@end example

@c EN
See also @code{bitvector-field-replace} above.
@c JP
上の@code{bitvector-field-replace}も参照のこと。
@c COMMON
@end defun


@defun bitvector-field-rotate bv count start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector whose content is the same as @var{bv} except
the range between @var{start}-th bit (inclusive) and
@var{end}-th bit (exclusive) being rotated by @var{count} bits toward
right.  You can give a negative @var{count} to rotate towards left.
@c JP
ビットベクタ@var{bv}の内容のうち、@var{start}ビット目から@var{end}ビット目までが
@var{count}ビットだけ右にローテートされた内容に置き換えられているものを返します。
@var{count}が負なら、その絶対値分だけ左にローテートします。
@c COMMON

@example
(bitvector-field-rotate #*001100110011 1 4 8)
 @result{} #*001101100011
(bitvector-field-rotate #*001100110011 -1 4 8)
 @result{} #*001110010011
@end example
@end defun

@defun bitvector-field-flip bv start end
@defunx bitvector-field-flip! bv start end
[SRFI-178]
@c MOD gauche.bitvector
@c EN
Returns a bitvector whose content is the same as @var{bv}
except the bits in the range
between @var{start}-th bit (inclusive) and
@var{end}-th bit (exclusive) are inverted.
@c JP
ビットベクタ@var{bv}の内容のうち、@var{start}ビット目から@var{end}ビット目までの
ビットが論理否定されているものを返します。
@c COMMON

@c EN
The liner-updating version may mutate @var{to-bv} to produce the result.
@c JP
線形更新版は結果を作るために@var{bv}を破壊的に変更するかもしれません。
@c COMMON

@example
(bitvector-field-flip #*001100110011 4 8)
 @result{} #*001111000011
@end example
@end defun



@c ----------------------------------------------------------------------
@node Generating C code, Character code conversion, Bitvector utilities, Library modules - Gauche extensions
@section @code{gauche.cgen} - Generating C code
@c NODE Cコードの生成, @code{gauche.cgen} - Cコードの生成

@c EN
Significant part of Gauche is written in Gauche or S-expression
based DSL.  During the building process, they are converted
into C sources and then compiled by C compiler.
The @code{gauche.cgen} module and its submodules expose
the functionality Gauche build process is using to the general use.
@c JP
Gauche本体の多くの部分は、Gauche自身、もしくはS式ベースのDSLで書かれています。
これらのコードはビルド中にCソースに変換され、Cコンパイラで
コンパイルされます。
@code{gauche.cgen}モジュールおよびそのサブモジュールは、
Gaucheビルドプロセスが使っているこの機能を一般にも使えるように公開するものです。
@c COMMON

@c EN
Required features for a C code generator differ greatly among
applications, and too much scaffolding could be a constraint
for the module users.  So, instead of providing a single
solid framework, we provide a set of loosely coupled modules
so that you can combine necessary features freely.  In fact,
some of Gauche build process only use @code{gauche.cgen.unit}
and @code{gauche.cgen.literal} (see @file{src/builtin-syms.scm},
for example).
@c JP
Cコードジェネレータに要求される機能はアプリケーションによって多種多様であり、
あまりがちがちに枠組みを固定してしまうと却って使い辛くなるでしょう。
そこで、ひとつの固定したフレームワークではなく、
ゆるく連携するいくつかのモジュールを提供し、ユーザが必要な機能を自由に
組み合わせて使えるようにしてあります。実際、Gaucheのビルド時に走る
プロセスの中には、@code{gauche.cgen.unit}や@code{gauche.cgen.literal}だけしか
使わないものもあります(例えば@file{src/builtin-syms.scm}を見てください)。
@c COMMON

@deftp {Module} gauche.cgen
@mdindex gauche.cgen
@c EN
This is a convenience module that extends
@code{gauche.cgen.unit}, @code{gauche.cgen.literal},
@code{gauche.cgen.type} and @code{gauche.cgen.cise} together.
@c JP
このモジュールは、簡便のために
@code{gauche.cgen.unit}、@code{gauche.cgen.literal}、
@code{gauche.cgen.type}、@code{gauche.cgen.cise}を
extendしたものです。
@c COMMON
@end deftp

@c EN
Usually you can just use @code{gauche.cgen} and don't need
to think about individual submodules.
The following subsections are organized by submodules
only for the convenience of explanation.
@c JP
大抵の場合、@code{gauche.cgen}をuseしておけば、個々のサブモジュールについて
考える必要はありません。
以降のセクションは主に説明のしやすさのために、サブモジュールごとに
分けて記述してあります。
@c COMMON

@menu
* Generating C source files::   gauche.cgen.unit
* Generating Scheme literals::  gauche.cgen.literals
* Conversions between Scheme and C::  gauche.cgen.type
* C in S expression::           gauche.cgen.cise
* Stub generation::             gauche.cgen.stub
@end menu

@node Generating C source files, Generating Scheme literals, Generating C code, Generating C code
@subsection Generating C source files
@c NODE Cソースファイルを生成する

@c EN
One of the tricky issues about generating C source is that
you have to put several fragments of code in different
parts of the source file, even you want to say just one thing---that is,
sometimes you have to put declaration before the actual definition,
plus some setup code that needs to be run at initialization time.
The @code{<cgen-unit>} class takes care of such code placement.
@c JP
Cソースを生成する際に面倒なのは、ひとつの機能を実装するのにも、
ソースの断片を離れた場所に配置しなければならないことです。
それが参照されているコードより前に宣言が置かれなければならないですし、
必要な初期化コードは初期化ルーチン内に書かれなければなりません。
@code{<cgen-unit>}クラスはそういったコード配置の面倒をみてくれます。
@c COMMON

@c EN
@subsubheading Creating a frame
@c JP
@subsubheading 枠組みを作る
@c COMMON

@deftp {Class} <cgen-unit>
@clindex cgen-unit
@c MOD gauche.cgen
@c EN
A @emph{cgen-unit} is a unit of C source generation.
It corresponds to one .c file, and optionally one .h file.
During the processing, a "current unit" is kept in a parameter
@code{cgen-current-unit}, and most cgen APIs implicitly work to it.
@c JP
@emph{cgen-uint}はCソースコード生成の単位です。
ひとつのインスタンスがひとつの@code{.c}ファイルと、
必要に応じてひとつの@code{.h}ファイルに対応します。
処理中には「現在のunit」がパラメータ@code{cgen-current-unit}に束縛されていて、
多くのcgen APIはそれを暗黙に参照します。
@c COMMON

@c EN
The following slot are for public use.  They are used to tailor
the output.  Usually you set those slots at initialization time.
The effect is undefined if you change them in the middle of
the code generation process.
@c JP
以下のスロットが公開されていて、出力をカスタマイズするのに使えます。
通常、これらのスロットは初期化時に設定します。
コード生成の途中でこれらのスロットの値を変えた場合の動作は未定義です。
@c COMMON

@defivar {<cgen-unit>} name
@c EN
A string to name this unit.  This is used for the default name
of the generated files (@file{@var{name}.c} and @file{@var{name}.h})
and the suffix of the default name of initialization function.
Other cgen modules may use this to generate names.  Avoid using
characters that are not valid for C identifiers.

You can override those default names by setting the other slots.
@c JP
このunitの名前を示す文字列。これは、
生成されるファイルのデフォルトの名前
(@file{@var{name}.c} と @file{@var{name}.h})、
および初期化関数名に使われます。
他のcgenモジュールでも、この値をもとに名前を作り出すものがあります。
従って、Cの識別子として有効な文字だけを使うようにしてください。

生成されるデフォルトの名前は個別に他のスロットで上書きすることができます。
@c COMMON
@end defivar

@defivar {<cgen-unit>} c-file
@defivarx {<cgen-unit>} h-file
@c EN
The name of the C source file and header file, in strings.
If they are @code{#f} (by default), the value of @code{name} slot
is used as the file name, with extension @code{.c} or @code{.h}
is attached, respectively.

To get the file names to be generated, use @code{cgen-unit-c-file}
and @code{cgen-unit-h-file} generic functions, instead of reading
these slots.
@c JP
Cソースファイルとヘッダファイルの名前を指定する文字列。
デフォルトは@code{#f}で、その場合は@code{name}スロットの値に
拡張子@code{.c}および@var{.h}をつけたものが使われます。

生成されるファイル名を使いたい場合は、これらのスロットの値ではなく、
@code{cgen-unit-c-file}および@code{cgen-unit-h-file}を呼んでください。
@c COMMON
@end defivar

@defivar {<cgen-unit>} preamble
@c EN
A list of strings to be inserted at the top of the generated sources.
The default value is @code{("/* Generated by gauche.cgen */")}.
Each string appears in its own line.
@c JP
生成されるソースの先頭に挿入される文字列のリスト。
デフォルトは@code{("/* Generated by gauche.cgen */")}です。
各文字列が独立した行になります。
@c COMMON
@end defivar

@defivar {<cgen-unit>} init-prologue
@defivarx {<cgen-init>} init-epilogue
@c EN
A string to start or to end the initialization function, respectively.
The default value of @code{init-prologue} is
@code{"void Scm_Init_NAME(void) @{"} where @code{NAME} is the
value of the @code{name} slot.  The default value of @code{init-epilogue}
is just @code{"@}"}.  Each string appears in its own line.

To get the default initialization function name, use @code{cgen-unit-init-name}
generic function.

To customize initialization function name, arguments and/or return type,
set @code{init-prologue}.

The content of initialization function is filled by the code
fragments registered by @code{cgen-init}.
@c JP
初期化関数の先頭と末尾に置かれる文字列。
@code{init-prologue}のデフォルトは
@code{"void Scm_Init_NAME(void) @{"}、
@code{init-epilogue}のデフォルトは
@code{"@}"}です。ただし@code{NAME}は@code{name}スロットの値です。
各文字列は独立した行におかれます。

デフォルトの初期化関数名を知りたい場合は、@code{gen-unit-init-name}を呼んでください。

初期化関数名やその引数をカスタマイズしたい場合は、
@code{init-prologue}を変更してください。

初期化関数の中身は、@code{cgen-init}で登録されたコード片から生成されます。
@c COMMON
@end defivar
@end deftp

@deffn {Parameter} cgen-current-unit
@c EN
A parameter to keep the current cgen-unit.
@c JP
現在のcgen unitを保持するパラメータです。
@c COMMON
@end deffn

@c EN
A typical flow of generating C code is as follows:
@c JP
Cコードを生成する典型的な流れは次のとおりです。
@c COMMON

@enumerate
@item
@c EN
Create a @code{<cgen-unit>} instance and make it the current unit.
@c JP
@code{<cgen-unit>}のインスタンスを作り、現在のunitとする。
@c COMMON
@item
@c EN
Call code insertion APIs with code fragments.  Fragments are accumulated
in the current unit.
@c JP
コード片を挿入するAPIを呼ぶ。コード片は現在のunitに蓄積される。
@c COMMON
@item
@c EN
Call @emph{emit} method (@code{cgen-emit-c}, @code{cgen-emit-h})
on the unit, which generates a C file
and optionally a header file.
@c JP
unitに対して@emph{emit}メソッド(@code{cgen-emit-c}、@code{cgen-emit-h})
を呼ぶ。これでCファイルと、必要に応じてヘッダファイルが生成される。
@c COMMON
@end enumerate

@deffn {Generic Function} cgen-emit-c cgen-unit
@deffnx {Generic Function} cgen-emit-h cgen-unit
@c MOD gauche.cgen
@c EN
Write the accumulated code fragments in @var{cgen-unit} to a
C source file and C header file.  The name of the files are
determined by calling @code{cgen-unit-c-file} and @code{cgen-unit-h-file},
respectively.  If the files already exist, its content is overwritten;
you can't gradually write to the files.
So, usually these procedures are called at the last step of the code
generation.
@c JP
@var{cgen-unit}に蓄積されたコード片を、それぞれCソースファイルとCヘッダファイルに
書き出します。ファイルの名前はそれぞれ@code{cgen-unit-c-file}と
@code{cgen-unit-h-file}が返す値になります。
ファイルが既に存在する場合、それは上書きされます
(コードを追加してゆくようなことはできません)。
したがって、これらはコード生成の最後のステップで呼ばれるのが普通です。
@c COMMON

@c EN
We'll explain the details of how each file is organized under
``Filling the content'' section below.
@c JP
各ファイルがどう構成されるかは、下の「内容を埋めてゆく」の項を参照してください。
@c COMMON
@end deffn

@deffn {Generic Function} cgen-unit-c-file cgen-unit
@deffnx {Generic Function} cgen-unit-h-file cgen-unit
@c MOD gauche.cgen
@c EN
Returns a string that names C source and header file for
@var{cgen-unit}, respectively.  The default method first
looks at @code{c-file} or @code{h-file} slot of the
@var{cgen-unit}, and if it is @code{#f}, use the value of @code{name}
slot and appends an extension @code{.c} or @code{.h}.
@c JP
@var{cgen-unit}が扱うCソースファイルおよびヘッダファイルの名前を返します。
デフォルトメソッドは、まず@var{cgen-unit}の@code{c-file}または@code{h-file}スロット
の値を見て、@code{#f}でなければそれを返し、
@code{#f}であれば@code{name}スロットの値に
@code{.c}または@code{.h}の拡張子をつけたものを返します。
@c COMMON
@end deffn

@deffn {Generic Function} cgen-unit-init-name cgen-unit
@c MOD gauche.cgen
@c EN
Returns a string that names the initialization function
generated to C.  It is used to create the default
@code{init-prologue} value.
@c JP
Cで生成される初期化関数の名前を返します。この名前は@code{init-prologue}の
デフォルト値の中で使われます。
@c COMMON
@end deffn

@c EN
@subsubheading Filling the content
@c JP
@subsubheading 中身を埋めてゆく
@c COMMON

@c EN
There are four parts to which you can add C code
fragment.  Within each part, code fragments are rendered in the
same order as added.
@c JP
Cコード片を追加できるパートは4つあります。それぞれのパートの中で、
コード片は追加された順に出力されます。
@c COMMON

@table @asis
@item extern
@c EN
This part is put into the header file, if exists.
@c JP
このパートは、ヘッダファイルに出力されます。
@c COMMON
@item decl
@c EN
Placed at the beginning of the C source, after the standard
prologue.
@c JP
Cソースファイル中の先頭部分、標準の先頭要素が出力されたあとに出力されます。
@c COMMON
@item body
@c EN
Placed in the C source, following the 'decl' part.
@c JP
Cソースファイル中の、declパートの後に出力されます。
@c COMMON
@item init
@c EN
Placed inside the initialization function, which appears at
the end of the C source.
@c JP
Cソースファイルの末尾に出力される、初期化関数の中に出力されます。
@c COMMON
@end table

@c EN
The following procedures are the simple way to put a source
code fragments in an appropriate part:
@c JP
それぞれのパートにコードを追加するための手続きは次のとおりです。
@c COMMON

@defun cgen-extern code @dots{}
@defunx cgen-decl code @dots{}
@defunx cgen-body code @dots{}
@defunx cgen-init code @dots{}
@c MOD gauche.cgen
@c EN
Put code fragments @var{code} @dots{} to the appropriate parts.
Each fragment must be a string.
@c JP
コード片@var{code} @dots{}を各パートに追加します。
各コード片は文字列でなければなりません。
@c COMMON
@end defun

@c EN
This is a minimal example to show the typical usage.
After running this code you'll get @code{my-cfile.c} and
@code{my-cfile.h} in the current directory.
@c JP
下に、典型的な使い方の単純な例を示します。このコードを走らせると、
カレントディレクトリに@code{my-cfile.c}と@code{my-cfile.h}ができます。
@c COMMON

@example
(use gauche.cgen)

(define *unit* (make <cgen-unit> :name "my-cfile"))

(parameterize ([cgen-current-unit *unit*])
  (cgen-decl "#include <stdio.h>")
  (cgen-init "fprintf(stderr, \"initialization function\\n\");")
  (cgen-body "void foo(int n) @{ printf(stderr, \"got %d\\n\", n); @}")
  (cgen-extern "void foo(int n);")
  )

(cgen-emit-c *unit*)
(cgen-emit-h *unit*)
@end example

@c EN
These are handy escaping procedures; they are useful even
if you don't use other parts of the @code{cgen} modules.
@c JP
次に示す手続きは、Cコードとして安全になるように文字列をエスケープします。
他の@code{cgen}モジュールを使わずにCコードを生成する際に便利です。
@c COMMON

@defun cgen-safe-name string
@defunx cgen-safe-name-friendly string
@defunx cgen-safe-string string
@defunx cgen-safe-comment string
@c MOD gauche.cgen
@c EN
Escapes characters invalid in C identifiers, C string literals or C comments.
@c JP
Cの識別子、文字列リテラル、あるいはコメントとして使えない文字の並びをエスケープします。
@c COMMON

@c EN
With @code{cgen-safe-name}, characters other than ASCII alphabets
and digits are converted to a form @code{_XX}, where @code{XX} is
hexadecimal notation of the character code.  (Note that the character
@code{_} is also converted.)  So the returned string can be used
safely as a C identifier.  The mapping is injective, that is,
if the source strings differ, the result string always differ.
@c JP
@code{cgen-safe-name}は、文字列中にASCIIアルファベットや数字以外の文字が
現れたら、@code{_XX}に変換します。ここで@code{XX}はその文字の文字コードの
16進数表現です(@code{_}自身も変換されます)。
返される文字列はそのままCの識別子として使えます。
この変換は単射であり、元の文字列が異なれば結果の文字列も異なったものになります。
@c COMMON

@c EN
On the other hand, @code{cgen-safe-name-friendly} converts
the input string into more readable C identifier.  @code{->} becomes
@code{_TO} (e.g. @code{char->integer} becomes @code{char_TOinteger}),
other @code{-} and @code{_} become @code{_},
@code{?} becomes @code{P} (e.g. @code{char?} becomes @code{charP}),
@code{!} becomes @code{X} (e.g. @code{set!} becomes @code{setX}),
@code{<} and @code{>} become @code{_LT} and @code{_GT} respectively.
Other special characters except @code{_} are converted to @code{_XX}
as in @code{cgen-safe-name}.  The mapping is not injective; e.g.
both @code{read-line} and @code{read_line} map to @code{read_line}.
Use this only when you think some human needs to read the generated
C code (which is not recommended, by the way.)
@c JP
一方、@code{cgen-safe-name-friendly}はちょっと異なり、
文字列をより読みやすいCの識別子の名前にします。
@code{->}は@code{_TO}に (例: @code{char->integer}は@code{char_TOinteger}に)、
他の@code{-}および@code{_}は@code{_}へとマップされます。
@code{?}は@code{P} (例: @code{char?}は@code{charP}に)、
@code{!}は@code{X} (例: @code{set!}は@code{setX}に),
@code{<}と@code{>}はそれぞれ@code{_LT}と@code{_GT}になります。
以上の文字を除く特殊な文字は@code{cgen-safe-name}と同様に@code{_XX}になります。
この変換は単射ではありません。@code{read-line}と@code{read_line}は
ともに@code{read_line}になってしまいます。
生成されたCコードを人間に読みやすくしたい場合に限り使ってください
(ただ、生成したCコードを人間が読むことは推奨されません)。
@c COMMON

@c EN
If you want to write out a Scheme string as a C string literal,
you can use @code{cgen-safe-string}.  It escapes control
characters and non-ascii characters.
(NB: It also escapes @code{?}, to avoid accidenal formation of
C trigraphs).
@c JP
Scheme文字列をCの文字列リテラルにしたい場合は@code{cgen-safe-string}が使えます。
これは制御文字と非ASCII文字をエスケープします。
(この変換はまた、@code{?}も変換します。うっかりCのトライグラフを出力してしまわないためです)。
@c COMMON

@c EN
Much simpler is @code{cgen-safe-comment}, which just converts
@code{/*} and @code{*/} into @code{/ *} and @code{* /} (a space
between those two characters), so that it won't terminate the
comment inadvertently.  (Technically, escaping only @code{*/} suffice,
but some simple-minded C parser might be confused by @code{/*} in the
comments).   The conversion isn't injective as well.
@c JP
@code{cgen-safe-comment}はずっとシンプルで、
@code{/*}と@code{*/}をそれぞれ@code{/ *}と@code{* /}にするだけです
(二文字の間に空白を入れます)。これは、Scheme文字列をCコメントの内部に出力する際に
うっかりコメントを終わらせてしまわないようにするためです。
(厳密には、エスケープするのは@code{*/}だけで良いはずですが、
簡易的なCパーザには余分な@code{/*}で混乱してしまうものがあるかもしれないので
@code{/*}もエスケープしています)。
この変換も単射ではありません。
@c COMMON

@example
(cgen-safe-name "char-alphabetic?")
  @result{} "char_2dalphabetic_3f"
(cgen-safe-name-friendly "char-alphabetic?")
  @result{} "char_alphabeticP"
(cgen-safe-string "char-alphabetic?")
  @result{} "\"char-alphabetic\\077\""

(cgen-safe-comment "*/*"
  @result{} "* / *"
@end example
@end defun

@c EN
If you want to conditionalize a fragment by C preprocessor
@code{#ifdef}s, use the following macro:
@c JP
コードの断片をCプリプロセッサの@code{#ifdef}で条件的に含めたい場合は、
次のマクロが使えます。
@c COMMON

@defmac cgen-with-cpp-condition cpp-expr body @dots{}
@c MOD gauche.cgen
@c EN
Code fragments submitted in @var{body} @dots{} are protected
by @code{#if @var{cpp-expr}} and @code{#endif}.
@c JP
@var{body} @dots{}中で提出されたコード片が
@code{#if @var{cpp-expr}}と@code{#endif}に囲まれて出力されます。
@c COMMON

@c EN
If @var{cpp-expr} is a string, it is emitted literally:
@c JP
@var{cpp-expr}が文字列の場合は、それが条件式としてそのまま出力されます。
@c COMMON

@example
(cgen-with-cpp-condition "defined(FOO)"
  (cgen-init "foo();"))

;; will generate:
#if defined(FOO)
foo();
#endif /* defined(FOO) */
@end example

@c EN
You can also construct @var{cpp-expr} by S-expr.
@c JP
@var{cpp-expr}にS式を使うこともできます。
@c COMMON

@example
<cpp-expr> : <string>
           | (defined <cpp-expr>)
           | (not <cpp-expr>)
           | (<n-ary-op> <cpp-expr> <cpp-expr> ...)
           | (<binary-op> <cpp-expr> <cpp-expr>)

<n-ary-op> : and | or | + | * | - | /

<binary-op> : > | >= | == | < | <= | !=
            | logand | logior | lognot | >> | <<
@end example

@c EN
Example:
@c JP
例:
@c COMMON

@example
(cgen-with-cpp-condition '(and (defined FOO)
                               (defined BAR))
  (cgen-init "foo();"))

;; will generate:
#if defined(FOO)&&defined(BAR)
foo();
#endif /* defined(FOO)&&defined(BAR) */
@end example

@c EN
You can nest @code{cgen-with-cpp-condition}.
@c JP
@code{cgen-with-cpp-condition}はネストすることもできます。
@c COMMON
@end defmac

@c EN
@subsubheading Submitting code fragments for more than one parts
@c JP
@subsubheading 二つ以上のパートにコード片を出力する
@c COMMON

@c EN
When you try to abstract code generation process,
calling individual procedures for each parts (e.g. @code{cgen-body}
or @code{cgen-init}) becomes tedious, since such higher-level
constructs are likely to require generating code fragments
to various parts.  Instead, you can create a customized class
that handles submission of fragments to appropriate parts.
@c JP
コードの生成を抽象化してゆくと、ひとつの高レベルの構造が
複数のパートにコードを出力しなければならないことがよくあります。
その度に@code{cgen-body}や@code{cgen-init}を個別に呼ぶのは不便です。
そのかわりに、カスタマイズされたクラスを定義して、適切なパートへの
コード出力を処理させることができます。
@c COMMON

@deftp {Class} <cgen-node>
@clindex cgen-node
@c MOD gauche.cgen
@c EN
A base class to represent a set of code fragments.

The state of C preprocessor condition (set by @code{with-cgen-cpp-condition})
is captured when an instance of the subclass of this class is
created, so generating appropriate @code{#if}s and @code{#endif}s are
automatically handled.
@c JP
関連するコード断片の集まりを表すベースクラスです。

このクラスのサブクラスのインスタンスが作られた時点で、
@code{with-cgen-cpp-condition}で指定されているCプリプロセッサの条件が補足され、
コード生成時に必要な@code{#if}や@code{#endif}が出力されます。
@c COMMON
@end deftp

@c EN
You subclass @code{<cgen-node>}, then define method(s) to
one or more of the following generic functions:
@c JP
@code{<cgen-node>}のサブクラスを定義して、それに対して以下のメソッドのうち一つ以上を
定義してください。
@c COMMON

@deffn {Generic Function} cgen-emit-xtrn cgen-node
@deffnx {Generic Function} cgen-emit-decl cgen-node
@deffnx {Generic Function} cgen-emit-body cgen-node
@deffnx {Generic Function} cgen-emit-init cgen-node
@c MOD gauche.cgen
@c EN
These generic functions are called during writing out
the C source within @code{cgen-emit-c} and @code{cgen-emit-h}.
Inside these methods, anything written out to the
current output port goes into the output file.
@c JP
@code{cgen-emit-c}や@code{cgen-emit-h}がCコードを書き出す際に、
これらのジェネリックファンクションが呼ばれます。
これらのメソッド内でcurrent output portに書き出されたものが、
出力ファイルへと書き込まれます。
@c COMMON

@c EN
While generating @code{.h} file by @code{cgen-emit-h},
@code{cgen-emit-xtrn} method for all submitted nodes are
called in order of submission.
@c JP
@code{cgen-emit-h}によって@code{.h}ファイルが生成されている最中に、
登録されたノードの@code{cgen-emit-xtrn}メソッドが、登録された順に呼ばれます。
@c COMMON

@c EN
While generating @code{.c} file by @code{cgen-emit-c},
@code{cgen-emit-decl} method for all submitted nodes are
called first, then @code{cgen-emit-body} method, then
@code{cgen-emit-init} method.
@c JP
@code{cgen-emit-c}によって@code{.c}ファイルが生成されている最中に、
登録されたノードに対し、
まず@code{cgen-emit-decl}メソッドがまず登録された順に呼ばれ、
次に@code{cgen-emit-body}メソッドが同じ順で呼ばれ、
最後に@code{cgen-emit-init}メソッドが同じ順で呼ばれます。
@c COMMON

@c EN
If you don't specialize any one of these method, it doesn't
generate code in that part.
@c JP
どれかのメソッドを特殊化していなければ、該当するパートのコードは生成されません。
@c COMMON
@end deffn

@c EN
Once you define your subclass and create an instance,
you can submit it to the current cgen unit by this procedure:
@c JP
サブクラスを定義しインスタンスを作った後で、次の手続きにより
現在のcgen unitに対してノードを登録できます。
@c COMMON

@defun cgen-add! cgen-node
@c MOD gauche.cgen
@c EN
Submit @var{cgen-node} to the current cgen unit.
If the current unit is not set, @var{cgen-node} is simply ignored.
@c JP
@var{cgen-node}を現在のcgen unitに登録します。
現在のunitがセットされていなければ、@var{cgen-node}は単に無視されます。
@c COMMON
@end defun

@c EN
In fact, the procedures @code{cgen-extern}, @code{cgen-decl},
@code{cgen-body} and @code{cgen-init} are just a convenience
wrapper to create an internal subclass specialized to generate
code fragment only to the designated part.
@c JP
実のところ、手続き@code{cgen-extern}、@code{cgen-decl}、
@code{cgen-body}、@code{cgen-init}はいずれも、
該当するパートに出力されるメソッドだけを定義した@code{<cgen-node>}のサブクラスを
内部的に使っています。
@c COMMON


@node Generating Scheme literals, Conversions between Scheme and C, Generating C source files, Generating C code
@subsection Generating Scheme literals
@c NODE Schemeリテラルを生成する

@c EN
Sometimes you want to refer to a Scheme constant value in C code.
It is trivial if the value is a simple thing like Scheme boolean
(@code{SCM_TRUE}, @code{SCM_FALSE}), characters (@code{SCM_MAKE_CHAR(code)}),
small integers (@code{SCM_MAKE_INT(value)}), etc.  You can directly
write it in C code.  However, once you step outside of these simple
values, it gets tedious quickly, involving static data declarations
and/or runtime initialization code.
@c JP
Schemeの値を定数としてCコードに埋め込みたい場合がしばしばあります。
それが単純な値、例えばSchemeの真偽値(@code{SCM_TRUE}/@code{SCM_FALSE})、
文字(@code{SCM_MAKE_CHAR(code)})、小さい整数(@code{SCM_MAKE_INT(value)})、
等であれば、直接Cコードに書き込めます。
しかし、ひとたび単純な値の範囲を離れると、
こっちでstaticデータ宣言をしてこっちでランタイムに初期化して…といった具合に
急速に面倒になります。
@c COMMON

@c EN
For example, to get a Scheme value of a list of symbols @code{(a b c)},
you have to (1) create @code{ScmString}s for the names of the symbols,
(2) pass them to @code{Scm_Intern} to get Scheme symbols, then
(3) call @code{Scm_Cons}es (or a convenience macro @code{SCM_LIST3}) to
build a list.
@c JP
例えば、シンボルのリスト@code{(a b c)}をCに埋め込みたいとしたら、次の手順を
踏む必要があります。
(1) それぞれのシンボルの名前を@code{ScmString}として作る、
(2) それを@code{ScmIntern}に渡してSchemeシンボルを作る、
(3) @code{ScmCons} (あるいは便利なマクロ@code{SCM_LIST3}) でリストを作る。
@c COMMON

@c EN
With @code{gauche.cgen}, those code can be generated automatically.
@c JP
@code{gauche.cgen}を使うと、これらのコードを自動的に生成できます。
@c COMMON

@c EN
NOTE: If you use @code{cgen-literal}, make sure you call
@code{(cgen-decl "#include <gauche.h>")} to include @file{gauche.h}
before the first call of @code{cgen-literal}, which may insert
declarations that needs @file{gauche.h}.
@c JP
註: @code{cgen-literal}を使う場合、最初にそれを呼ぶ前に
@code{(cgen-decl "#include <gauche.h>")}
を呼ぶようにしてください。@code{cgen-literal}が生成するコードは
@file{gauche.h}内にある宣言を必要とします。
@c COMMON

@defun cgen-literal obj :optional comment
@c MOD gauche.cgen
@c EN
Returns an @code{<cgen-literal>} object for a Scheme object @var{obj},
and submit necessary declarations and initialization code to the
current cgen unit.
@c JP
Schemeオブジェクト@var{obj}を表す@code{<cgen-literal>}オブジェクトを返します。
また、必要な宣言や初期化コードが現在のcgenユニットに登録されます。
@c COMMON

@c EN
The detail of the @code{<cgen-literal>} object isn't for public use,
but one thing you can do is to pass it to @code{cgen-cexpr}
to obtain a C code fragment that refers to the Scheme value at runtime.
See the example in @code{cgen-expr} entry below.
@c JP
@code{<cgen-literal>}オブジェクトの詳細は公開していませんが、
@code{cgen-cexpr}にそれを渡すことで、Scheme値を実行時にCから参照するための
Cコード断片を得ることができます。下の@code{cgen-cexpr}のエントリにある
例を参照してください。
@c COMMON

@c EN
The optional @var{comment} will be attached to the created
@code{<cgen-literal>} objet, which may be included in the output
C code inside a comment.
How to use @var{comment} is up to individual cgen-literal
subclass.  The argument must be a string.
@c JP
省略可能な@var{comment}引数は、作られた@code{<cgen-literal>}オブジェクトに
付加され、生成されたCコードのコメント内に使われる可能性があります。
実際に@var{comment}をどう使うかはcgen-literalの個々のサブクラスに依存します。
この引数は文字列でなければなりません。
@c COMMON

@c EN
When a created literal isn't wrapped by C preprocessor conditionals
and doesn't have a comment, it is registered in the internal hashtable
per unit, and the same (in @code{equal?} sense) literals share a common
instance.  For example, if you call @code{(cgen-literal '(a b c))} multiple
times, there will be only one literal object created at runtime
and all of its use site references that one object.  Furthermore,
if there's a literal @code{(d a b c)}, the cdr of its literal also
refers to the literal @code{(a b c)}.
@c JP
リテラルにCプリプロセッサコンディションやコメントが付加されていない場合、
作られたリテラルはユニットごとのハッシュテーブルに登録され、
同じ(@code{equal?}な)リテラルは共有されます。
例えば@code{(cgen-literal '(a b c))}を複数回呼んだとすると、
リテラルのインスタンスは一つだけ作られ、リテラルを使う場面は全て
その同じリテラルを参照します。
さらに@code{(d a b c)}のリテラルを作ると、作られたリテラルのcdrは
さきほどの@code{(a b c)}のリテラルを参照します。
@c COMMON
@end defun

@deffn {Generic Function} cgen-cexpr cgen-literal
@c MOD gauche.cgen
@c EN
Returns a C code expression fragment of type @code{ScmObj},
which represents the Scheme literal value.
@c JP
@var{cgen-literal}が表すSchemeリテラル値を得るCコード片を返します。
Cでの型は@code{ScmObj}になります。
@c COMMON

@c EN
If the Scheme object is a immediate one such as boolean or fixnum,
the C code is a immediate code to return the value, e.g.
@code{SCM_FALSE} or @code{SCM_MAKE_INT(1234)}.  If the Scheme object
requires allocation, @code{cgen-literal} allocates memory and
initializes it, and @code{cgen-cexpr} returns a pointer to that object.
@c JP
Schemeオブジェクトが真偽値やfixnumのような単純な即値オブジェクトの場合は、
@code{SCM_FALSE}や@code{SCM_MAKE_INT(1234)}といったその値を生成する式が
返されます。Schemeオブジェクトがメモリ上に置かれなければならない場合は、
@code{cgen-literal}は必要なメモリアロケーションと初期化のコードを生成し、
@code{cgen-cexpr}はそのオブジェクトへのポインタを返す式を返します。
@c COMMON

@c EN
The following example creates a C function @code{printabc} that prints
the literal value @code{(a b c)}, created by @code{cgen-literal}.
@c JP
次の例では、@code{cgen-literal}で作られたリテラル値@code{(a b c)}を
表示するC関数@code{printabc}を生成しています。
@c COMMON

@example
(define *unit* (make <cgen-unit> :name "foo"))
(parameterize ((cgen-current-unit *unit*))
  (let1 lit (cgen-literal '(a b c))
    (cgen-body
     (format "void printabc() @{ Scm_Printf(SCM_CUROUT, \"%S\", ~a); @}"
             (cgen-c-name lit)))))
(cgen-emit-c *unit*)
@end example

@c EN
If you examine the generated file @file{foo.c}, you'll get a
general idea of how it is handled.
@c JP
作られた@file{foo.c}を見ると、どのようにリテラル値が扱われているかわかるでしょう。
@c COMMON
@end deffn

@c EN
One advantage of @code{cgen-literal} is that it tries to share
the same literal whenever possible.  If you call
@code{(cgen-literal '(a b c))} twice in the same cgen unit,
you'll get one instance of cgen-literal.  If you call
@code{(cgen-literal '(b c))} then, it will share the tail
of the original list @code{(a b c)}.  So you can just use
@code{cgen-literal} whenever you need to have Scheme literal
values, without worrying about generating excessive amount of
duplicated code.
@c JP
@code{cgen-literal}を使うひとつのメリットは、共通のリテラルが共有されることです。
ひとつのunitの中で@code{(cgen-literal '(a b c))}を2度呼ぶと、
同じ実体が参照されます。さらに@code{(cgen-literal '(b c))}を呼ぶと、
そのリテラルは@code{(a b c)}のリテラルの末尾部分を共有します。
従って、リテラルが重複することを心配せずに、必要になった時に@code{cgen-literal}を
呼ぶことができます。
@c COMMON

@c EN
(Note that the literals registered with @code{cgen-literal} must
be treated as immutable, just as in the Scheme world.)
@c JP
(@code{cgen-literal}で登録されたリテラルは変更不可なものとして扱ってください。
Scheme界でリテラルが変更不可なのと同じです)
@c COMMON

@c EN
Certain Scheme objects cannot be generated as a literal; for example,
an opened port can't, since it carries lots of runtime information.
@c JP
Schemeオブジェクトの中にはリテラルにできないものもあります。
例えばオープンされているポートは、実行時特有の情報を含むためリテラルにできません。
@c COMMON

@c EN
(There's a machinery to allow programmers to extend the @code{cgen-literal}
behavior for new types.  The API isn't fixed yet, though.)
@c JP
(プログラマが独自の型のために@code{cgen-literal}を拡張できる仕組みもありますが、
APIがまだ固まっていません。)
@c COMMON

@node Conversions between Scheme and C, C in S expression, Generating Scheme literals, Generating C code
@subsection Conversions between Scheme and C
@c NODE SchemeとCの間の変換

@c EN
In the C world, Scheme objects are uniformly represented
as an opaque tagged pointer @code{ScmObj}.  In order to access
the actual objects, you need to check its runtime type information
and to retrive the actual C type out of it.
@c JP
Cの世界では、Schemeオブジェクトは不透明なタグつきポインタ@code{ScmObj}として
統一的に扱われます。オブジェクトの実体にアクセスするには、
実行時型情報を調べて、適切なCの型を取り出す必要があります。
@c COMMON

@c EN
@emph{Stub types} are the objects that bridge Scheme runtime types
and C types.  Since mappings between Scheme types and C types are
not one-to-one, there are more stub types than either types;
for example, Scheme @code{<integer>} type may be bridged to C @code{int}
type by the stub type @code{<int>}, but it may also be bridged to
C @code{short} type by the stub type @code{<short>}.
@c JP
@emph{スタブタイプ}はSchemeの型とCの型の橋渡しをするオブジェクトです。
Schemeの型とCの型の対応は1対1ではないので、どちらの型よりも多いスタブタイプがあります。
例えばSchemeの@code{<integer>}型は、スタブタイプ@code{<int>}によってCの@code{int}型
にマップされるかもしれませんし、スタブタイプ@code{<short>}によってCの@code{short}型に
マップされるかもしれません。
@c COMMON

@c EN
Do not confuse stub types and Gauche's runtime types---stub types
are meta information associated to runtime types.  You can look up
a stub type by its name by @code{cgen-type-from-name}.
The session below shows the difference of the runtime types and
stub types:
@c JP
スタブタイプとGaucheの実行時型を混同しないようにしてください。
スタブタイプは、実行時の型に結びつけられたメタ情報と言えます。
スタブタイプの名前がわかると、@code{cgen-type-from-name}によって
スタブタイプの実体を得ることができます。
次のセッションは実行時型とスタブタイプの違いを見せるものです。
@c COMMON

@example
gosh> <int>
#<native-type <int>>
gosh> ,d
#<native-type <int>> is an instance of class <native-type>
slots:
  name      : <int>
  super     : #<class <integer>>
  c-type-name: "int"
  size      : 4
  alignment : 4

gosh> (cgen-type-from-name '<int>)
#<cgen-type <int>>
gosh> ,d
#<cgen-type <int>> is an instance of class <cgen-type>
slots:
  name      : <int>
  scheme-type: #<native-type <int>>
  c-type    : "int"
  description: "int"
  cclass    : #f

gosh> <integer>
#<class <integer>>
gosh> ,d
#<class <integer>> is an instance of class <integer-meta>
slots:
  name      : <integer>
  cpl       : (#<class <integer>> #<class <rational>> #<class <real>> #<cl
  direct-supers: (#<class <rational>>)
  accessors : ()
  slots     : ()
  direct-slots: ()
  num-instance-slots: 0
  direct-subclasses: ()
  direct-methods: ()
  initargs  : ()
  defined-modules: (#<module gauche>)
  redefined : #f
  category  : builtin
  core-size : 0

gosh> (cgen-type-from-name '<integer>)
#<cgen-type <integer>>
gosh> ,d
#<cgen-type <integer>> is an instance of class <cgen-type>
slots:
  name      : <integer>
  scheme-type: #<class <integer>>
  c-type    : "ScmObj"
  description: "exact integer"
  cclass    : #f
@end example

Each stub type ``knows'' how to generate C expressions of
@emph{C-predicate}, a @emph{boxer} and an @emph{unboxer}.
A C-predicate takes @code{ScmObj} object and returns C boolean
value that if the given object has a valid type and range for the
stub type.
A boxer takes C object and converts it to a Scheme object; it
usually involves wrapping or @emph{boxing} the C value in a
tagged pointer or object, hence the name.
An unboxer does the opposite: takes a Scheme object and convert
it to a C value.  The Scheme object must be checked by the C-predicate
before being passed to the unboxer.

We have a few categories of stub types.

@itemize @bullet
@item
Stub types corresponds to native types (@pxref{Native types}).
@item
Stub types corresponds to C-class types.  These are Scheme object whose structure is defined in C.
They can be treated as ScmObj or can be casted to the specific C type;
e.g. @code{<symbol>} can be casted to @code{ScmSymbol*}.
Its unboxer is @code{ScmObj -> C-TYPE*},
and boxer is @code{C-TYPE* -> ScmObj}.
@item
Pass-through types.  These are Scheme object that are also handled
as ScmObj in C-level.  Stub types only typecheck, and its boxer and
unboxer are just identity.  It can be either purely-Scheme-defined
objects, or an object that can take multiple representations
(e.g. @code{<integer>} can be a fixnum or @code{ScmBignum*},
so the stub generator passes through it,
and the C routine handles the internals.)
@item
Maybe stub types.  It is noted by a question mark suffix.
In stub context, we only concern maybe type
that can be unboxed into a C pointer type.  In addition to the objects
of the origial type, it maps Scheme's @code{#f} to C's @code{NULL}
and vice versa.  For example, @code{<port>?} maps Scheme's @code{<port>}
instance to C's @code{ScmPort*},
@emph{and} Scheme's @code{#f} to C's @code{NULL}.
@end itemize

@deftp {Class} <cgen-type>
@clindex cgen-type
@c MOD gauche.cgen
An instance of this class represents a stub type.
It can be looked up by name such as @code{<const-cstring>} by
@code{cgen-type-from-name}.
@end deftp

@defun cgen-type-from-name name
@c MOD gauche.cgen
Returns an instance of @code{<cgen-type>} that has @var{name}.
If the name is unknown, @code{#f} is returned.
@end defun

@defun cgen-box-expr cgen-type c-expr
@defunx cgen-unbox-expr cgen-type c-expr
@defunx cgen-pred-expr cgen-type c-expr
@c MOD gauche.cgen
@var{c-expr} is a string denotes a C expression.
Returns a string of C expression that boxes, unboxes, or
typechecks the @var{c-expr} according to the @var{cgen-type}.

@example
;; suppose foo() returns char*
(cgen-box-expr
 (cgen-type-from-name '<const-cstring>)
 "foo()")
 @result{} "SCM_MAKE_STR_COPYING(foo())"
@end example
@end defun


@node C in S expression, Stub generation, Conversions between Scheme and C, Generating C code
@subsection CiSE - C in S expression
@c NODE S式で書くC, CiSE - S式で書くC

Some low-level routines in Gauche are implemented in C, but they're
written in S-expression.  We call it ``C in S expression'', or @emph{CiSE}.

The advantage of using S-expression is its readability, obviously.
Another advantage is that it allows us to write macros as
S-expr to S-expr translation, just like the legacy Scheme macros.
That's a powerful feature---effectively you can extend C language
to suit your needs.

The @code{gauche.cgen.cise} module provides a set of tools to convert
CiSE code into C code to be passed to the C compiler.  It also has
some support to overcome C quirks, such as preparing forward
declarations.

Currently, we don't do rigorous check for CiSE; you can pass a
CiSE expression to the translator that yields invalid C code, which will
cause the C compiler
to emit errors.  The translator inserts line directives by default so the
C compiler error message points to the location of original (CiSE) source
instead of generated code; however, sometimes you need to look at
the generated code to figure out what went wrong.  We hope this
will be improved in future.

In Gauche source code, CiSE is extensively used in precompiled Scheme
files and recognized by the precompiler.  However,
@code{gauche.cgen.cise} is an independent module only relies
on @code{gauche.cgen} basic features, so you can plug it
to your own C code generating programs.

@menu
* CiSE overview::
* CiSE syntax::
* CiSE procedures::
@end menu

@node CiSE overview, CiSE syntax, C in S expression, C in S expression
@subsubsection CiSE overview

Before diving into the details, it's easier to grasp
some basic concepts.

A @emph{CiSE fragment} is an S-expression that follows
CiSE syntax (@pxref{CiSE syntax}).  A CiSE fragment can be
translated to a C code fragment by @code{cise-render}.
Note that some translation may not be local, e.g. it may
want to emit forward declarations before other C code fragments.
So, the full translation requires buffering---you process all
the CiSE fragments and save output, emit forward declarations,
then emit the saved C code fragments.  We have a wrapper procedure,
@code{cise-translate}, to take care of it, but for your purpose
you may want to roll your own wrapper.

A @emph{CiSE macro} is a Scheme code that translates a CiSE
fragment to another CiSE fragment.  There are number of
predefined CiSE macros.  You can add your own CiSE macros by
utilities such as
@code{define-cise-stmt} and @code{define-cise-expr}.

A @emph{CiSE ambient} is a bundle of information that affects
fragment translation.  It contains CiSE macro definitions,
and also it keeps track of forward declarations.

If you're not sure how a cise fragment corresponds to C code,
you can interactively try it:

@example
gosh> (cise-render-to-string
        '(.struct foo (i::int c::(const char*)))))
"struct foo @{ int i; const char* c; @} "
gosh> (cise-render-to-string
        '(define-cfn foo (x::int) (return (+ x 3)))
        'toplevel))
" ScmObj foo(int x)@{@{return ((x)+(3));@}@}"
@end example

(The second argument of @code{cise-render-to-string} specifies the
context; @pxref{CiSE procedures}, for the details.)

@node CiSE syntax, CiSE procedures, CiSE overview, C in S expression
@subsubsection CiSE syntax

In this section, we list basic CiSE syntax.  They are just data from
the viewpoint of Gauche---so you can build and manipulate them like
any S-expression (quasiquote comes pretty handy).

@subsubheading CiSE types

C types can be written either as a symbol (e.g. @code{int}) or
a list (e.g. @code{(const char *)}.  When used in definition, it is
preceded by @code{::}.  The following example shows types
are used in local variable definitions:

@example
(let* ([a :: int 0]
       [b :: (const char *) "abc"])
  ...)
@end example

For the convenience and readability, you can write the variable name,
separating double-colon and type name concatenated.  You can also concatenate
point suffixes (@code{char*} instead of @code{char *} in the following example):

@example
(let* ([a::int 0]
       [b::(const char*) "abc"])
  ...)
@end example

CiSE translater first breaks up these concatenated forms, then
deal with types.

At this moment, CiSE does @emph{not} check if type is valid C type.
It just pass along whatever given.

There are a few special type notations for more complex types.
These can appear in middle of the type; for example, you can write
@code{(const .struct x (a::int b::double) *)} to produce
@code{const struct x @{int a; double b;@} *}.

@deffn {CiSE Type} .array elt-type (dim @dots{})
Expands to C array type, whose element type is of @var{elt-type}
and dimensions are @var{dim @dots{}}.

@example
(cise-render-to-string '(.array char (3)))
  @result{} "char [3]"

(cise-render-to-string '(.array int (2 5)))
  @result{} "int [2][5]"
@end example

The last element of @var{dim} can be @code{*}, corresponds to
the C type without specifying the array size:

@example
(cise-render-to-string '(.array char (*)))
  @result{} "char [3]"

(cise-render-to-string '(.array int (10 *)))
  @result{} "int [10][]"
@end example

Here's an example of global C variable definition of array type:

@example
(cise-render-to-string '(define-cvar params ::(.array int (PARAM_SIZE)))
                       'toplevel)
  @result{} " int params[PARAM_SIZE];"
@end example
@end deffn

@deffn {CiSE Type} .struct [tag] [(field-spec @dots{})]
@deffnx {CiSE Type} .union [tag] [(field-spec @dots{})]
@end deffn

@deffn {CiSE Type} .function (arg-spec @dots{}) ret-type
@end deffn


@subsubheading CiSE statements

@deffn {CiSE Statement} begin stmt @dots{}
Code grouping with @code{@{} and @code{@}}
@end deffn

@deffn {CiSE Statement} let* (binding @dots{}) stmt @dots{}
Define and optionally assign initial values to local variables.
The @var{binding} is a form of either one of the following type:

@table @code
@item (@var{name} [:: @var{type}] [@var{init-expr}])
Define a C variable @var{name} of type @var{type}.
@var{type} should be a CiSE type.
If @var{type} is omitted, the default type is @code{ScmObj}.
Optional @var{init-expr} is a CiSE expression to compute the initial
value of @var{name}.
Note that array initialization is not supported yet.
@item (_ @var{cise-form})
This is to allow arbitrary CiSE statement or expression @var{cise-form}
between local variable definitions.  See the example below.
@end table

The @code{(_ cise-form)} binding is useful when you want to
do some check between other bindings, without having nested
@code{let*}:

@example
(let* ([len::ScmSmallInt (Scm_Length lis)]
       [_ (when (< len 1) (Scm_Error "Lis is too short: %S" lis))]
       [first (SCM_CAR lis)])
  ...)
@end example
@end deffn

@deffn {CiSE Statement} if test-expr then-stmt [else-stmt]
@deffnx {CiSE Statement} when test-expr stmt @dots{}
@deffnx {CiSE Statement} unless test-expr stmt @dots{}
@deffnx {CiSE Statement} cond (cond1 stmt1 @dots{}) @dots{} [ (@code{else} else-stmt @dots{}) ]
Conditional statements.
@end deffn

@deffn {CiSE Statement} case expr ((val1 @dots{}) stmt1 @dots{}) @dots{} [ (@code{else} else-stmt @dots{}) ]
@deffnx {CiSE Statement} case/fallthrough expr ((val1 @dots{}) stmt1 @dots{}) @dots{} [ (@code{else} else-stmt @dots{}) ]
Switch-case statement. @code{case} does not fall through between 'case'
blocks while @code{case/fallthrough} does.
@end deffn

@deffn {CiSE Statement} for (start-expr test-expr update-expr) stmt @dots{}
@deffnx {CiSE Statement} for () stmt @dots{}
@deffnx {CiSE Statement} loop stmt @dots{}
@deffnx {CiSE Statement} while test-expr body @dots{}
Loop statements.
@end deffn

@deffn {CiSE Statement} for-each (@code{lambda} (var) stmt @dots{}) expr
@deffnx {CiSE Statement} dolist [var expr] stmt @dots{}
@var{expr} must yield a list. Traverse the list, binding each element to @var{var}
and executing @var{stmt} @dots{}. The lambda form is a fake; you don't
really create a closure.
@end deffn

@deffn {CiSE Statement} pair-for-each (@code{lambda} (var) stmt @dots{}) expr
Like @code{for-each}, but @var{var} is bound to each 'spine' cell instead of each
element of the list.
@end deffn

@deffn {CiSE Statement} dopairs [var expr] stmt @dots{}
@end deffn

@deffn {CiSE Statement} dotimes (var expr) stmt @dots{}
@var{expr} must yield an integer, @var{n}.  Repeat @var{stmt} @dots{} by binding @var{var} from 0
to (@var{n}-1).
@end deffn

@deffn {CiSE Statement} return [expr]
@deffnx {CiSE Statement} break
@deffnx {CiSE Statement} continue
Return, break and continue statements.
@end deffn

@deffn {CiSE Statement} label name
@deffnx {CiSE Statement} goto name
Label and goto statements. We always add a null statement after the
label so that we can place @code{(label @var{name})} at the end of a compound
statement.
@end deffn

@deffn {CiSE Statement} .if @var{expr} @var{stmt} [@var{stmt}]
@deffnx {CiSE Statement} .when @var{expr} @var{stmt} @dots{}
@deffnx {CiSE Statement} .unless @var{expr} @var{stmt} @dots{}
@deffnx {CiSE Statement} .cond @var{clause} @dots{}
@deffnx {CiSE Statement} .define @var{name}[(@var{arg} @dots{})] [@var{expr}]
@deffnx {CiSE Statement} .undef @var{name}
@deffnx {CiSE Statement} .include @var{path}
Preprocessor directives.

@var{expr} could be
a string, a symbol, a number or one of the following forms:
@itemize
@item
@code{(defined @var{c})}
@item
@code{(not @var{c})}
@item
@code{(and @var{c})}
@item
@code{(or @var{c})}
@item
@code{(@var{op} @var{c} @dots{})} where @var{op} is either @code{+} or
@code{*}.
@item
@code{(@var{op} @var{c} @var{c} @dots{})} where @var{op} is either
@code{-} or @code{/}.
@item
@code{(@var{op} @var{c} @var{c})} where @var{op} is either @code{>},
@code{>=}, @code{==}, @code{<}, @code{<=}, @code{!=}, @code{logand},
@code{logior}, @code{lognot}, @code{<<} or @code{>>}.
@end itemize

Note that defining a macro function without value
@example
#define foo(abc)
@end example
is not supported because it's ambiguous with
@example
#define foo abc()
@end example
when written in CiSE syntax. @code{(.define foo (abc))} always
generates the latter.

@code{.include} could take a symbol. This is used for including system
header files, e.g. @code{(.include <stdint.h>)}.
@end deffn

@deffn {CiSE Statement} define-cfn name (arg [@code{::} type] @dots{}) [ret-type [qualifier @dots{}]] stmt @dots{}
Defines a C function.

If @var{type} or @var{ret-type} is omitted, the default type is
@code{ScmObj}.

Supported qualifiers are @code{:static} and @code{:inline}, corresponding
to C's @code{static} and @code{inline} keywords.  If @code{:static} is
specified, forward declaration is automatically generated.
@end deffn

@deffn {CiSE Statement} define-cvar name [@code{::} type] [qualifier @dots{}] [<init-expr>]
Defines a global C variable. Supported qualifier is
@code{:static}. Note that array initialization is not supported yet.
@end deffn

@deffn {CiSE Statement} define-ctype name [@code{::} type]
Defines a new type using @code{typedef}
@end deffn

@deffn {CiSE Statement} declare-cfn name (arg [@code{::} type] @dots{}) [ret-type]
@deffnx {CiSE Statement} declare-cvar name [@code{::} type]
Declares an external C function or variable.
@end deffn


@deffn {CiSE Statement} .static-decls

Produce declarations of static functions before function bodies.

@end deffn

@deffn {CiSE Statement} .raw-c-code body @dots{}

@end deffn

@subsubheading CiSE expressions

@deffn {CiSE Expression} + expr @dots{}
@deffnx {CiSE Expression} - expr @dots{}
@deffnx {CiSE Expression} * expr @dots{}
@deffnx {CiSE Expression} / expr @dots{}
@deffnx {CiSE Expression} % expr1 expr2
Arithmetic operations.
@end deffn

@deffn {CiSE Expression} and expr @dots{}
@deffnx {CiSE Expression} or expr @dots{}
@deffnx {CiSE Expression} not expr
Boolean operations.
@end deffn

@deffn {CiSE Expression} logand expr1 expr2 @dots{}
@deffnx {CiSE Expression} logior expr1 expr2 @dots{}
@deffnx {CiSE Expression} logxor expr1 expr2 @dots{}
@deffnx {CiSE Expression} lognot expr
@deffnx {CiSE Expression} << expr1 expr2
@deffnx {CiSE Expression} >> expr1 expr2
Bitwise operations.
@end deffn

@deffn {CiSE Expression} * expr
@deffnx {CiSE Expression} -> expr1 expr2 @dots{}
@deffnx {CiSE Expression} ref expr1 expr2 @dots{}
@deffnx {CiSE Expression} aref expr1 expr2 @dots{}
@deffnx {CiSE Expression} & expr
Dereference, reference and address operations. @code{ref} is C's
@code{.}. @code{aref} is array reference.
@end deffn

@deffn {CiSE Expression} pre++ expr
@deffnx {CiSE Expression} post++ expr
@deffnx {CiSE Expression} pre-- expr
@deffnx {CiSE Expression} post-- expr
Pre/Post increment or decrement.
@end deffn

@deffn {CiSE Expression} < expr1 expr2
@deffnx {CiSE Expression} <= expr1 expr2
@deffnx {CiSE Expression} > expr1 expr2
@deffnx {CiSE Expression} >= expr1 expr2
@deffnx {CiSE Expression} == expr1 expr2
@deffnx {CiSE Expression} != expr1 expr2
Comparison.
@end deffn

@deffn {CiSE Expression} set! lvalue1 expr1 lvalue2 expr2 @dots{}
@deffnx {CiSE Expression} = lvalue1 expr1 lvalue2 expr2 @dots{}
@deffnx {CiSE Expression} += lvalue expr
@deffnx {CiSE Expression} -= lvalue expr
@deffnx {CiSE Expression} *= lvalue expr
@deffnx {CiSE Expression} /= lvalue expr
@deffnx {CiSE Expression} %= lvalue expr
@deffnx {CiSE Expression} <<= lvalue expr
@deffnx {CiSE Expression} >>= lvalue expr
@deffnx {CiSE Expression} logand= lvalue expr
@deffnx {CiSE Expression} logior= lvalue expr
@deffnx {CiSE Expression} logxor= lvalue expr
Assignment expressions.
@end deffn

@deffn {CiSE Expression} cast type expr
Type casting.
@end deffn

@deffn {CiSE Expression} ?: test-expr then-expr else-expr
Conditional expression.
@end deffn

@deffn {CiSE Expression} .type type
Useful to  place a type name, e.g. an argument of sizeof operator.
@end deffn

@deffn {CiSE Expression} new type
@deffnx {CiSE Expression} new (type expr ...)
@deffnx {CiSE Expression} new type (dim ...)
@deffnx {CiSE Expression} new (type expr ...) (dim ...)
C++ new operator.  The second argument can be just a type name,
or a constructor call.  The optional second argument specifies
array dimensions.

@example
(new MyClass)              @result{} new MyClass;
(new (MyClass a b) (1 2))  @result{} new MyClass(a, b)[1,2];
@end example
@end deffn

@deffn {CiSE Expression} delete expr
@deffnx {CiSE Expression} delete () expr
C++ delete operator.  The second form is to delete an array.

@example
(delete (* foo))  @result{} delete *foo;
(delete () foo)   @result{} delete[] foo;
@end example
@end deffn


@node CiSE procedures,  , CiSE syntax, C in S expression
@subsubsection CiSE procedures


@deffn {Parameter} cise-ambient
@c MOD gauche.cgen
@end deffn

@defun cise-default-ambient
@c MOD gauche.cgen
@end defun

@defun cise-ambient-copy ambient
@c MOD gauche.cgen
@end defun

@defun cise-ambient-decl-strings ambient
@c MOD gauche.cgen
@end defun

@deffn {Parameter} cise-emit-source-line
@c MOD gauche.cgen
@end deffn

@defun cise-render cise-fragment :optional port context
@c MOD gauche.cgen
@end defun

@defun cise-render-to-string cise-fragment :optional context
@c MOD gauche.cgen
@end defun

@defun cise-render-rec cise-fragment stmt/expr env
@c MOD gauche.cgen
@end defun

@defun cise-translate inp outp :key environment
@c MOD gauche.cgen
@end defun


@defun cise-register-macro! name expander :optional ambient
@c MOD gauche.cgen
@end defun

@defun cise-lookup-macro name :optional ambient
@c MOD gauche.cgen
@end defun

@defmac define-cise-stmt name [env] clause @dots{} [:where definition @dots{}]
@defmacx define-cise-expr name [env] clause @dots{} [:where definition @dots{}]
@defmacx define-cise-toplevel name [env] clause @dots{} [:where definition @dots{}]
@c MOD gauche.cgen
@end defmac

@defmac define-cise-macro (name form env) body @dots{}
@defmacx define-cise-macro name name2
@c MOD gauche.cgen
@end defmac

@node Stub generation,  , C in S expression, Generating C code
@subsection Stub generation
@c NODE スタブの生成

@deffn {Stub Form} declare-stub-type NAME C-TYPE [DESC C-PREDICATE UNBOXER BOXER]
Register a new type to be recognized.  This is rather a declaration
than definition; no C code will be generated directly by this form.
@end deffn

@deffn {Stub Form} define-cproc name (args @dots{}) [ret-type] [flag @dots{}] [qualifier @dots{}] stmt @dots{}
Create Scheme procedure.

@var{args} specifies arguments:
@itemize
@item
@code{@var{arg} @dots{} [:rest @var{var}]} :
Each @var{arg} is variable name or @var{var::type}, specifies required
argument. If @code{:rest} is given, list of excessive arguments are
passed to @var{var}.

@item
@code{@var{arg} @dots{} :optional @var{spec} @dots{} [:rest @var{rest-var}]} :
Optional arguments. @var{spec} is @var{var} or (@var{var}
@var{default}). If no @var{default} is given, @var{var} receives
@code{SCM_UNBOUND}---if @var{var} isn't a type of @code{ScmObj} it will
raise an error.

@item
@code{@var{arg} @dots{} :key @var{spec} @dots{} [:allow-other-keys [:rest @var{rest-var}]]} :
Keyword arguments. @var{spec} is @var{var} or (@var{var}
@var{default}).  If no @var{default} is given, @var{var} receives
@code{SCM_UNBOUND}---if @var{var} isn't a type of @code{ScmObj} it will raise
an error.

@item
@code{@var{arg} @dots{} :optarray (@var{var} @var{cnt} @var{max}) [:rest @var{rest-var}]} :
A special syntax to receive optional arguments as a C array.
@var{var} is a C variable of type @code{ScmObj*}. @var{cnt} is a C
variable of type @code{int}, which receives the number of optional
argument in the ScmObj array.  @var{max} specifies the maximum number
of optional arguments that can be passed in the array form.  If more
than @var{max} args are given, a list of excessive arguments are
passed to the @var{rest-var} if it is specified
@end itemize

@var{ret-type} specifies the return type of function. It could be
either @code{:: @var{typespec}} or @code{::@var{typespec}} where
@var{typespec} is a valid stub type, or @code{(@var{type} @dots{})} when
multiple values are returned. When omitted, the procedure is assumed
to return @code{<top>}.

@var{flag} is a keyword to modify some aspects of the procedure.
Supported flags are as follows:

@itemize
@item
@code{:fast-flonum} - indicates that the procedure accepts flonum
arguments and it won't retain the reference to them. The VM can pass
flonums on VM registers to the procedure with this flag. (This
improves floating-point number handling, but it's behavior is highly
VM-specific; ordinary stub writers shouldn't need to care about this
flag at all.)

@item
@code{:constant} - indicates that this procedure returns a constant
value if all args are compile-time constants. The compiler may replace
the call to this proc with the value, if it determines all arguments
are known at the compile time. The resulting value should be
serializable to the precompiled file.

NB: Since this procedure may be called at compile time, a subr that
may return a different value for batch/cross compilation shouldn't
have this flag.
@end itemize

@var{qualifier} is a list to adds auxiliary information to the
procedure. Currently the following qualifiers are officially
supported.

@itemize
@item
@code{(setter @var{setter-name})} : specify setter. @var{setter-name} should
be a cproc name defined in the same stub file

@item
@code{(setter (@var{args} @dots{}) @var{body} @dots{})} : specify setter
anonymously.

@item
@code{(catch (@var{decl} @var{c-stmt} @dots{}) @dots{})} : when writing a stub
for C++ function that may throw an exception, use this spec to ensure
the exception will be caught and converted to Gauche error condition.

@item
@code{(inliner @var{insn-name})} : only used in Gauche core procedures that
can be inlined into an VM instruction.
@end itemize

@var{stmt} is a cise expression.  Inside the expression, a cise macro
@code{(result expr @dots{})} can be used to assign the value(s) to
return from the cproc. As a special case, if @var{stmt} is a single
symbol, it names a C function to be called with the same argument (mod
unboxing) as the cproc.
@end deffn

@deffn {Stub Form} define-cgeneric @var{name} @var{c-name} @var{property-clause} @dots{}
Defines generic function. @var{c-name} specifies a C variable name
that keeps the generic function structure. One or more of the
following clauses can appear in @var{property-clause} @dots{}:

@itemize
@item
@code{(extern)} : makes @var{c-name} visible from other file (i.e. do
not define the structure as @code{static}).

@item
@code{(fallback "fallback")} : specifies the fallback function.

@item
@code{(setter . @var{setter-spec})} : specifies the setter.
@end itemize
@end deffn

@deffn {Stub Form} define-cmethod @var{name} (@var{arg} @dots{}) @var{body} @dots{}
@end deffn

@deffn {Stub Form} define-cclass @var{scheme-name} [@var{qualifier} @dots{}] @var{c-type-name} @var{c-class-name} @var{cpa} (@var{slot-spec} @dots{}) @var{property} @dots{}
Generates C stub for static class definition, slot accessors and
initialization. Corresponding C struct has to be defined elsewhere.

The following qualifiers are supported:
@itemize
@item
@code{:base} generates a base class definition (inheritable from
Scheme code).
@item
@code{:built-in} generates a built-in class definition (not
inheritable from Scheme code). This is the default if neither
@code{:base} nor @code{:built-in} are specified.
@item
@code{:private} - the class declaration and standard macro definitions
are also generated (which needs to be in the separate header file if
you want the C-level structure to be used from other C code. If the
extension is small enough to be contained in one C file, this option
is convenient.)
@end itemize

@var{cpa} lists ancestor classes in precedence order. They need to be
C identifiers of Scheme class @code{Scm_*Class}, for the time being.
@code{Scm_TopClass} is added at the end automatically.

@var{slot-spec} is defined as @code{(@var{slot-name} [@var{qualifier}
@dots{}])} or @code{@var{slot-name}}. The following qualifiers are
supported:

@itemize
@item
@code{:type @var{cgen-type}}
@item
@code{:c-name @var{c-name}} specifies the C field name if the
autogenerated name from @var{slot-name} is not accurate.
@item
@code{:c-spec @var{c-spec}}
@item
@code{:getter @var{proc-spec}}
specifies how to create the slot getter. @var{proc-spec} could be
@itemize
@item
@code{#f} to omit the getter
@item
@code{#t} to generate a default one with type conversion according to
@var{type}
@item
A string is interpreted as the C code to implement the getter
@item
@code{(c @var{c-name})} specifies the C function name that implements
the getter, which is implemented elsewhere.
@end itemize
@item
@code{:setter @var{proc-spec}}
specifies how to create the slot setter. The syntax is the same as
@code{:getter}.
@end itemize

The following @var{property} are supported:

@itemize
@item
@code{(allocator @var{proc-spec})}
@item
@code{(printer @var{proc-spec})}
@item
@code{(comparer @var{proc-spec})}
@item
@code{(direct-supers @var{string} @dots{})}
@end itemize

@end deffn

@deffn {Stub Form} define-cptr @var{scheme-name} [@var{qualifier} @dots{}] @var{c-type} @var{c-name} @var{c-pred} @var{c-boxer} @var{c-unboxer} [(flags @var{flag} @dots{})] [(print @var{print-proc})] [(cleanup @var{cleanup-proc})]
Defines a new foreign pointer class based on
@code{<foreign-pointer>}. It is suitable when the C structure is
mostly passed around using pointers; most typically, when the foreign
library allocates the structure and returns the pointer to the Scheme
world.

@var{scheme-name} is a Scheme variable name. This will be bound to a
newly-created subclass of @code{<foreign-pointer>} to represent this
C-ptr type.

@var{c-type} is the type of the C pointer we wrap.

@var{c-name} is the C variable name (of type @code{ScmClass *}).  In
initialization code, an instance of a class (the same one bound to
@var{scm-name} in the Scheme world) will be stored in this C variable.

@var{c-pred} is a macro name to determine if a @code{ScmObj} is of
this type.
@var{c-boxer} is a macro name to wrap C pointer and return a
@code{ScmObj}
@var{c-unboxer} is a macro name to extract C pointer from a
@code{ScmObj}

The only supported qualifier is @code{:private}, which will generate
@var{c-pred}, @var{c-boxer} and @var{c-unboxer} definitions
automatically. Otherwise those definitions must be provided elsewhere.

The two supported flags are
@itemize
@item
@code{:keep-identity} (which is
@code{SCM_FOREIGN_POINTER_KEEP_IDENTITY} in the C world) keeps a weak
hash table that maps the wrapped C pointer to the wrapping
@code{ScmObj}, so @code{Scm_MakeForeignPointer} (i.e. @var{c-boxer}
when @code{:private} is used) returns eq? object if the same C pointer
is given.

This incurs some overhead, but cleanup procedure can safely free the
foreign object without worrying if there's other ScmObj that's
pointing to the same C pointer.

Do not use this flag if the C pointer is also allocated by
@code{GC_malloc}. The used hash table is only weak for its value, so
the C pointer wouldn't be GCed.
@item
@code{:map-null} (which is @code{SCM_FOREIGN_POINTER_MAP_NULL} in the
C world) makes @code{Scm_MakeForeignPointer} (i.e. @var{c-boxer} when
@code{:private} is used) return @code{SCM_FALSE} when the C pointer is
@code{NULL}.
@end itemize
@end deffn

@deffn {Stub Form} define-symbol @var{scheme-name} [@var{c-name}]
Defines a Scheme symbol. No Scheme binding is created.
When @var{c-name} is given, the named C variable points to the created
@code{ScmSymbol}.
@end deffn

@deffn {Stub Form} define-variable @var{scheme-name} @var{initializer}
Defines a Scheme variable.
@end deffn

@deffn {Stub Form} define-constant @var{scheme-name} @var{initializer}
Defines a Scheme constant.
@end deffn

@deffn {Stub Form} define-enum @var{name}
A @code{define-constant} specialized for enum values. This is useful for
exporting C enums to Scheme.
@end deffn

@deffn {Stub Form} define-enum-conditionally @var{name}
Abbreviation of @code{(if "defined(name)" (define-enum name))}
@end deffn

@deffn {Stub Form} define-cise-stmt @var{name} @var{clause} @dots{}
@deffnx {Stub Form} define-cise-expr @var{name} @var{clause} @dots{}
@deffnx {Stub Form} define-cfn @dots{}
@deffnx {Stub Form} declare-cfn @dots{}
@deffnx {Stub Form} define-cvar @dots{}
@deffnx {Stub Form} declare-cvar @dots{}
@deffnx {Stub Form} define-ctype @dots{}
@deffnx {Stub Form} .define @dots{}
@deffnx {Stub Form} .if @dots{}
@deffnx {Stub Form} .include @dots{}
@deffnx {Stub Form} .undef @dots{}
@deffnx {Stub Form} .unless @dots{}
@deffnx {Stub Form} .when @dots{}
Cise macro definitions (see @ref{C in S expression}).
@end deffn

@deffn {Stub Form} initcode @var{c-code}
Insert @var{c-code} literally in the initialization function
@end deffn

@deffn {Stub Form} declcode @var{stmt} @dots{}
Inserts declaration code. @var{stmt} is usually @code{.include} or
other preprocessor statements but it could also be a string which is
treated as C fragments.
@end deffn

@deffn {Stub Form} begin @var{form} @dots{}
Treat each @var{form} as if they are toplevel stub forms.
@end deffn

@deffn {Stub Form} if @var{test} @var{then-stmt} [@var{else-stmt}]
@deffnx {Stub Form} when @var{test} @var{stmt}
@c DEPRECATED
Please use @code{.if} and @code{.when} instead.
@end deffn

@deffn {Stub Form} include @var{file}
Include and evaluate another stub file.
@end deffn


@c ----------------------------------------------------------------------
@node Character code conversion, Collection framework, Generating C code, Library modules - Gauche extensions
@section @code{gauche.charconv} - Character Code Conversion
@c NODE 文字コード変換, @code{gauche.charconv} - 文字コード変換

@deftp {Module} gauche.charconv
@mdindex gauche.charconv
@c EN
This module defines a set of functions that converts character encoding
schemes (CES) of the given data stream.

This module is implicitly loaded when @code{:encoding} keyword argument
is given to the file stream creating functions
(such as @code{open-input-file} and @code{call-with-output-file}).
@c JP
与えられたデータストリームの文字エンコーディングを変換するための手続き群を提供する
モジュールです。

このモジュールはまた、@code{open-input-file}や
@code{call-with-output-file}等のファイルストリームを作成する手続きに
@code{:encoding}キーワード引数が与えられた場合に暗黙にロードされます。
@c COMMON

@c EN
For the portable programs, you can use @emph{transcoded ports}
defined in SRFI-181 (@pxref{Transcoded ports}).
@c JP
ポータブルなコードには、SRFI-181で定義される@emph{符号変換ポート}を使うこともできます
(@ref{Transcoded ports}参照)。
@c COMMON
@end deftp

@menu
* Supported character encoding schemes::
* Autodetecting the encoding scheme::
* Conversion ports::
@end menu

@node Supported character encoding schemes, Autodetecting the encoding scheme, Character code conversion, Character code conversion
@subsection Supported character encoding schemes
@c NODE サポートされる文字エンコーディング

@c EN
A CES is represented by its name as a string or a symbol.
Case is ignored.  There may be several aliases defined for a single encoding.
@c JP
CESの名前は文字列またはシンボルで指定します。大文字小文字の違いは無視されます。
同じCESにいくつかの別名がついていることがあります。
@c COMMON

@c EN
A CES name "none" is special; it means the string is an octet sequence
and it's up to the application
to interpret the sequence in an appropriate encoding.  So, conversion
to and from CES "none" does nothing.
@c JP
CES名 "none" は特殊で、文字列を単なるバイト列として扱い、そのエンコーディングの解釈は
アプリケーションに任されます。したがって、CES "none" への変換、および "none"
からの変換は「何もしない」変換として扱われます。
@c COMMON

@c EN
Gauche natively supports conversions between
Unicode transfer encodings (UTF-8, UTF-16, UTF-16BE, UTF-16LE,
UTF-32, UTF-32BE, UTF-32LE), Latin-N encodings
(ISO8859-1 to 16), and
typical Japanese character encodings: ISO2022JP, ISO2022JP-3,
EUC-JP (EUC-JISX0213), Shift_JISX0213.
@c JP
Gaucheは自前で、Unicode Transfer Encoding (UTF-8, UTF-16, UTF-16BE, UTF-16LE,
UTF-32, UTF-32BE, UTF-32LE)、Latin-N (ISO8859-1から16)、
そして主要な日本語エンコーディング
(ISO2022JP, ISO2022JP-3, EUC-JP (EUC-JISX0213), Shift_JIS (Shift_JISX0213))、
の間の変換を行います。
@c COMMON

@c EN
Conversions between other encodings are handled by @code{iconv(3)}
by default.  However, @code{iconv(3)} API lacks a feature to customize
the behavior when an input character can't be encoded in the output CES.
If you need to be sensitive about it, you can disable delegation to
@code{iconv(3)} by the following parameter.
@c JP
上記以外のコードとの変換はデフォルトで@code{iconv(3)}を利用します。
ただ、@code{iconv(3)}のAPIには、出力CESでエンコードできない文字が入力に
含まれていた場合の振る舞いをカスタマイズするインタフェースがありません。
そこまでの制御が必要なら、次のパラメータで@code{iconv(3)}の使用を止めることができます。
@c COMMON

@deffn {Parameter} external-conversion-library
@c EN
The value of this parameter can be a symbol @code{iconv} or @code{#f}.
The default value is @code{iconv}.

Conversion ports opened during this parameter being @code{iconv}
will use @code{iconv(3)} library if the requested conversion isn't
supported by Gauche's native converters.
This only affect when the conversion port
is opened---once it is opened, this parameter value is irrelevant.
@c JP
このパラメータの値はシンボル@code{iconv}か@code{#f}でなければなりません。
デフォルトの値は@code{iconv}です。

このパラメータの値が@code{iconv}である間にオープンされた変換ポートは、
要求された変換がGauche内部でサポートされていなかった場合に@code{iconv(3)}ライブラリを
使います。変換ポートがopenされる時点でのパラメータの値が重要です--一旦オープンされたら、
パラメータの値はそのポートの動作に影響を与えません。
@c COMMON
@end deffn

@c EN
You can check whether the specific conversion is supported on
your system or not, by the following function.
@c JP
特定の変換がシステムでサポートされているかどうかは次の手続きで調べることができます。
@c COMMON

@defun ces-conversion-supported? from-ces to-ces
@c MOD gauche.charconv
@c EN
Returns @code{#t} if conversion from the character encoding scheme
(CES) @var{from-ces} to @var{to-ces} is supported in this system.

Note that this procedure may return true even if system only supports
partial conversion between @var{from-ces} and @var{to-ces}.
In such case, actual conversion might lose information by coercing
characters in @var{from-ces} which are not supported in @var{to-ces}.
(For example, conversion from Unicode to EUC-JP is "supported",
although Unicode has characters that are not in EUC-JP).

Also note that this procedure always returns @code{#t}
if @var{from-ces} and/or @var{to-ces} is "none",
for conversion to/from CES "none" always succeeds (in fact, it does nothing).

This procedure may be affected by the value of the parameter
@code{external-conversion-library}.
@c JP
CES @var{from-ces}から@var{to-ces}への変換がサポートされていれば@code{#t}を、
そうでなければ@code{#f}を返します。

システムが@var{from-ces}から@var{to-ces}への変換を部分的にしか
サポートしていない場合でもこの手続きは@code{#t}を返すことに注意して下さい。
そのような場合、実際の変換作業は@var{from-ces}にあって@var{to-ces}にない
コードを置換文字に置き換える等で情報を失うかもしれません
(例えば、UnicodeからEUC-JPへの変換はサポートされていますが、
UnicodeにはEUC-JPにない文字も含まれています)。

@var{from-ces}か@var{to-ces}が "none" ならばこの手続きは常に@code{#t}を
返します。なぜならそのような変換は常に成功するからです(何も変換しないわけですが)。

この手続きは、パラメータ@code{external-conversion-library}に影響を受けます。
@c COMMON
@end defun

@c EN
Also there are two useful procedures to deal with CES names.
@c JP
また、CESを扱う二つの便利な手続きが用意されています。
@c COMMON

@defun ces-equivalent? ces-a ces-b :optional unknown-value
@c MOD gauche.charconv
@c EN
Returns true if two CESes @var{ces-a} and @var{ces-b} are equivalent
to the knowledge of the system.  Returns false if they are not.
If the system doesn't know about equivalency, @var{unknown-value}
is returned, whose default is @code{#f}.

CES "none" works like a wild card; it is "equivalent" to any CES.
(Thus, @code{ces-equivalent?} is not transitive.
The intended use of @code{ces-equivalent?}
is to compare two given CES names and see if conversion is required or not).
@c JP
CES @var{ces-a}と@var{ces-b}がシステムの知る限りで等価だった場合に
@code{#t}を、等価でない場合に@code{#f}を返します。
システムがその等価性を判断出来ない場合は@var{unknown-value}に与えられた
値を返します。そのデフォルトは@code{#f}です。

CES名 "none" はワイルドカードのように動作します。それはどんなCESとも
等価と見倣されます。(従って、@code{ces-equivalent?} は遷移的ではありません。
この手続きは、二つのCESを知った時に相互の変換が
必要かどうかを判断するためのものです)。
@c COMMON

@example
(ces-equivalent? 'eucjp "EUC-JP")            @result{} #t
(ces-equivalent? 'shift_jis "EUC-JP")        @result{} #f
(ces-equivalent? "NoSuchEncoding" 'utf-8 '?) @result{} ?
@end example
@end defun

@defun ces-upper-compatible? ces-a ces-b :optional unknown-value
@c MOD gauche.charconv
@c EN
Returns true if a string encoded in CES @var{ces-b} can also
be regarded as a string encoded in @var{ces-a} without conversion,
to the knowledge of the system.
Returns false if not.  Returns @var{unknown-value}
if the system can't determine which is the case.

Like @code{ces-equivalent?}, CES "none" works like a wildcard.
It is upper-compatible to any CES, and any CES is upper-compatible to
"none".
@c JP
CES @var{ces-b}でエンコードされた文字列が、システムの知る限りで
変換無しに@var{ces-a}でエンコードされたものと見倣せる場合に@code{#t}を
返します。見倣せない場合は@code{#f}を返します。
システムが判断できない場合は@var{unknown-value}に与えられた
値を返します。そのデフォルトは@code{#f}です。

@code{ces-equivalent?}と同様に、CES名 "none" はワイルドカードとして
働きます。@var{ces-a} か @var{ces-b} が "none" であれば、
常に@code{#t}が返されます。
@c COMMON

@example
(ces-upper-compatible? "eucjp" "ASCII")             @result{} #t
(ces-upper-compatible? "eucjp" "utf-8")             @result{} #f
(ces-upper-compatible? "utf-8" "NoSuchEncoding" '?) @result{} ?
@end example
@end defun

@c EN
When Gauche's internal conversion routine encounters a character that can't
be mapped, the behaivor depends on the @emph{illegal output handling mode}
of the conversion port, specified by @var{illegal-output} keyword
arguments.
If the mode is @code{raise}, an @code{<io-encoding-error>}
is thrown.  If the mode is @code{replace},
the character is replaced with a replacement character.

A replacement character is U+FFFD (REPLACEMENT CHARACTER) if it is
available.  For Japanese encodings, U+FFFD isn't available, and
we use U+3013 (geta mark), for it is traditionally used as the
replacement character.  If neither one is available,
@code{?} is used.

If that happens in iconv, handling of such character depends
on iconv implementation (glibc implementation returns an error).
@c JP
出力CESへマップ不可能な入力文字に出会った場合のGaucheの内部変換ルーチンの動作は、
@var{illegal-output}キーワード引数で指定される
変換ポートの不正出力ハンドリングモードで決まります。
モードが@code{raise}なら@code{<io-encoding-error>}が投げられます。
モードが@code{replace}なら、その文字は置換文字に置き換えられます。

変換先の文字エンコーディングで UniocdeのU+FFFD (REPLACEMENT CHARACTER)
が使えればそれが置換文字となります。日本語エンコーディングではその文字は
使えませんが、伝統的にgeta mark '〓' (U+3013) が使われてきたので
それに準じてU+3013を使います。どちらの文字も使えなければ@code{?}に置換します。

入力CESでシングルバイトである場合は '?' に置換します。
iconvによる変換でマップ不可能な文字に出会った場合の処理はiconvの実装に
依存します(例えばglibcではエラーとなります)。
@c COMMON

@c EN
If the conversion routine encounters an input sequence that
is illegal in the input CES, an @code{<io-decoding-error>} is signaled.
@c JP
変換ルーチンが、入力CESとして不正な入力文字列に出会った場合は
@code{<io-decoding-error>}が報告されます。
@c COMMON

@c EN
@subsubheading UTF encoding and BOM
@c JP
@subsubheading UTFエンコーディングとBOM
@c COMMON

@c EN
Unicode character U+FEFF (Zero-Width No-Break Space) can have a
special meaning if it appears at the very beginning of UTF stream.
It serves as a BOM (Byte-order mark) to signify the byte order
of the following UTF data.  For UTF-16 and UTF-32, it is critical
to know the byte order.  UTF-8 does not need one, for the byte order
doesn't matter.  Nevertheless, some software adds BOM to a UTF-8 data
just to indicate it is in UTF-8.
@c JP
Unicode文字U+FEFF (Zero-Width No-Break Space) はUTFストリームの最初に
現れると特別な意味を持ちます。後続のUTFデータのバイトオーダーを記述する
BOM (Byte-order mark)になるのです。
UTF-16とUTF-32ではバイトオーダーを知ることは決定的に重要です。
一方、UTF-8ではバイトオーダーは関係ないのでBOMは必要ではありませんが、
いくつかのソフトウェアはデータがUTF-8であることを判別するためだけに
BOMを付加することがあります。
@c COMMON

@c EN
Technically, BOM is not a part of the text content, but rather a
piece of meta-information about the format.  That poses an issue;
when you deal with a data stream,
sometimes you just want to deal with the content, while the other times
you want to deal with the entire data, including the meta-information.
Traditionally those two are not strictly distinguished and
dealt in ad-hoc way.
We take the following approach, depending on the specified encoding.
@c JP
技術的な観点からは、BOMはテキストの内容の一部ではなく、フォーマットに関するメタ情報です。
これはちょっと困った事態を引き起こします。データストリームを扱う時に、
テキストの内容を読みたい場合と、メタ情報を含めた全体を扱いたい場合があるからです。
伝統的に、この二つは厳密には区別されず、アドホックな方法で処理されてきました。
Gaucheでは指定されたエンコーディングに応じて以下のとおりにしています。
@c COMMON

@table @code
@item UTF-8
@c EN
We don't treat BOM specially; if the first codepoint is U+FEFF,
it is read as the character @code{#\ufeff}.
For output, no BOM will be produced.
This is the default behaivor of I/O.
@c JP
BOMは特別扱いされません。入力の最初にU+FEFFがあれば、それは文字@code{#\ufeff}
として読まれます。出力の場合、BOMは付加されません。
これがI/Oでのデフォルトの挙動です。
@c COMMON
@item UTF-8-BOM
@c EN
This is a 'pseudo' encoding---it is UTF-8, but if the input data begins
with BOM, it is simply ignored.  This is for the convenience
of the programs that just don't want to be bothered by optional BOM
at the beginning of UTF-8 stream.  This encoding can't be used
for output.  If you absolutely need to produce UTF-8 with BOM,
just write @code{#\ufeff} at the beginning of the UTF-8 stream.
@c JP
これは、UTF-8だけれども入力データにBOMがあればそれをただ無視するという
「擬似」エンコーディングです。UTF-8ストリームの先頭のBOMの有無を気にしたくない
プログラムのために用意されています。
このエンコーディングは出力には使えません。UTF-8の出力にどうしてもBOMをつける必要があるなら、
最初に@code{#\ufeff}を書き出してください。
@c COMMON
@item UTF-16, UTF-32
@c EN
The input recognizes BOM and decides the byte order; BOM itself won't
appear in the read data.  If BOM is missing, big-endian
(UTF-16BE, UTF-32BE) is assumed.
The output emits BOM at the beginning of the data.
@c JP
入力はBOMを認識してバイトオーダーを決定します。BOM自身は読まれるデータには含まれません。
BOMが無かった場合はビッグエンディアン(UTF-16BE, UTF-32BE)が使われます。
出力の場合はBOMが先頭に付加されます。
@c COMMON
@item UTF-16LE, UTF-32LE, UTF-16BE, UTF-32BE
@c EN
We assume the byte-order meta-information is given via separate channel,
so that the caller already know the byte-order of the input.
These do not treat BOM specially; if the first codepoint is U+FEFF,
it is read as the character @code{#\ufeff}.
For output, no BOM will be produced.
@c JP
これらのエンコーディングでは、メタ情報は既に別の方法で与えられていて
呼び出し元は入力データのバイトオーダーを既に知っているものとみなします。
従ってBOMは特別扱いされません。入力の最初にU+FEFFがあれば、それは文字@code{#\ufeff}
として読まれます。出力の場合、BOMは付加されません。
@c COMMON
@end table

@c EN
@subsubheading Details of Gauche's native conversion algorithm
@c JP
@subsubheading Gaucheの内部変換アルゴリズムの詳細
@c COMMON

@c EN
Between EUC_JP, Shift JIS and ISO2022JP, Gauche uses arithmetic
conversion whenever possible.  This even maps the undefined codepoint
properly.  Between Unicode (UTF-8) and EUC_JP, Gauche uses lookup tables.
Between Unicode and Shift JIS or ISO2022JP, Gauche converts the
input CES to EUC_JP, then convert it to the output CES.
ISO8859-N are converted to Unicode using tables, then converted to
the output CES if necessary.
If the same CES is specified for input and output, Gauche's conversion
routine just copies input characters to output characters, without
checking the validity of the encodings.
@c JP
EUC_JP、Shift JIS、及びISO2022JP間の変換は可能な限り計算で行います。
文字が未定義のコードポイントも計算式に従って変換されます。
Unicode(UTF-8)とEUC_JP間の変換はテーブルルックアップによって行われます。
UnicodeとShift JISまたはISO2022JP間の変換は、入力CESを一度EUC_JPに
変換し、それを出力CESに変換することによって行います。
ISO8859-NはUnicodeにへテーブルで変換され、必要ならばそこから出力CESに変換されます。
入力と出力のCESがGaucheの内部アルゴリズムがサポートする範囲で等しかった場合、
Gaucheの変換ルーチンはエンコーディングの正当性はチェックせず、
単に入力を出力にコピーします。
@c COMMON

@table @code
@item EUC_JP, EUCJP, EUCJ, EUC_JISX0213
@c EN
Covers ASCII, JIS X 0201 kana, JIS X 0212 and JIS X 0213 character sets.
JIS X 0212 character set is supported merely because it uses
the code region JIS X 0213 doesn't use, and JIS X 0212 characters
are not converted properly to Shift JIS and UTF-8.
Use JIS X 0213.
@c JP
ASCII, JIS X 0201カナ、JIS X 0212、及びJIS X 0213文字集合をカバーします。
JIS X 0212は、単にJIS X 0213と重ならないコードを使っているためにサポート
されていますが、他のCESへの変換は行われないので注意して下さい。
なるべくJIS X 0213の使用をおすすめします。
@c COMMON

@item SHIFT_JIS, SHIFTJIS, SJIS
@c EN
Covers Shift_JISX0213, except that 0x5c and 0x7e is mapped to ASCII
character set (REVERSE SOLIDUS and TILDE),
instead of JIS X 0201 Roman (YEN SIGN and OVERLINE).
@c JP
Shift_JISX0213をカバーします。但し、0x5cと0x7eに関しては
JIS X 0201 Roman (YEN SIGNとOVERLINE) ではなく
ASCII (REVERSE SOLIDUSとTILDE) にマップされます。
@c COMMON

@item UTF-8, UTF8
@c EN
Unicode.  Note that some JIS X 0213 characters are mapped to Extension B
(U+20000 and up).
Some JIS X 0213 characters are mapped to two
unicode characters (one base character plus a combining character).
@c JP
Unicodeです。JIS X 0213中の文字のいくつかはExtension B (U+20000〜)
にマップされます。JIS X 0213中の他の文字のいくつかは2つのUnicode文字
(base character + combining character)にマップされます。
@c COMMON

@item ISO2022JP, CSISO2022JP, ISO2022JP-1, ISO2022JP-2, ISO2022JP-3
@c EN
These encodings differ a bit
(except ISO2022JP and CSISO2022JP, which are synonyms), but
Gauche handles them same.  If one of these CES is specified as input,
Gauche recognizes escape sequences of any of CES.
ISO2022JP-2 defines several non-Japanese escape sequences, and
they are recognized by Gauche, but mapped to substitution character
('?' or geta mark).
@c JP
これらのエンコーディングは、CSISO2022JPがISO2022JPのエイリアスであることを除き
異なるエスケープシーケンスを使いますが、Gaucheの中では同じルーチンで処理されます。
これらのエンコーディングのいずれかが入力CESに指定された場合、
Gaucheは全てのバリエーションのエスケープシーケンスを認識します。
但し、ISO2022JP-2に定義された日本語以外の言語のエスケープシーケンスに関しては、
Gaucheはエスケープシーケンスの認識だけを行い、
文字は'?'あるいは'〓' に置換します。
@c COMMON

@c EN
For output, Gauche assumes ISO2022JP first, and uses ISO2022JP-1
escape sequence to put JIS X 0212 character, or uses ISO2022JP-3
escape sequence to put JIS X 0213 plane 2 character.
Thus, if the string contains only JIS X 0208 characters,
the output is compatible to ISO2022JP.
Precisely speaking, JIS X 0213 specifies some characters in JIS X 0208
codepoint that shouldn't be mixed with JIS X 0208 characters;
Gauche output those characters as JIS X 0208 for compatibility.
(This is the same policy as Emacs-Mule's iso2022jp-3-compatible mode).
@c JP
出力に関してはGaucheは出来る限りISO2022JPでエンコードし、
JIS X 0212文字に出会ったらISO2022JP-1のエスケープシーケンスを、
JIS X 0213の第2面の文字に出会ったらISO2022JP-3のエスケープシーケンスを
用います。したがって、文字列がJIS X 0208の範囲だけで構成されていた場合は
出力はISO2022JP互換となります。
厳密には、JIS X 0213では包摂基準の変更により、
「JIS X 0208と同じコードポイントを用いるがJIS X 0208のエスケープシーケンスを
使ってはいけない文字」というのが定義されています。
Gaucheでは互換性のため、これらの文字もJIS X 0208のエスケープシーケンスを
用いてエンコードします (これは、Emacs-Muleにおけるiso2022jp-3-compatible
モードと同じ方針です)。
@c COMMON
@end table

@node Autodetecting the encoding scheme, Conversion ports, Supported character encoding schemes, Character code conversion
@subsection Autodetecting the encoding scheme
@c NODE 文字エンコーディングの自動判定

@c EN
There are cases that you don't know the CES of the input, but
you know it is one of several possible encodings.
The charconv module has a mechanism
to guess the input encoding.  There can be multiple algorithms,
and each algorithm has the name (wildcard CES).  Right now, there's only one
algorithm implemented:
@c JP
しばしば、入力のCESが未知であり、可能性のあるいくつかの候補から入力のCESを
推測しなければならない場合があります。推測するアルゴリズムはいくつも考えられるので、
それぞれに名前がついています(ワイルドカードCES)。
今のところ、一つのアルゴリズムしか実装されていません。
@c COMMON
@table @code
@item "*JP"
@c EN
To guess the character encoding from japanese text, among either
ISO2022-JP(-1,2,3), EUCJP, SHIFT_JIS or UTF-8.

(Even when the input is UTF-8 with BOM, it is still recognized as UTF-8,
not UTF-8-BOM).
@c JP
日本語のテキストのCESを、ISO2022-JP(-1,2,3), EUCJP, SHIFT_JIS または UTF-8の
いずれかであるとして推測する。

(入力がBOMつきUTF-8であった場合も、UTF-8-BOMではなくUTF-8が認識結果となります)。
@c COMMON
@end table

@c EN
The wildcard CES can be used in place of CES name for some conversion functions.
@c JP
ワイルドカードCESは、いくつかの変換関数においてCES名の代わりに使うことができます。
@c COMMON


@defun ces-guess-from-string string scheme
@c MOD gauche.charconv
@c EN
Guesses the CES of @var{string} by the character guessing scheme
@var{scheme} (e.g. "*JP").  Returns CES name that can be used
by other charconv functions.   It may return @code{#f} if the
guessing scheme finds no possible encoding in @var{string}.
Note that if there may be more than one possible encoding in
@var{string}, the guessing scheme returns one of them,
usually in favor of the native CES.
@c JP
文字列@var{string}のCESを、CES推測アルゴリズム@var{scheme} ("*JP"など)
を使って推測し、結果のCES名を返します。もしどのCESにも該当しないデータが
含まれていれば@code{#f}が返されます。複数のCESが可能である場合、
ネイティブエンコーディングが含まれていればそれを、
そうでなければ可能なCESからどれかひとつが選んで返されます。
@c COMMON
@end defun


@node Conversion ports,  , Autodetecting the encoding scheme, Character code conversion
@subsection Conversion ports
@c NODE 変換ポート

@defun open-input-conversion-port source from-code :key to-code buffer-size owner? illegal-output
@c MOD gauche.charconv
@c EN
Takes an input port @var{source}, which feeds characters
encoded in @var{from-code}, and returns another input port,
from which you can read characters encoded in @var{to-code}.
@c JP
文字が符号化方法@var{from-code}で符号化されているデータを読み出せる
入力ポート@var{source}を取り、符号化方法@var{to-code}で符号化されたデータを
読み出せるポートを作成して返します。
@c COMMON

@c EN
If @var{to-code} is omitted, the native CES is assumed.
@c JP
@var{to-code}が省略された場合はネイティブのCESと見なされます。
@c COMMON

@c EN
@var{buffer-size} is used to allocate internal buffer size for
conversion.  The default size is about 1 kilobytes and it's suitable
for typical cases.
@c JP
@var{buffer-size}は変換のための内部バッファのサイズを指定します。
省略時のサイズは1Kバイト程で、通常の使用には問題ないサイズです。
@c COMMON

@c EN
@var{hanlding} argument specifies the behavior when the output CES
doesn't have the corresponding character of input.  It can be a symbol
@code{raise} to raise an @code{<io-encoding-error>} in such cases,
or a symbol @code{replace} to replace the character with a replacement
character appropriate in the output CES.  If omitted, @code{raise}
is assumed.
@c JP
@var{illegal-output}引数は、出力CESに入力に対応する文字がない場合の動作を指定します。
引数はシンボル@code{raise}か@code{replace}でなければなりません。
@code{raise}の場合は、@code{<io-encoding-error>}が投げられます。
@var{replace}の場合は、出力CESに応じた適切な置換文字が代わりに出力されます。
省略された場合は@code{raise}の動作となります。
@c COMMON

@c EN
Note that @code{iconv(3)} library API doesn't offer an option to
choose the illegal-output handling mode. So when the conversion is delegated to
@code{iconv(3)}, @var{illegal-output} is ignored and the behavior follows
the underlying @code{iconv(3)} implementation.  If you need to make
sure @var{illegal-output} is honored, you can bind the parameter
@code{external-conversion-library} to @code{#f} when calling
this procedure; then the conversion port won't
use @code{iconv(3)} and raises unsupported encodings error if the
conversion can't be handled entirely within Gauche.
@c JP
@code{iconv(3)}ライブラリは、ハンドリングモードを指定するAPIを持っていないことに
注意してください。変換が@code{iconv(3)}に任されると、@var{illegal-output}の指定は
無視され、動作は@code{iconv(3)}の実装に依存します。
@var{illegal-output}の指定通りに動いて欲しい場合は、パラメータ
@code{external-conversion-library}を@code{#f}に束縛している環境で
この手続きを呼んでください。そうすると、変換ポートは@code{iconv(3)}を使わず、
Gauche内部で変換できない場合はエラーを投げます。
@c COMMON

@c EN
By default, @code{open-input-conversion-port} leaves @var{source} open.
If you specify true value to @var{owner?}, the function closes
@var{source} after it reads EOF from the port.
@c JP
通常、@code{open-input-conversion-port}は変換が全て終了した後でも@var{source}
はオープンしたままにします。キーワード引数@var{owner?}に真の値を指定すると、
EOFが読まれた後で@var{source}はクローズされます。
@c COMMON

@c EN
If you don't know the @var{source}'s CES, you can specify
CES guessing scheme, such as @code{"*JP"}, in place of @var{from-code}.
The conversion port tries to guess the encoding, by prefetching
the data from @var{source} up to the buffer size.  It signals an error
if the code guessing routine finds no appropriate CES.
If the guessing routine finds ambiguous input, however, it silently
assume one of possible CES's, in favor of the native CES.
Hence it is possible that the guessing is wrong if the buffer
size is too small.  The default size is usually enough for most
text documents, but it may fail if the large text contains mostly ASCII
characters and multibyte characters appear only at the very end of
the document.
To be sure for the worst case,
you have to specify the buffer size large enough to
hold entire text.
@c JP
入力のCESが不明な場合、@code{"*JP"}などのCES推測アルゴリズム名を@var{from-code}
として指定することができます。変換ポートは最高でバッファサイズまでのデータを先読みし、
CESを推測しようとします。そのアルゴリズムで推測されるどのCESにも該当しないデータが
検出された場合はエラーが報告されます。もし複数のCESが可能であるようなデータであった
場合は、Gaucheのネイティブエンコーディングが可能なCESに含まれていればそれが選ばれ、
そうでなければいずれかのCESが適当に選ばれます。従って、バッファサイズが小さすぎると
誤った判定をする可能性が高くなります。大抵のテキストドキュメントに対して、
既定のバッファサイズは十分ですが、大きなテキストのほとんどがASCII文字で最後だけ
マルチバイト文字が現われるようなテキストでは誤判定の可能性があります。
最悪の場合でも結果を保証するには、テキスト全体が格納できるバッファサイズを指定すると
良いでしょう。
@c COMMON


@c EN
For example, the following code copies a file @file{unknown.txt} to a file
@file{eucjp.txt}, converting unknown japanese CES to EUC-JP.
@c JP
例を示しましょう。以下のコードは未知のCES(但しEUC-JP, SJIS, ISO2022-JP, UTF8の
いずれかであることは分かっている)で書かれたテキストファイル@file{unknown.txt}を
読みだし、文字エンコーディングをEUC-JPに変換して@file{eucjp.txt}に書き出します。
@c COMMON
@example
(call-with-output-file "eucjp.txt"
  (lambda (out)
    (copy-port (open-input-conversion-port
                 (open-input-file "unknown.txt")
                 "*jp"             ;@r{guess code}
                 :to-code "eucjp"
                 :owner? #t)       ;@r{close unknown.txt afterwards}
               out)))
@end example

@c EN
For the portable code, you can also use SRFI-181 @code{transcoded-port}
(@pxref{Transcoded ports}).
@c JP
ポータブルなコードでは、SRFI-181の@code{transcoded-port}を使うこともできます
(@ref{Transcoded ports}参照)。
@c COMMON
@end defun


@defun open-output-conversion-port sink to-code :key from-code buffer-size owner? illegal-output
@c MOD gauche.charconv
@c EN
Creates and returns an output port that converts
given characters from @var{from-code} to @var{to-code}
and feed to an output port @var{sink}.
If @var{from-code} is omitted, the native CES is assumed.
You can't specify a character guessing scheme (such as "*JP") to
neither @var{from-code} nor @var{to-code}.
@c JP
文字のエンコーディングを@var{from-code}から@var{to-code}に変換して
出力ポート@var{sink}に書き出すような出力変換ポートを作成して返します。
@var{from-code}が省略された場合はネイティブのCESと見なされます。
@var{from-code}にも@var{to-code}にも、CES推測アルゴリズム名を
使用することはできません。
@c COMMON

@c EN
@var{buffer-size} specifies the size of internal conversion buffer.
The characters put to the returned port may stay in the buffer,
until the port is explicitly flushed (by @code{flush}) or
the port is closed.
@c JP
@var{buffer-size}は内部で変換に使われるバッファサイズを指定します。
出力変換ポートに書き出された文字は、@code{flush}を使って明示的に
フラッシュするか出力変換ポートが閉じられるまで、バッファ内に残っている可能性があります。
@c COMMON

@c EN
By default, the returned port doesn't closes @var{sink} when
itself is closed.  If a keyword argument @var{owner?} is provided
and true, however, it closes @var{sink} when it is closed.
@c JP
通常、出力変換ポートがクローズされても@var{sink}はクローズされません。
@var{owner?}に真の値を与えれば、出力変換ポートのクローズ時に@var{sink}を
クローズするようにできます。
@c COMMON

@c EN
The @var{illegal-output} keyword argument is the same
as @code{open-input-conversion-port}.
@c JP
@var{illegal-output}キーワード引数は、
@code{open-input-conversion-port}と同じです。
@c COMMON

@c EN
For the portable code, you can also use SRFI-181 @code{transcoded-port}
(@pxref{Transcoded ports}).
@c JP
ポータブルなコードでは、SRFI-181の@code{transcoded-port}を使うこともできます
(@ref{Transcoded ports}参照)。
@c COMMON
@end defun

@defun ces-convert-to return-type source from-code :optional to-code :key illegal-output
@defunx ces-convert source from-code :optional to-code :key illegal-output
@c MOD gauche.charconv
@c EN
Convert @var{source}, which is a string or an u8vector
of multibyte encoding in @var{from-code}, to a
string or u8vector encoded in @var{to-code}.  If @var{to-code} is
omitted, the native CES is assumed.
@c JP
文字エンコーディング@var{from-code}でエンコードされた
文字列もしくはu8vectorの@var{source}を変換し、
文字エンコーディング@var{to-code}でエンコードされた文字列またはu8vectorを返します。
@var{to-code}が省略された場合はネイティブエンコーディングへと変換されます。
@c COMMON

@c EN
In @code{ces-convert-to}, you can specify the return type by
@var{return-type} argument; it must be either a class object @code{<string>}
or @code{<u8vector>}.  On the other hand, @code{ces-convert} always returns
a string, regardless of the type of @var{source}.
@c JP
@code{ces-convert-to}では、戻り値の型を@var{return-type}で指定します。
@var{return-type}はクラスオブジェクト@code{<string>}か@code{<u8vector>}
でなければなりません。一方、@code{ces-convert}は、@var{source}の型にかかわらず
常に文字列を返します。
@c COMMON

@c EN
If @var{to-code} is different from the native CES and a string
is returned, it can be an incomplete string.  It's for the backward
compatibility---in general, we recommend to use u8vector to represent
multibyte sequence in CES other than the native encoding.
@c JP
ネイティブエンコーディング以外のエンコーディングを@var{to-code}に指定して
文字列が返された場合、それは不完全な文字列であるかもしれません。
これは後方互換性のためです。一般的には、ネイティブエンコーディング以外の
マルチバイトシーケンスを扱う場合はu8vectorを使うことをおすすめします。
@c COMMON

@c EN
@var{from-code} can be a name of character guessing scheme
(e.g. "*JP").
@c JP
@var{from-code}にはCES推測アルゴリズム名("*JP"など)を与えることができます。
@c COMMON

@c EN
The keyword argument @var{illegal-output} controls
the behavior when input contains a character that can't be encoded
in the output.  See @code{open-input-conversion-port} above for the
description.  By default, an @code{<io-encoding-error>} is raised,
except when the conversion is delegated to @code{iconv(3)}, in which case
the behavior depends on the external library.
@c JP
キーワード引数@var{illegal-output}は出力側でエンコードできない文字が
入力された場合の振る舞いを指定します。上の@code{open-input-conversion-port}の
説明を参照してください。デフォルトでは@code{<io-encoding-error>}が投げられます
(ただし、変換が@code{iconv(3)}に任された場合、
その振る舞いは外部ライブラリの実装に依存します)。
@c COMMON

@c EN
For the portable code, you can also use SRFI-181 @code{bytevector->string}
and @code{string->bytevector}
(@pxref{Transcoded ports}).
@c JP
ポータブルなコードでは、SRFI-181の@code{bytevector->string}
および@code{string->bytevector}を使うこともできます
(@ref{Transcoded ports}参照)。
@c COMMON
@end defun

@defun call-with-input-conversion iport proc :key encoding conversion-buffer-size illegal-output
@defunx call-with-output-conversion oport proc :key encoding conversion-buffer-size illegal-output
@c MOD gauche.charconv
@c EN
These procedures can be used to perform character I/O with
different encoding temporary from the original port's encoding.

@code{call-with-input-conversion} takes an input port @var{iport}
which uses the character encoding @var{encoding}, and
calls @var{proc} with one argument, a conversion input port.
From the port, @var{proc} can read characters in utf-8.
Note that once @var{proc} is called, it has to read all the
characters until EOF; see the note below.

@code{call-with-output-conversion} takes an output port @var{oport}
which expects the character encoding @var{encoding}, and
calls @var{proc} with one argument,
a temporary conversion output port.
To the port, @var{proc} can write characters in utf-8.
When @var{proc} returns, or it exits with an error,
the temporary conversion output port is flushed and closed.
The caller of @code{call-with-output-conversion}
can continue to use @var{oport} with original encoding afterwards.

Both procedure returns the value(s) that @var{proc} returns.
The default value of @var{encoding} is Gauche's internal
encoding.  Those procedures don't create a conversion port
when it is not necessary.   If @var{conversion-buffer-size} is given,
it is used as the @var{buffer-size} argument when the conversion
port is open.

You shouldn't use @var{iport}/@var{oport} directly
while @var{proc} is active---character encoding is a
stateful process, and mixing I/O from/to the conversion port and
the underlying port will screw up the state.

@emph{Note:} for the @code{call-with-input-conversion}, you can't
use @var{iport} again unless @var{proc} reads EOF from it.
It's because a conversion port needs to buffer the input, and
there's no way to undo the buffered input to @var{iport}
when @var{proc} returns.
@c JP
この2つの手続きを使うと、元のポートのエンコーディングとは異る一時的な
エンコーディングをもつ文字I/Oを行うことが可能です。

@code{call-with-input-conversion} は、文字エンコード@var{encoding} を
もつ入力ポート @var{iport} をとり、@var{proc}を一つの引数、すなわち、
変換入力ポートとともに呼びだします。このポートから、@var{proc} は文字を
Gauche の内部エンコーディングで読み込むことができます。いったん、
@var{proc}が呼ばれたら、EOFまでのすべての文字を読み込まなくてはなりません。
後述の注意を参照してください。

@code{call-with-output-conversion} は、文字エンコーディング @var{encoding}
を期待する出力ポート @var{oport} をとり、@var{proc}を一つの引数、すなわち、
一時的な変換出力ポートとともに呼びだします。このポートへ、@var{proc}は
Gauche の内部エンコーディングをもつ文字を書き込むことができます。
@var{proc} が戻るか、エラーで抜けると、この一時的な変換出力ポートは
フラッシュされて、クローズされます。@code{call-with-output-conversion}
の呼出し側は、その後、元のエンコーディングのポート@var{oport}を使い
続けること可能です。

どちらの手続きも @var{proc} が返す値を返します。@var{encoding}
のデフォルト値は Gauche の内部エンコーディングです。この2つの手続きは
必要がなければ、変換ポートを作成しません。もし
@var{conversion-buffer-size} が与えられていれば、変換ポートがオープン
されるときに、@var{buffer-size} 引数として使われます。

@var{proc} がアクティブであるあいだは、@var{iport}/@var{oport} を直接
使うべきではありません。文字のエンコーディングはステートフルなプロセスで
変換ポート(から/へ)の入出力を混在させると元にあるポートの状態がおかしく
なってしまいます。

@emph{注意:} @code{call-with-input-conversion} については、
@var{proc} が EOF を読むまでは、@var{iport} を再度利用することはできません。
これは、変換ポートがバッファを必要とし、@var{proc} がもどったときに
@var{iport}へのバッファ付き入力をアンドゥする方法がないからです。
@c COMMON
@end defun

@defun with-input-conversion iport thunk :key encoding conversion-buffer-size illegal-output
@defunx with-output-conversion oport thunk :key encoding conversion-buffer-size illegal-output
@c MOD gauche.charconv
@c EN
Similar to @code{call-with-*-conversion},
but these procedures call @var{thunk} without arguments,
while the conversion port is set as the current input or output port,
respectively.
The meaning of keyword arguments are the same as @code{call-with-*-conversion}.
@c JP
@code{call-with-*-conversion} と似ていますが、この2つの手続きは、
@var{thunk} を引数なしで呼びます、また、変換ポートはそれぞれ標準入力、標準
出力のポートにセットされます。
キーワード引数の意味は @code{call-with-*-conversion} と同じです。
@c COMMON
@end defun

@defun wrap-with-input-conversion port from-code :key to-code owner? buffer-size illegal-output
@defunx wrap-with-output-conversion port to-code :key from-code owner? buffer-size illegal-output
@c MOD gauche.charconv
@c EN
Convenient procedures to avoid adding unnecessary conversion port.
Each procedure works like @code{open-input-conversion-port}
and @code{open-output-conversion-port}, respectively,
except if system knows no conversion is needed,
no conversion port is created and @var{port} is returned as is.

When a conversion port is created, @var{port} is always owned by the port.
When you want to close the port, always close the port returned
by @code{wrap-with-*-conversion}, instead the original @var{port}.
If you close the original @var{port} first, the pending conversion
won't be flushed.  (Some conversion requires trailing sequence that
is generated only when the conversion port is closing, so simply
calling @code{flush} isn't enough.)

The @var{buffer-size} and @var{illegal-output} arguments are passed to
the @code{open-*-conversion-port}.
@c JP
不要な変換ポートを作らないようにする便利な手続きです。
各手続きはそれぞれ@code{open-input-conversion-port}と
@code{open-output-conversion-port}のように動作します。
但し、指定されたCES間の変換が必要でないとシステムが知っている場合は、
変換ポートは作られず、@var{port}がそのまま返されます。

変換ポートが作られた場合、@var{port}は常に変換ポートに所有されます
(@code{:owner #t}となる)。ポートを閉じる場合は@var{port}ではなく
常に@code{wrap-with-*-conversion}が返したポートを閉じるようにして下さい。
元の@var{port}が先に閉じられた場合、変換中の結果が書き出されない可能性があります。
(変換によっては、ポートが閉じられる時点で終了シーケンスを書き出すものがあるので、
単にポートを@code{flush}するだけでは不十分です)。

@var{buffer-size}と@var{illegal-output}引数はそのまま
変換ポート作成手続きに渡されます。
@c COMMON
@end defun

@c ----------------------------------------------------------------------
@node Collection framework, Configuration parameters, Character code conversion, Library modules - Gauche extensions
@section @code{gauche.collection} - Collection framework
@c NODE コレクションフレームワーク, @code{gauche.collection} - コレクションフレームワーク

@deftp {Module} gauche.collection
@mdindex gauche.collection
@c EN
This module provides a set of generic functions (GFs) that iterate over
various collections.   The Scheme standard has some iterative
primitives such as @code{map} and @code{for-each},
and @code{scheme.list} (@pxref{R7RS lists} adds a rich set of such functions,
but they work only on lists.

Using the method dispatch of the object system, this module
efficiently extends those
functions for other collection classes such as vectors and hash tables.
It also provides a simple way for user-defined class to adapt
those operations.
So far, the following operations are defined.
@c JP
このモジュールは、様々なコレクションに対して繰り返し処理を行う総称関数を提供します。
Schemeの規格は@code{map}や@code{for-each}などの繰り返し手続きを定義しており、
また@code{scheme.list}
(@ref{R7RS lists}参照)は更に数多くの繰り返し手続きを提供しますが、
それらはリストに対してしか動作しません。

このモジュールはオブジェクトシステムのメソッドディスパッチを利用して、
これらの手続きをベクタやハッシュテーブルのような一般のコレクションタイプに対しても
効率良く動作するように拡張します。また、ユーザ定義のクラスにこれらの操作を実装するための
簡単な方法も提供します。今のところ、次のような総称関数が提供されています。
@c COMMON

@table @asis
@c EN
@item Mapping
@c JP
@item マッピング
@c COMMON
@code{fold}, @code{fold2}, @code{fold3},
@code{map}, @code{map-to}, @code{map-accum}, @code{for-each}
@c EN
@item Selection and searching
@c JP
@item 選択と探索
@c COMMON
@code{find}, @code{find-min}, @code{find-max}, @code{find-min&max},
@code{filter}, @code{filter-to},
@code{remove}, @code{remove-to}, @code{partition}, @code{partition-to}
@code{group-collection}, @code{group-collection->alist},
@code{group-by-size}, @code{group-by-size-to}
@c EN
@item Conversion
@c JP
@item 変換
@c COMMON
@code{coerce-to}
@c EN
@item Miscellaneous
@c JP
@item その他
@c COMMON
@code{size-of}, @code{lazy-size-of}
@c EN
@item Fundamental iterator creator
@c JP
@item 基礎的なイテレータ構築メソッド
@c COMMON
@code{call-with-iterator}, @code{call-with-builder},
@code{with-iterator}, @code{with-builder}, @code{call-with-iterators}.
@end table

@c EN
Those operations work on @emph{collections} and its subclass,
@emph{sequences}.  A collection is a certain form of a set
of objects that you can traverse all the object in it in a certain way.
A sequence is a collection that all its elements are ordered, so that
you can retrieve its element by index.
@c JP
これらの操作は、@emph{コレクション}とそのサブクラスである
@emph{シーケンス}に対して動作します。コレクションは、その要素を全て
訪れる方法が用意されているようなオブジェクトの集合です。
シーケンスは、要素を訪れる順序が定義されており、インデックスで要素を取り出すことが
できるようなコレクションです。
@c COMMON

@c EN
The following Gauche built-in objects are treated as collections and/or
sequences.
@c JP
次にあげるGaucheの組み込みオブジェクトはシーケンスあるいはコレクションとして動作します。
@c COMMON
@table @code
@item <list>
@c EN
A sequence.
@c JP
シーケンス
@c COMMON
@item <vector>
@c EN
A sequence.
@c JP
シーケンス
@c COMMON
@item <string>
@c EN
A sequence (of characters)
@c JP
文字のシーケンス
@c COMMON
@item <hash-table>
@c EN
A collection.  Each element is a pair of a key and a value.
@c JP
コレクション。各要素はキーと値のペア。
@c COMMON
@item <s8vector>, <u8vector>, @dots{} <c128vector>
@c EN
A sequence (methods defined in @code{gauche.uvector} module,
@pxref{Uniform vectors}).
@c JP
シーケンス。メソッドは@code{gauche.uvector}モジュール内で定義されます。
@ref{Uniform vectors}参照。
@c COMMON
@end table

@c EN
@xref{Sequence framework}, for it adds more sequence specific
methods.
@c JP
@ref{Sequence framework}も参照してください。シーケンス特有のメソッドが
追加されます。
@c COMMON

@c EN
The methods that needs to return a set of objects, i.e.
@code{map}, @code{filter}, @code{remove} and @code{partition}.
returns a list (or lists).  The corresponding ``-to'' variant
(@code{map-to}, @code{filter-to}, @code{remove-to} and @code{partition-to}.
takes a collection class argument and returns the collection of the class.
@c JP
オブジェクトの集合を返すようなメソッド、すなわち
@code{map}、@code{filter}、@code{remove}および@code{partition}は、
リストを返します。対応する``-to''がつくメソッド
(@code{map-to}、@code{filter-to}、@code{remove-to}、@code{partition-to})
はコレクションクラスも引数に取り、そのクラスのコレクションを返します。
@c COMMON
@end deftp

@menu
* Mapping over collection::
* Selection and searching in collection::
* Miscellaneous operations on collection::
* Fundamental iterator creators::
* Implementing collections::
@end menu

@node Mapping over collection, Selection and searching in collection, Collection framework, Collection framework
@subsection Mapping over collection
@c NODE コレクションに対するマッピング

@c EN
These generic functions extends the standard mapping procedures.
See also @ref{Mapping over sequences}, if you care the index
as well as elements.
@c JP
これらのジェネリックファンクションは標準のマッピング手続きを拡張します。
要素だけでなくそのインデックスも必要な場合は@ref{Mapping over sequences}を
参照して下さい。
@c COMMON

@deffn {Generic function} fold proc knil coll coll2 @dots{}
@c MOD gauche.collection
@c EN
This is a natural extension of @var{fold} (@pxref{Other list procedures}).
@c JP
@var{fold} (@ref{Other list procedures}参照) の自然な拡張です。
@c COMMON

@c EN
For each element @var{Ei} in the collection @var{coll}, @var{proc} is
called as (@var{proc} @var{Ei} @var{Ri-1}), where @var{Ri-1} is the
result of (@var{i}-1)-th invocation of @var{proc} for @var{i} > 0,
and @var{R0} is @var{knil}.  Returns the last invocation of @var{proc}.
@c JP
コレクション@var{coll}の各要素@var{Ei}に対して、手続き@var{proc}が
(@var{proc} @var{Ei} @var{Ri-1}) のように呼ばれます。ここで、
@var{Ri-1} は @var{i} > 0 に対しては (@var{i}-1)番目の@var{proc}の呼び出しの
結果であり、@var{R0}は@var{knil}です。最後の@var{proc}の戻り値を返します。
@c COMMON
@example
(fold + 0 '#(1 2 3 4)) @result{} 10
(fold cons '() "abc")  @result{} (#\c #\b #\a)
@end example

@c EN
If the @var{coll} is a sequence, it is guaranteed that
the elements are traversed in order.  Otherwise, the order
of iteration is undefined.
@c JP
@var{coll}がシーケンスでもある場合、要素はシーケンスの順に@var{proc}に渡されます。
そうでなければ繰り返しの順序は未定義です。
@c COMMON

@c EN
Note: We don't provide @code{fold-right} on collections, since the order
of elements doesn't matter, so only @code{fold} is sufficient for
meaningful traversal.
However, sequences do have @code{fold-right};
see @ref{Mapping over sequences}.
@c JP
註：コレクションに対する@code{fold-right}は提供されません。コレクションでは
要素の順序は定義されないため、意味のあるトラバースをするのには
@code{fold}だけあれば十分だからです。
しかし、シーケンスに対しては@code{fold-right}が定義されます。
@ref{Mapping over sequences}を参照して下さい。
@c COMMON

@c EN
You can fold more than one collection, although it doesn't make
much sense unless all of the collections are sequences.
Suppose @code{@var{E}(@var{k}, @var{i})} for @var{i}-th element
of @var{k}-th collection.  @var{proc} is called as
@c JP
複数のコレクションを@code{fold}に渡すこともできます (但し、その全てがシーケンスで
なければあまり意味のある操作では無いでしょう)。
@var{k}番目のコレクションの@var{i}番目の要素を@code{@var{E}(@var{k}, @var{i})}とするとき、
@var{proc}は以下のように呼ばれます。
@c COMMON
@example
(@var{proc} @var{E}(0,i) @var{E}(1,i) @dots{} @var{E}(K-1,i) @var{Ri-1})
@end example

@c EN
Different types of collections can be mixed together.
@c JP
異なる型のコレクションを混ぜて扱うことができます。
@c COMMON

@example
(fold acons '() "abc" '#(1 2 3))
  @result{} ((#\c 3) (#\b 2) (#\a 1))

@c EN
;; @r{calculates dot product of two vectors}
@c JP
;; @r{二つのベクタの内積を計算}
@c COMMON
(fold (lambda (a b r) (+ (* a b) r)) 0
      '#(3 5 7) '#(2 4 6))
  @result{} 68
@end example

@c EN
When more than one collection is given, @code{fold} terminates
as soon as at least one of the collections exhausted.
@c JP
複数のコレクションが与えられた場合、@code{fold}は少なくともひとつのコレクションが
終了した時点で終了します。
@c COMMON
@end deffn

@deffn {Generic function} fold2 proc knil1 knil2 coll coll2 @dots{}
@deffnx {Generic function} fold3 proc knil1 knil2 knil3 coll coll2 @dots{}
@c MOD gauche.collection
@c EN
Like @code{fold}, but they can carry two and three state values
instead of one, respectively.  The state values are
initialized by @var{knilN}.  The procedure @var{proc} is called
with each element of @var{collN}, and the state values.  It must return
two (@code{fold2}) or three (@code{fold3}) values, which will be used
as the state values of next iteration.  The values returned in the
last iteration will be the return values of @code{fold2} and @code{fold3}.
@c JP
@code{fold}と似ていますが、1つではなくそれぞれ2, 3個の状態値を
持ち回ります。状態値は@var{knilN}によって初期化されます。
手続き@var{proc}はコレクション@var{collN}の各要素値と状態値を
引数として取り、@code{fold2}の場合は2個、@code{fold3}の場合は3個の
値を返さねばなりません。返された値が次の繰り返しでの状態値として
使われます。最後に返された値が@code{fold2}, @code{fold3}の戻り値と
なります。
@c COMMON

@example
(fold2 (lambda (elt a b) (values (min elt a) (max elt b)))
       256 0 '#u8(33 12 142 1 74 98 12 5 99))
 @result{} 1 and 142  ;; find minimum and maximum values
@end example

@c EN
See also @code{map-accum} below.
@c JP
下の@code{map-accum}も参照。
@c COMMON
@end deffn


@deffn {Generic function} map proc coll coll2 @dots{}
@c MOD gauche.collection
@c EN
This extends the built-in @code{map} (@pxref{Walking over lists}).
Apply @var{proc} for each element in the collection @var{coll}, and
returns a list of the results.
@c JP
組み込み手続き@code{map} (@ref{Walking over lists}参照) を拡張します。
コレクション@var{coll}の各要素に手続き@var{proc}を適用し、その結果をリストにして
返します。
@c COMMON

@c EN
If the @var{coll} is a sequence, it is guaranteed that
the elements are traversed in order.  Otherwise, the order
of iteration is undefined.
@c JP
@var{coll}がシーケンスでもある場合、要素はシーケンスの順に@var{proc}に渡されます。
そうでなければ繰り返しの順序は未定義です。
@c COMMON

@c EN
If more than one collection is passed, @var{proc} is called with
elements for each collection.  In such case, @code{map} terminates
as soon as at least one of the collection is exhausted.  Note that passing
more than one collection doesn't make much sense unless
all the collections are sequences.
@c JP
複数のコレクションが与えられた場合、@var{proc}は各コレクションからの要素を引数として
呼び出されます。@code{map}はひとつでもコレクションの最後に到達したら終了します。
複数のコレクションを渡すのは、コレクションの全てがシーケンスでないとあまり意味がないでしょう。
@c COMMON

@example
(map (lambda (x) (* x 2)) '#(1 2 3))
  @result{} #(2 4 6)

(map char-upcase "abc")
  @result{} (#\A #\B #\C)

(map + '#(1 2 3) '#(4 5 6))
  @result{} (5 7 9)
@end example

@c EN
@code{map} @emph{always} returns a list.  If you want to get the result
in a different type of collection, use @code{map-to} described below.
If you wonder why @code{(map char-upcase "abc")} doesn't return
@code{"ABC"}, read the discussion in the bottom of this subsection.
@c JP
@code{map}は常にリストを返します。別のコレクション型で結果を得たい場合は、
次に示す@code{map-to}を使って下さい。何故@code{(map char-upcase "abc")}が
@code{"ABC"}を返さないのか疑問なら、この最後にあるディスカッションを参照してください。
@c COMMON
@end deffn

@deffn {Generic function} map-to class proc coll coll2 @dots{}
@c MOD gauche.collection
@c EN
This works the same as @code{map}, except the result is returned
in a collection of class @var{class}.   @code{Class} must be a
collection class and have a builder interface
(@pxref{Fundamental iterator creators}).
@c JP
@code{map}と同じように動作しますが、結果はクラス@var{class}のインスタンスとして返されます。
@var{class}はコレクションクラスでなければなりません。
また、ビルダーインタフェースを持っている必要があります
(@ref{Fundamental iterator creators}参照).
@c COMMON

@example
(map-to <vector> + '#(1 2 3) '#(4 5 6))
  @result{} #(5 7 9)

(map-to <string> char-upcase "def")
  @result{} "DEF"

(map-to <vector> char=? "bed" "pet")
  @result{} #(#f #t #f)
@end example
@end deffn

@deffn {Generic function} map-accum proc seed coll1 coll2 @dots{}
@c MOD gauche.collection
@c EN
Collects results of @var{proc} over collections, while passing
a state value.  @var{proc} is called like this:
@c JP
状態値を持ち回りながら@var{proc}のコレクションの各要素への呼び出しを集めます。
@var{proc}は次のように呼ばれます。
@c COMMON
@example
(@var{proc} @var{elt1} @var{elt2} @dots{} @var{seed})
@end example
@c EN
Where @var{elt1} @var{elt2} @dots{} are the elements of
@var{coll1} @var{coll2} @dots{}.
It must return two values; the first value is collected into
a list (like @code{map}), while the second value is passed as
@var{seed} to the next call of @var{proc}.
@c JP
ここで@var{elt1} @var{elt2} @dots{}は
@var{coll1} @var{coll2} @dots{}の各要素です。
@var{proc}は2つの値を返さねばなりません。最初の値が@code{map}のように
リストへと集められます。2つ目の値は次の@var{proc}の呼び出しの@var{seed}
として使われます。
@c COMMON

@c EN
When one of the collections is exhausted, @code{map-accum} returns
two values, the list of the first return values from @var{proc},
and the second return value of the last call of @var{proc}.
@c JP
いずれかのコレクションの要素を使い切った時点で、@code{map-accum}は
2つの値を返します。最初の値は@var{proc}の最初の戻り値をリストにしたもの、
2番目の値は@var{proc}の最後の呼び出しの2番目の戻り値です。
@c COMMON

@c EN
If the given collections are sequences, it is guaranteed that
@var{proc} is applied in order of the sequence.
@c JP
もし与えられたコレクションがシーケンスであった場合は、
@var{proc}はシーケンスの順序通りに適用されます。
@c COMMON

@c EN
This is similar to Haskell's @code{mapAccumL}, but note that
the order of @code{proc}'s argument and return values are
reversed.
@c JP
この手続きはHaskellの@code{mapAccumL}と似ています。但し、
@code{proc}の引数と戻り値の順が逆転していることに注意して下さい。
@c COMMON
@end deffn


@deffn {Generic function} for-each proc coll coll2 @dots{}
@c MOD gauche.collection
@c EN
Extension of built-in @code{for-each} (@pxref{Walking over lists}).
Applies @var{proc} for each elements in the collection(s).
The result of @var{proc} is discarded.  The return value of
@code{for-each} is undefined.
@c JP
組み込み手続き@code{for-each} (@ref{Walking over lists}参照) を拡張します。
コレクション@var{coll}の各要素に手続き@var{proc}を適用します。
@var{proc}の結果は捨てられます。@code{for-each}の結果は未定義です。
@c COMMON

@c EN
If the @var{coll} is a sequence, it is guaranteed that
the elements are traversed in order.  Otherwise, the order
of iteration is undefined.
@c JP
@var{coll}がシーケンスでもある場合、要素はシーケンスの順に@var{proc}に渡されます。
そうでなければ繰り返しの順序は未定義です。
@c COMMON

@c EN
If more than one collection is passed, @var{proc} is called with
elements for each collection.  In such case, @code{for-each} terminates
as soon as one of the collection is exhausted.  Note that passing
more than one collection doesn't make much sense unless
all the collections are sequences.
@c JP
複数のコレクションが与えられた場合、@var{proc}は各コレクションからの要素を引数として
呼び出されます。@code{for-each}はひとつでもコレクションの最後に到達したら終了します。
複数のコレクションを渡すのは、コレクションの全てがシーケンスでないとあまり意味がないでしょう。
@c COMMON
@end deffn


@deffn {Generic Function} fold$ proc
@deffnx {Generic Function} fold$ proc knil
@deffnx {Generic Function} map$ proc
@deffnx {Generic Function} for-each$ proc
@c MOD gauche.collection
@c EN
Partial-application version of @code{fold}, @code{map} and @code{for-each}.
@c JP
@code{fold}、@code{map}、@code{for-each}の部分評価版です。
@c COMMON
@end deffn


@c EN
@emph{Discussion:}  It is debatable what type of collection @code{map}
should return when it operates on the collections other than lists.
It may seem more ``natural'' if @code{(map * '#(1 2) '#(3 4))}
returns a vector, and @code{(map char-upcase "abc")} returns a string.
@c JP
@emph{Discussion:}  @code{map}がリスト以外に対して適用されたとき、どういう
コレクション型を返すべきでしょう。
@code{(map * '#(1 2) '#(3 4))} がベクタを返し、
@code{(map char-upcase "abc")} が文字列を返すようにするほうが「自然」でしょうか。
@c COMMON

@c EN
Although such interface seems work for simple cases, it'll become
problematic for more general cases.  What type of collection should
be returned if a string and a vector are passed?  Furthermore,
some collection may only have iterator interface but no builder
interface, so that the result can't be coerced to the argument type
(suppose you're mapping over database records, for example).
And Scheme programmers are used to think @code{map} returns a list,
and the result of @code{map} are applied to the procedures that
takes list everywhere.
@c JP
そのようなインタフェースは単純な場合には動作するように思えますが、
一般的な拡張は困難です。文字列とベクタが同時に渡されたらどうします?
更に、コレクションクラスによっては繰り返しインタフェースは持っていても
ビルダーインタフェースを持っていない場合があり、結果をそのコレクションクラスとして
返せない場合もあります (データベースレコードのコレクションに対してマップする、
といった用法を考えてみて下さい)。また、Schemeプログラマは@code{map}が
リストを返すという事実に慣れ親しんでおり、既存のコードも@var{map}の戻り値を
リストを受け取る手続きに渡すことがよく行われています。
@c COMMON

@c EN
So I decided to add another method, @code{map-to}, to specify
the return type explicitly
The idea of passing the return type is taken from CommonLisp's @code{map}
function, but taking a class metaobject, @code{map-to} is much flexible
to extend using method dispatch.
This protocol (``-to'' variant takes a class metaobject
for the result collection) is used throughout the collection framework.
@c JP
そこで、結果の型を明示的に指定する@code{map-to}という別のメソッドを定義しました。
結果の型を渡すのは、CommonLispの@code{map}関数にならっていますが、
Gaucheではクラスメタオブジェクトを渡すようにしたため、メソッドディスパッチを使って
拡張することが容易です。``-to'' のつくメソッドは結果のコレクションのクラスを
取るというインタフェースはコレクションフレームワーク中で統一的に使われています。
@c COMMON

@node Selection and searching in collection, Miscellaneous operations on collection, Mapping over collection, Collection framework
@subsection Selection and searching in collection
@c NODE コレクションからの選択と探索

@deffn {Generic function} find pred coll
@c MOD gauche.collection
@c EN
Applies @var{pred} for each element of a collection @var{coll} until
@var{pred} returns a true value.  Returns the element on which @var{pred}
returned a true value, or @code{#f} if no element satisfies @var{pred}.
@c JP
@var{pred}をコレクション@var{coll}の要素に適用してゆきます。@var{pred}が
真の値を返したらそこで打ち切り、その要素を返します。@var{pred}が真の値を返す
要素が無かった場合は@code{#f}を返します。
@c COMMON

@c EN
If @var{coll} is a sequence, it is guaranteed that @var{pred} is
applied in order.  Otherwise the order of application is undefined.
@c JP
@var{coll}がシーケンスでもある場合、要素はシーケンスの順に@var{proc}に渡されます。
そうでなければ繰り返しの順序は未定義です。
@c COMMON

@example
(find char-upper-case? "abcDe") @result{} #\D
(find even? '#(1 3 4 6)) @result{} 4
(find even? '(1 3 5 7))  @result{} #f
@end example
@end deffn

@deffn {Generic function} find-min coll :key key compare default
@deffnx {Generic function} find-max coll :key key compare default
@c MOD gauche.collection
@c EN
Returns a minimum or maximum element in the collection @var{coll}.

A one-argument procedure @var{key}, whose default is @code{identity},
is applied for each element to obtain a comparison value.
Then a comparison value is compared by a two-argument procedure
@var{compare}, whose default is @code{<}.
If the collection has zero or one element, the @var{compare} procedure
is never called.

When the collection is empty, a value given to @var{default} is
returned, whose default is @code{#f}.
@c JP
コレクション@var{coll}から最小もしくは最大の要素を探して返します。

コレクションの各要素に対し、1引数の手続き@var{key}が適用され、
その戻り値が比較対象となります。@var{key}のデフォルトは@code{identity}です。
比較対象の値は2引数の手続き@var{compare}で比較されます。
@var{compare}のデフォルトは@code{<}です。コレクション中の要素数が
1つ以下の場合は@var{compare}は呼ばれません。

コレクションが空の場合は、@var{default}で指定した値が返されます。
@var{default}のデフォルト値は@code{#f}です。
@c COMMON

@example
(find-min '((a . 3) (b . 9) (c . -1) (d . 7)) :key cdr) @result{} (c . -1)
@end example
@end deffn

@deffn {Generic function} find-min&max coll :key key compare default default-min default-max
@c MOD gauche.collection
@c EN
Does @code{find-min} and @code{find-max} simultaneously, and returns
two values, the minimum element and the maximum element.
The keyword arguments @var{key}, @var{compare}, and @var{default} are
the same as @code{find-min} and @code{find-max}.  Alternatively
you can give default values for minimum and maximum separately,
by @var{default-min} and @var{default-max}.
@c JP
@code{find-min}と@code{find-max}の動作を同時に行い、
最小と最大の要素をふたつの値として返します。
キーワード引数@var{key}、@var{compare}、@var{default}の意味は
@code{find-min}、@code{find-max}と同じです。
また、@var{default-min}と@var{default-max}を使って
最小要素と最大要素のデフォルト値を別々に指定することもできます。
@c COMMON
@end deffn

@deffn {Generic function} filter pred coll
@c MOD gauche.collection
@c EN
Returns a list of elements of collection @var{coll} that satisfies
the predicate @var{pred}.   If the collection is a sequence,
the order is preserved in the result.
@c JP
コレクション@var{coll}中の要素のうち、述語手続き@var{pred}が真の値を返したものの
リストを返します。コレクションがシーケンスであれば、結果の要素の順序は元のシーケンスの
順序と同じになります。
@c COMMON

@example
(filter char-upper-case? "Hello, World")
  @result{} (#\H #\W)
(filter even? '#(1 2 3 4)) @result{} (2 4)
@end example
@end deffn

@deffn {Generic function} filter-to class pred coll
@c MOD gauche.collection
@c EN
Same as @code{filter}, but the result is returned
as a collection of class @var{class}.
@c JP
@code{filter}と同じですが、結果のコレクションが@var{class}のインスタンスで
返されます。
@c COMMON

@example
(filter-to <vector> even? '#(1 2 3 4)) @result{} #(2 4)
(filter-to <string> char-upper-case? "Hello, World")
  @result{} "HW"
@end example
@end deffn

@deffn {Generic function} remove pred coll
@c MOD gauche.collection
@c EN
Returns a list of elements of collection @var{coll} that does not
satisfy the predicate @var{pred}.   If the collection is a sequence,
the order is preserved in the result.
@c JP
コレクション@var{coll}中の要素のうち、述語手続き@var{pred}が偽の値を返したものの
リストを返します。コレクションがシーケンスであれば、結果の要素の順序は元のシーケンスの
順序と同じになります。
@c COMMON

@example
(remove char-upper-case? "Hello, World")
  @result{} (#\e #\l #\l #\o #\, #\space #\o #\r #\l #\d)
(remove even? '#(1 2 3 4)) @result{} (1 3)
@end example
@end deffn

@deffn {Generic function} remove-to class pred coll
@c MOD gauche.collection
@c EN
Same as @code{remove}, but the result is returned
as a collection of class @var{class}.
@c JP
@code{remove}と同じですが、結果のコレクションが@var{class}のインスタンスで
返されます。
@c COMMON

@example
(remove-to <vector> even? '#(1 2 3 4)) @result{} #(1 3)
(remove-to <string> char-upper-case? "Hello, World")
  @result{} "ello, orld"
@end example
@end deffn

@deffn {Generic function} partition pred coll
@c MOD gauche.collection
@c EN
Does @code{filter} and @code{remove} the same time.
Returns two lists, the first consists of elements of the collection
@var{coll} that satisfies the predicate @var{pred}, and the second
consists of elements that doesn't.
@c JP
@code{filter}と@code{remove}を同時に行います。
二つのリストを返します。最初のリストはコレクション@var{coll}の要素のうち
述語手続き@var{pred}が真の値を返したものから構成され、二つ目のリストは
そうでない要素から構成されます。
@c COMMON

@example
(partition char-upper-case? "PuPu")
  @result{} (#\P #\P) @r{and} (#\u #\u)
(partition even? '#(1 2 3 4))
  @result{} (2 4) @r{and} (1 3)
@end example
@end deffn

@deffn {Generic function} partition-to class pred coll
@c MOD gauche.collection
@c EN
Same as @code{partition}, except the results are returned
in the collections of class @var{class}.
@c JP
@code{partition}と同じですが、結果がクラス@var{class}のコレクションとして
返されます。
@c COMMON

@example
(partition-to <string> char-upper-case? "PuPu")
  @result{} "PP" @r{and} "uu"
(partition-to <vector> even? '#(1 2 3 4))
  @result{} #(2 4) @r{and} #(1 3)
@end example
@end deffn

@deffn {Generic function} group-collection coll :key key test
@c MOD gauche.collection
@c EN
Generalized @code{partition}.  Groups elements in @var{coll}
into those who has the same key value, and returns the groups as
of lists.  Key values are calculated by applying the procedure @var{key}
to each element of @var{coll}.  The default value of @var{key} is
@code{identity}.   For each element of @var{coll}, @var{key} is applied
exactly once.
The equal-ness of keys are compared by
@var{test} procedure, whose default is @code{eqv?}.
@c JP
@code{partition}を汎化したものです。@var{coll}内の要素を同じキーを
持つ値同士でグループ化し、リストのリストにして返します。
キーの値は要素に手続き@var{key}を適用することで得られます。@var{key}の
デフォルト値は@code{identity}です。@var{coll}の各要素に対して、
@var{key}は正確に一回だけ呼ばれます。
キーの等価性判定には手続き@var{test}が使われます。デフォルト値は@code{eqv?}です。
@c COMMON

@c EN
If @var{coll} is a sequence, then the order of elements in each group
of the result is the same order in @var{coll}.
@c JP
@var{coll}がシーケンスである場合、結果の各グループに含まれる要素の順は
もとのシーケンス内での順と同じになります。
@c COMMON

@example
(group-collection '(1 2 3 2 3 1 2 1 2 3 2 3))
  @result{} ((1 1 1) (2 2 2 2 2) (3 3 3 3))

(group-collection '(1 2 3 2 3 1 2 1 2 3 2 3) :key odd?)
  @result{} ((1 3 3 1 1 3 3) (2 2 2 2 2))

(group-collection '(("a" 2) ("b" 5) ("c" 1) ("b" 3) ("a" 6))
  :key car :test string=?)
  @result{} ((("a" 2) ("a" 6)) (("b" 5) ("b" 3)) (("c" 1)))
@end example

@c EN
See also @code{group-sequence} in @code{gauche.sequence}
(@pxref{Other operations over sequences}),
which only groups adjacent elements.
@c JP
@code{gauche.sequence}の@code{group-sequence}も参照して下さい
(@ref{Other operations over sequences}参照)。
隣り合う要素同士でグループ化するものです。
@c COMMON
@end deffn

@deffn {Generic function} group-collection->alist coll :key key value test
@c MOD gauche.collection
@c EN
Similar to @code{group-collection}, but returns the result as an assoc
list keyed by extracted keys of comparison.  It's eaiser to see the example:
@c JP
@code{group-collection}に似ていますが、結果を比較に使ったキーでまとめた
連想リストにして返します。例を見るのがわかりやすいでしょう。
@c COMMON

@example
(group-collection->alist '((3 "a") (2 "b") (1 "c") (3 "d") (1 "e"))
                         :key car :value cadr)
  @result{} ((3 "a" "d") (2 "b") (1 "c" "e"))

;; Compare with this
(group-collection '((3 "a") (2 "b") (1 "c") (3 "d") (1 "e"))
                  :key car)
  @result{} (((3 "a") (3 "d")) ((2 "b")) ((1 "c") (1 "e")))
@end example

@c EN
First, elements in the collection is grouped with the common keys.
Then, a pair @code{(cons @var{key} (map value-proc @var{elements}))}
is computed, where @code{value-proc} is the value extraction procedure
passed by the @var{value} keyword argument.  List of those pairs is returned.

If omitted, @var{key} and @var{value} arguments are assumed to be
@code{identity}, and @var{test} argument (used to compare keys)
is assumed to be @code{eqv?}.

If the collection is ordered, the order of the alist is the same
as the order the first element with each key appears in the collection,
and within each alist entry, the values are the same order of appearance
in the collection.
@c JP
まず、コレクション中で共通のキーを持つ要素がグループにまとめられます。
次に各グループについて@code{(cons @var{key} (map value-proc @var{elements}))}
が計算され、そのリストが結果となります。ここで@code{value-proc}はキーワード引数
@var{value}で渡した値抽出手続きです。

キーワード引数@var{key}および@var{value}の省略時の値は@code{identity}、
キーの比較に使われる@var{test}の省略時の値は@code{eqv?}です。
@c COMMON
@end deffn

@deffn {Generic function} group-by-size coll k :optional padding
@deffnx {Generic function} group-by-size-to class coll k :optional padding
@c MOD gauche.collection
@c EN
Rerurns a list of ``groups'', where a ``group'' is a list
(or a collection of @var{class}) consisting of
@var{k} items from the collection @var{coll}.
This can be considered as a generalized version of @code{slices} for lists
(@pxref{List accessors and modifiers}).

If the number of elements of @var{coll}
isn't multiples of @var{k}, the last group
may have less elements than @var{k} if @var{padding} is not given
If @var{padding} is given, however, it is added to make the size of
the last group to be @var{k}.

Internally, the default method calls @code{ggroup} of @code{gauche.generator}
(@pxref{Generator operations}).  So if @var{coll} is a sequence,
it is guaranteed to take every @var{k} elements from the beginning.
@c JP
@var{coll}の要素を@var{k}個づつの「グループ」に分割してそのリストを返します。
各グループは要素のリストか、@var{class}クラスのコレクションです。
これはリストに対する@code{slices}の一般化と考えることもできます
(@ref{List accessors and modifiers}参照)。

@var{coll}の要素数が@var{k}の倍数でない場合、@var{padding}与えられていなければ
最後のグループは@var{k}個より少ない要素を持ちますが、
@var{padding}が与えられていればそれが@var{k}個になるまで足されます。

デフォルトメソッドは内部的に@code{gauche.generator}の@code{ggroup}を
使っています(@ref{Generator operations}参照)。
特に、@var{coll}がシーケンスであれば、最初から順に要素が取られることは
保証されます。
@c COMMON

@example
(group-by-size '#(a b c d e f g) 3)
 @result{} ((a b c) (d e f) (g))
(group-by-size-to <string> "abracadabra" 5)
 @result{} ("abrac" "adabr" "a")
(group-by-size-to <string> "abracadabra" 5 #\X)
 @result{} ("abrac" "adabr" "aXXXX")
@end example
@end deffn


@node Miscellaneous operations on collection, Fundamental iterator creators, Selection and searching in collection, Collection framework
@subsection Miscellaneous operations on collection
@c NODE コレクションに対する様々な操作

@deffn {Generic function} size-of coll
@c MOD gauche.collection
@c EN
Returns the number of elements in the collection.  Default method iterates over
the collection to calculate the size, which is not very efficient
and may diverge if the collection is infinite.
Some collection classes overload the method for faster calculation.
@c JP
コレクションの要素数を返します。
デフォルトのメソッドは、コレクション中の要素をすべて数え上げるものですが、
あまり効率は良くないでしょう。また、無限個の要素を持つコレクションでは
帰ってきません。多くのコレクションクラスはより効率の良い方法でこのメソッドを定義しています。
@c COMMON
@end deffn

@deffn {Generic function} lazy-size-of coll
@c MOD gauche.collection
@c EN
Returns either the size of the collection, or a promise to
calculate it.  The intent of this method is to avoid
size calculation if it is expensive.  In some cases, the caller
wants to have size just for optimization, and it is not desirable
to spend time to calculate the size.  Such caller uses this method
and just discards the information if it is a promise.
@c JP
コレクションの要素数か、もしくはそれを計算するプロミスを返します。
このメソッドの目的は、要素数の計算が高価な場合にそれを避けることにあります。
しばしば、呼び出し側では最適化のための参考値として要素数が欲しい場合があり、
そういった場合は要素数を計算するために時間を費すのは望ましくありません。
このメソッドを代わりに呼び出して、結果がプロミスであればそれを使わない、
という選択ができます。
@c COMMON
@end deffn

@deffn {Generic function} coerce-to class coll
@c MOD gauche.collection
@c EN
Convert a collection @var{coll} to another collection
which is an instance of @var{class}.
If @var{coll} is a sequence and @var{class} is a sequence class,
the order is preserved.
@c JP
コレクション@var{coll}を、クラス@var{class}のインスタンスである
別のコレクションへと変換します。@var{coll}がシーケンスであり、
@var{class}がシーケンスクラスであれば、元のシーケンスの順序は保存されます。
@c COMMON

@example
(coerce-to <vector> '(1 2 3 4))
  @result{} #(1 2 3 4)

(coerce-to <string> '#(#\a #\b #\c))
  @result{} "abc"
@end example
@end deffn

@node Fundamental iterator creators, Implementing collections, Miscellaneous operations on collection, Collection framework
@subsection Fundamental iterator creators
@c NODE 基礎的なイテレータ構築メソッド

@c EN
These are fundamental methods on which all the rest of
iterative method are built.  The method interface is not intended
to be called from general code, but suitable for building
other iterator construct.   The reason why I chose this interface
as fundamental methods are explained at the bottom of this subsection.
@c JP
ここに挙げるメソッドは、他のコレクションメソッドの基礎となるものです。
メソッドのインタフェースは一般のコードで使われることよりも、
効率良く他の繰り返しメソッドを記述するのに便利なように設計されています。
何故このインタフェースを基礎のメソッドとして選んだかについてはこの章の最後に説明します。
@c COMMON

@deffn {Generic function} call-with-iterator collection proc :key start
@c MOD gauche.collection
@c EN
A fundamental iterator creator.   This creates two procedures
from @var{collection}, both take no argument, and then call
@var{proc} with those two procedures.   The first procedure is
terminate predicate, which returns @code{#t} if the iteration
is exhausted, or @code{#f} if there are still elements to be visited.
The second procedure is an incrementer,
which returns one element from the collection and sets the
internal pointer to the next element.
The behavior is undefined if you call the incrementer after
the terminate predicate returns @code{#t}.
@c JP
基礎となるイテレータ構築メソッドです。このメソッドはコレクション@var{collection}
から繰り返しのための二つの手続きを作成し、それらを引数として手続き@var{proc}を
呼びます。作られる最初の手続きは終了判定手続きで、引数無しで呼び出され、繰り返しが
終了していれば@code{#t}を、まだ要素が残っていれば@code{#f}を返します。
作られる二番目の手続きはインクリメント手続きで、呼ばれる度に現在の要素を返し、
内部のポインタを次の要素へと進めます。終了判定手続きが@code{#t}を返した後に
インクリメント手続きを呼んだ場合の動作は未定義です。
@c COMMON

@c EN
If the collection is actually a sequence, the incrementer is guaranteed
to return elements in order, from 0-th element to the last element.
If a keyword argument @var{start} is given, however, the iteration
begins from @var{start}-th element and ends at the last element.
If the collection is not a sequence, the iteration order is
arbitrary, and @var{start} argument has no effect.
@c JP
コレクションがシーケンスでもある場合、インクリメント手続きはシーケンスの順番に要素を取り出します。
キーワード引数@var{start}が与えられていればイテレーションの範囲は
@var{start}番目の要素から最後の要素までとなります。シーケンスでないコレクションに
対しては@var{start}引数は意味を持ちません。
@c COMMON

@c EN
An implementation of @var{call-with-iterator} method may
limit the extent of the iterator inside the dynamic scope of the method.
For example, it allocates some resource (e.g. connect to a database)
before calling @var{proc}, and deallocates it (e.g. disconnect from a database)
after @var{proc} returns.
@c JP
@var{call-with-iterator}のメソッド実装は、イテレータのエクステントを
そのメソッドのダイナミックスコープ内に限ることを許されます。例えば、
メソッドは@var{proc}を呼ぶ前に何らかのリソースを確保し(データベースへのコネクションなど)、
@var{proc}から戻った後でそれを解放するということができます。
@c COMMON

@c EN
This method returns the value(s) @var{proc} returns.
@c JP
このメソッドは @var{proc} が返した値をそのまま返します。
@c COMMON

@example
(call-with-iterator '(1 2 3 4 5)
  (lambda (end? next)
    (do ((odd-nums 0))
        ((end?) odd-nums)
      (when (odd? (next)) (inc! odd-nums)))))
 @result{} 3
@end example

@c EN
See also @code{with-iterator} macro below, for it is easier to use.
@c JP
下に示す@code{with-iterator}マクロも参照してください。
@c COMMON
@end deffn

@defmac with-iterator (collection end? next args @dots{}) body @dots{}
@c MOD gauche.collection
@c EN
A convenience macro to call @code{call-with-iterator}.
@c JP
@code{call-with-iterator}を簡潔に呼び出すマクロです。
@c COMMON
@example
(with-iterator (coll end? next args @dots{}) body @dots{})
 @equiv{}
(call-with-iterator coll
  (lambda (end? next) body @dots{})
   args @dots{})
@end example
@end defmac

@defun call-with-iterators collections proc
@c MOD gauche.collection
@c EN
A helper function to write n-ary iterator method.
This function applies @code{call-with-iterator} for each @var{collection}s,
and makes two lists, the first consists of terminate predicates
and the second of incrementers.  Then @var{proc} is called
with those two lists.  Returns whatever @var{proc} returns.
@c JP
N-aryのイテレータメソッドを書くのに便利な手続きです。
この手続きはコレクションのリスト@var{collections}の各コレクションに対して
@code{call-with-iterator}を呼び、二つのリストを作ります。最初のリストには
終了判定手続きが順に集められており、二つ目のリストにはインクリメント手続きが
順に集められています。そして、これらのリストを引数として@var{proc}を呼び出します。
@var{proc}が返した値を返します。
@c COMMON
@end defun

@deffn {Generic function} call-with-builder collection-class proc :key size
@c MOD gauche.collection
@c EN
A fundamental builder creator.  Builder is a way to construct
a collection incrementally.  Not all collection classes provide
this method.
@c JP
基礎的なビルダー構築メソッドです。ビルダーはコレクションをインクリメンタルに
作成する方法です。コレクションクラスによってはこの手続きを提供しないものもあります。
@c COMMON

@c EN
@var{Collection-class} is a class of the collection to be built.
This method creates two procedures, adder and getter, then calls
@var{proc} with those procedures.
Adder procedure takes one argument and adds it to the collection
being built.  Getter takes no argument and returns a built collection object.
The effect is undefined if adder is called after getter is called.
@c JP
@var{Collection-class}は作成されるコレクションのクラスです。
このメソッドは、追加手続きと結果手続きの二つの手続きを作成し、それらを
引数として@var{proc}を呼びます。追加手続きは一つ引数を取り、それを作成中の
コレクションに追加します。結果手続きは引数を取らず、作成されたコレクションを返します。
結果手続きが呼ばれた後で追加手続きを呼んだ場合の動作は未定義です。
@c COMMON

@c EN
A keyword argument @var{size} may be specified if the size of
the result collection is known.  Certain collections may be
built much more efficiently if the size is known; other collections
may just ignore it.   The behavior is undefined if more than
@var{size} elements are added, or the collection is retrieved before
@var{size} elements are accumulated.
@c JP
作られるコレクションのサイズが分かっている場合、キーワード引数@var{size}を与える
ことができます。コレクションクラスによってはその情報を使って効率的にコレクションを
作成することができます。その情報を単に無視するコレクションクラスもあります。
@var{size}個より多くの要素が追加されたり、@var{size}個の要素が追加される前に
結果手続きが呼ばれたりした場合の動作は未定義です。
@c COMMON

@c EN
If the collection class is actually a sequence class,
adder is guaranteed to add elements in order.  Otherwise,
the order of elements are insignificant.
@c JP
コレクションクラスがシーケンスクラスであった場合、追加手続きは要素を
シーケンスの順に追加してゆきます。
@c COMMON

@c EN
Some collection class may take more keyword arguments to
initialize the collection.
@c JP
コレクションクラスによっては、コレクションオブジェクトの初期化のために
他のキーワード引数を取るかもしれません。
@c COMMON

@c EN
This method returns the value(s) @var{proc} returned.
@c JP
このメソッドは@var{proc}が返す値を返します。
@c COMMON

@example
(call-with-builder <list>
  (lambda (add! get)
    (add! 'a) (add! 'b) (add! 'c) (get)))
 @result{} (a b c)

(call-with-builder <vector>
  (lambda (add! get)
    (add! 'a) (add! 'b) (add! 'c) (get)))
 @result{} #(a b c)
@end example

@c EN
See also @code{with-builder} macro below, for it is much easier to use.
@c JP
下に示す@code{with-builder}マクロも参照してください。
@c COMMON
@end deffn

@defmac with-builder (collection add! get args @dots{}) body @dots{}
@c MOD gauche.collection
@c EN
A convenience macro to call @code{call-with-builder}.
@c JP
@code{call-with-builder}を簡潔に呼び出すマクロです。
@c COMMON
@example
(with-builder (coll add! get args @dots{}) body @dots{})
 @equiv{}
(call-with-builder coll
  (lambda (add! get) body @dots{})
  args @dots{})
@end example
@end defmac

@emph{Discussion}:
@c EN
Other iterator methods are built on top of call-with-iterator and
call-with-builder.
By implementing those methods, you can easily adapt your own collection
class to all of those iterative
operations.   Optionally you can overload some of higher-level
methods for efficiency.
@c JP
他のイテレータメソッドは全てこのcall-with-iteratorとcall-with-builderの上に構築可能です。
最低限これらのメソッドを定義すれば、そのクラスはコレクションとして振舞うことができます。
もちろん最適化のために他のイテレータメソッドを定義しても構いませんが。
@c COMMON

@c EN
It is debatable that which set of operations should be primitives.
I chose call-with-iterator style for efficiency of the applications
I see most.   The following is a discussion of other possible
primitive iterators.
@c JP
どの操作を基礎的なメソッドとするかには議論の余地があります。
Gaucheでは、作者がよく見るパターンで最も効率が良くなるように考えて現在のスタイルを
選びました。以下に、他の基礎的なメソッドの可能性を検討します。
@c COMMON

@table @asis
@item @code{fold}
@c EN
It is possible to make @code{fold} a primitive method, and
build other iterator method on top of it.
Collection-specific iterating states can be kept in the
stack of @code{fold}, thus it runs efficiently.  The method
to optimize a procedure that uses @code{fold} as a basic
iterator construct.
However, it is rather cumbersome to derive
generator-style interface from it.   It is also tricky
to iterate irregularly over more than one collections.
@c JP
@code{fold}を最も基礎的なメソッドとして、他のイテレータメソッドをその上に
構築することも可能です。繰り返しの状態はスタックに置かれるので効率良く走ります。
@code{fold}を基礎とした繰り返し関数を最適化する方法は良く知られています。
しかし、@code{fold}を元にしてジェネレータスタイルのインタフェースを
作成するのは複雑です。また、複数のコレクションに対しての繰り返しを書くのも
面倒です。
@c COMMON

@item CPS
@c EN
Passes iteratee the continuation procedure that continues
the iteration.   The iteratee just returns when it want
to terminate the iteration.
It has resource management problem described in
Oleg Kiselyov's article (@uref{http://okmij.org/ftp/Scheme/enumerators-callcc.html}).
@c JP
繰り返しの中身の手続きに対し、繰り返しを続けるための継続手続きを渡す方法です。
繰り返しを続けたくなければ、手続きは継続を呼ばすにそのまま戻ります。
Oleg Kiselyovの記事(@uref{http://okmij.org/ftp/Scheme/enumerators-callcc.html})に指摘されているような、
リソース管理の問題があります。
@c COMMON

@item Iterator object
@c EN
Like C++ iterator or Common Lisp generator.
Easy to write loop.   The problem is that every call of
checking termination or getting next element must be dispatched.
@c JP
C++のイテレータやCommon Lispのジェネレータのようなオブジェクトを使う方法です。
ループを書くのは容易ですが、終了判定や要素取り出しの度にメソッドディスパッチが
起こってしまいます。
@c COMMON

@item Series
@c EN
Common Lisp's series can be very efficient if the compiler can statically
analyze the usage of series.  Unfortunately it is not the case in
Gauche.  Even if it could, the extension mechanism doesn't blend well
with Gauche's object system.
@c JP
Common Lispのシリーズはコンパイラがシリーズの使われかたを追跡できれば
非常に効率の良いコードに変換できます。Gaucheのコンパイラはそこまでのデータフロー解析を
行っていません。また、それをやったとしても、コレクションクラスを拡張するための方法が
Gaucheのオブジェクトシステムとはうまく調和しません。
@c COMMON

@item Macros
@c EN
Iterator can be implemented as macros, and that will be very efficient;
e.g. Scheme48's iterator macro.  It uses macros to extend, however,
and that doesn't blend well with Gauche's object system.
@c JP
効率を気にするなら、イテレータをマクロで書いてしまう方法もあります
(例えばScheme48の@code{iterator}マクロなど)。
効率は良いのですが、拡張するにはマクロを書くことが必要となり、
Gaucheのオブジェクトシステムとうまく調和しません。
@c COMMON
@end table

@c EN
The current implementation is close to the iterator object approach,
but using closures instead of iterator objects so that avoiding
dispatching in the inner loop.  Also it allows the iterator
implementor to take care of the resource problem.
@c JP
現在の実装はイテレータオブジェクトアプローチに近いですが、イテレータオブジェクトを
作る代わりにクロージャを使うことで内部のループでのメソッドディスパッチを
避けています。また、現在のインタフェースはリソース管理の問題を解決しています。
@c COMMON

@node Implementing collections,  , Fundamental iterator creators, Collection framework
@subsection Implementing collections
@c NODE コレクションの実装

@c EN
The minimum requirements of the collection class implementation
is as follow:
@itemize @bullet
@item
The class inherits @code{<collection>} abstract class.
@item
A method @code{call-with-iterator} is implemented.
@end itemize

This makes iterator methods such as @code{map}, @code{for-each},
@code{find} and @code{filter} to work.
@c JP
コレクションクラスの実装に最低限要求されるものには、以下のものがあります。
@itemize @bullet
@item
抽象クラス@code{<collection>}を継承している。
@item
メソッド@code{call-with-iterator}が実装されている。
@end itemize

これにより、@code{map}、@code{for-each}、@code{find}、@code{filter}などの
イテレータメソッドが動作するようになります。
@c COMMON

@c EN
Optionally, you can specialize other generic functions to optimize
performance.  Particularly, we strongly recommend to specialize
@code{size-of}, since its default method iterates entire collection
to find the size, which is O(N).  Usually a collection has bette way
to find out its size.
@c JP
パフォーマンスの最適化のために、他のジェネリック関数をオーバロードすることも
できます。特に、@code{size-of}のメソッドは定義しておくことを強くおすすめします。
デフォルトのメソッドはコレクション全体をなめて大きさを計算するのでO(N)かかりますが、
通常、コレクションは大きさをもっと簡単に得られる手段を持っています。
@c COMMON



@c EN
In order to make the constructive methods (e.g. @code{map-to} to
create your collection), you have to implement @code{call-with-builder}
method as well.  Note that @code{call-with-builder} method must work
a sort of class method, dispatched by class, rather than normal method
dispatched by instance.   In Gauche, you can implement it by using a
metaclass.   Then the minimal code will look like this:
@c JP
建設的なメソッド(例えば、コレクションを作るための@code{map-to}など)を
作るためには、メソッド@code{call-with-builder}も実装しなければなりません。
メソッド@code{call-with-builder}は、クラスによりディスパッチされるクラスメソッドの
一種で、インスタンスによりディスパッチされる通常のメソッドとは異なります。
Gaucheでは、これはメタクラスを使うことによって実装できます。
最小限のコードは次のようになります。
@c COMMON

@example
(define-class <your-collection-meta> (<class>) ())

(define-class <your-collection> (<collection>)
 (...) ;; @r{slots}
 :metaclass <your-collection-meta>)

(define-method call-with-iterator
    ((coll <your-collection>) proc . options)
  @dots{}
  )

(define-method call-with-builder
     ((coll <your-collection-meta>) proc . options)
  @dots{}
  )
@end example


@c ----------------------------------------------------------------------
@node Configuration parameters, Generating build files, Collection framework, Library modules - Gauche extensions
@section @code{gauche.config} - Configuration parameters
@c NODE コンフィグレーション情報, @code{gauche.config} - コンフィグレーション情報

@deftp {Module} gauche.config
@mdindex gauche.config
@c EN
This module allows the Scheme program to access the configuration information
the same as you can get from the @code{gauche-config} program.
@c JP
このモジュールは、@code{gauche-config} プログラム経由で得られるのと
同等の情報をSchemeプログラムから取得すること可能にします。
@c COMMON
@end deftp

@defun gauche-config option
@c MOD gauche.config
@c EN
Returns the configured value of the @var{option}.

See the manual page of @code{gauche-config}
(@pxref{Command to query configuration}), or run @code{gauche-config}
without any argument from the shell, to find out the valid options.
@c JP
@var{option}に対応するコンフィグレーション値を返します。

有効なオプションについては、@code{gauche-config} のマニュアルページ(@ref{Command to query configuration})を見るか、
シェルで @code{gauche-config} を引数なしで実行して下さい。
@c COMMON
@example
(gauche-config "--cc")
  @result{} "gcc"
(gauche-config "-L")
  @result{} "-L/usr/lib/gauche/0.6.5/i686-pc-linux-gnu"
(gauche-config "-l")
  @result{} "-ldl -lcrypt -lm -lpthread"
@end example
@end defun

@c ----------------------------------------------------------------------
@node Generating build files, Connection framework, Configuration parameters, Library modules - Gauche extensions
@section @code{gauche.configure} - Generating build files
@c NODE ビルド用ファイルの生成, @code{gauche.configure} - ビルド用ファイルの生成

@deftp {Module} gauche.configure
@mdindex gauche.configure
@c EN
This is a utility library to write a @file{configure} script.
It is used to check the system properties and generates build files
(usually @file{Makefile}) from templates.
@c JP
このモジュールは@file{configure}スクリプトを書くためのユーティリティライブラリです。
@file{configure}スクリプトはシステムの属性をチェックして、
ビルド用のファイル(通常は@file{makefile})をテンプレートから生成します。
@c COMMON

@c EN
The primary purpose is to replace autoconf-generated
@file{configure} shell scripts
in Gauche extension packages.
@c JP
主な目的は、Gauche拡張パッケージにおいて、autoconfが生成する
@file{configure}シェルスクリプトを置き換えることです。
@c COMMON

@c EN
The advantage of using autoconf is that it generates
a script that runs on most vanilla unix variants, for it only uses minimal
shell features and basic unix commands.
However, when you configure Gauche extension,
you sure have Gauche already, so you don't need to limit
yourself with minimal environment.
@c JP
autoconfを使う利点は、生成されるスクリプトが最小限のシェル機能と基本的なunixコマンドにしか
依存しないため、ほとんど何も入れないunix上でも実行できることです。
けれども、Gauche拡張パッケージをビルドする時には、
既にGaucheはインストールされているわけですから、これを使わない手はありません。
@c COMMON

@c EN
Writing a @file{configure} script directly in Gauche means developers
don't need an extra step to generate @file{configure} before
distribution.  They can directly check-in @file{configure} in
the source repo, and anybody who pulls the source tree can
run @file{configure} at once without having autoconf.
@c JP
@file{configure}スクリプトがGaucheで直接書ければ、配布前に
@file{configure}スクリプトを生成するという余分な手間が省けます。
@file{configure}スクリプト自体をリポジトリにチェックインしておけますし、
誰でもソースツリーをチェックアウトしたら(autoconfを使わずに)すぐに
@file{configure}を実行できます。
@c COMMON

@c EN
Currently, @code{gauche.configure} only covers small subset of
autoconf, though, so if you need to write complex tests
you may have to switch back to autoconf.  We'll add tests
as needed.
@c JP
ただ、今のところ@code{gauche.configure}はautoconfの機能の小さなサブセット
しかカバーしないので、複雑な機能テストが必要ならautoconfに戻らなければ
ならない場合もあります。必要に応じて機能テストを足して行く予定です。
@c COMMON
@end deftp

@c EN
The core feature of @code{gauche.configure} is the ability to generate files
(e.g. @file{Makefile}) from templates (e.g. @file{Makefile.in}) with replacing
parameters.  We follow autoconf convention, so the substitution parameters
in a template is written like @code{@@VAR@@}.  You should be able
to reuse @file{Makefile.in} used for autoconf without changing them.
@c JP
@code{gauche.configure}のコアとなる機能は、テンプレート(例: @file{Makefile.in})
から、@code{@@VAR@@}のように書かれたパラメータを置換して
ファイル(例: @file{Makefile})を生成することです。
autoconf用に書いた@file{Makefile.in}はそのまま流用できるはずです。
@c COMMON

@c EN
The API corresponds to autoconf's @code{AC_*} macros, while we use
@code{cf-} prefix instead.
@c JP
autoconfの@code{AC_*}マクロに対応する機能は、プレフィクスを@code{cf-}に置き換えた
名前で提供されています。
@c COMMON

@menu
* Structure of configure script::
* Configure API::
@end menu

@node Structure of configure script, Configure API, Generating build files, Generating build files
@subsection Structure of configure script and build files
@c NODE configureスクリプトの構成とビルドファイル

@c EN
A @file{configure} script tests
running system's properties to determine values of
substitution parameters, then read one or more template build files,
and write out one output build file for each, replacing
substitution parameters for the assigned values.
@c JP
@file{configure}スクリプトは、それを実行しているシステムの特性を調べて
置換パラメータの値を決定し、ビルドファイルのテンプレート中の置換パラメータを
値に書き換えてビルドファイルを生成します。
@c COMMON

@c EN
By convention, a template file has a suffix @code{.in}, and
the corresponding output file is named without the suffix.
For example, @code{Makefile.in} is a template that generates
@code{Makefile}.
@c JP
通常、テンプレートファイルにはサフィックス@code{.in}がつけられ、
対応する出力ファイルはそのサフィックスが除かれたものになります。
例えば@code{Makefile.in}は@code{Makefile}を生成するテンプレートです。
@c COMMON

@c EN
Templates may contain substitution parameters, noted @code{@@PARAMETER_NAME@@}.
This is a fragment of a typical Makefile template:
@c JP
テンプレートファイル中には@code{@@PARAMETER_NAME@@}という形式の
置換パラメータを含めることができます。以下は典型的なMakefileのテンプレートです。
@c COMMON

@example
GAUCHE_PACKAGE = "@@GAUCHE_PACKAGE@@"
SOEXT          = @@SOEXT@@
LOCAL_PATHS    = "@@LOCAL_PATHS@@"

foo.$(SOEXT): $(foo_SRCS)
        $(GAUCHE_PACKAGE) compile \
          --local=$(LOCAL_PATHS) --verbose foo $(foo_SRCS)
@end example

@c EN
When processed by @code{configure}, @code{@@GAUCHE_PACKAGE@@},
@code{@@SOEXT@@} and @code{@@LOCAL_PATHS@@} are replaced
with appropriate values.   If you know autoconf, you are already
familiar with this.
@c JP
@code{configure}がこのテンプレートを処理する際に、@code{@@GAUCHE_PACKAGE@@}、
@code{@@SOEXT@@}、@code{@@LOCAL_PATHS@@}はそれぞれ適切な値に
置換されます。autoconfを知っている読者には馴染み深い動作でしょう。
@c COMMON

@c EN
The Gauche configure script is structurally similar to autoconf's
@code{configure.in}, but you can use full power of Scheme.
The following is the minimal configure script:
@c JP
Gaucheのconfigureスクリプトはautoconfの@code{configure.in}と
似たような構造をとりますが、フルセットのSchemeの力を使うことができます。
次は最小のconfigureスクリプトです:
@c COMMON

@example
#!/usr/bin/env gosh
(use gauche.configure)
(cf-init-gauche-extension)
(cf-output-default)
@end example

@c EN
This script does several common tasks.
@c JP
このスクリプトはいくつかの共通タスクを行います。
@c EN
The @code{cf-init-gauche-extension} does the following:
@c JP
@code{cf-init-gauche-extension}の仕事は以下のとおりです。
@c COMMON

@itemize @bullet
@item
@c EN
First, it handles command-line arguments given to @file{configure}.
In the default settings, it recognizes standard configure
arguments such as @code{--prefix}, and
@code{--with-local=PATH:PATH:...}
which adds @code{PATH/include}s and @code{PATH/lib}s to
the header and library search paths.
You can handle more arguments by adding
@code{cf-arg-with} and @code{cf-arg-enable} before
@code{cf-init-gauche-extension}.
@c JP
まず、@file{configure}スクリプトに渡されたコマンドライン引数が処理されます。
デフォルトの設定では、@code{--prefix}のようなconfigure標準の引数および、
@code{--with-local=PATH:PATH:...}が認識されます。後者は
@code{PATH/include}と@code{PATH/lib}をそれぞれヘッダとライブラリサーチパスに
追加するものです。@code{cf-arg-with}や@code{cf-arg-enable}を
@code{cf-init-gauche-extension}に使うことで、処理する引数を追加できます。
@c COMMON
@item
@c EN
Then it reads @code{package.scm}.  Package name and version are taken
from it.  Dependencies are also checked.
@c JP
次に@code{package.scm}が読み込まれます。
パッケージの名前とバージョンはそこから取られます。
依存関係のチェックも行われます。
@c COMMON
@item
@c EN
It sets up global environment to run other configure checks.
@c JP
configureのチェックのためのグローバルな環境が準備されます。
@c COMMON
@item
@c EN
It sets up default values for standard substitution parameters such as
@code{@@prefix@@}.
@c JP
@code{@@prefix@@}などの標準の置換パラメータのデフォルト値が設定されます。
@c COMMON
@end itemize

@c EN
And @code{cf-output-default} does the following:
@c JP
@code{cf-output-default}は次の処理を行います。
@c COMMON

@itemize
@item
@c EN
Generate gpd (Gauche package description) file.
@c JP
gpd (Gauche package description) ファイルを生成します。
@c COMMON
@item
@c EN
Writes package version to @code{VERSION} file.
@c JP
パッケージのバージョンを@code{VERSION}ファイルに書き出します。
@c COMMON
@item
@c EN
Scan @code{Makefile.in}'s in the source directory and its subdirectories,
and process them
to generate @code{Makefile}s.
@c JP
ソースディレクトリ以下にある@code{Makefile.in}を処理して@code{Makefile}を書き出します。
@c COMMON
@c EN
If config header files (typically @code{config.h}) are specified by
@code{cf-config-headers}, process input files
(e.g. @code{config.h.in}) to generate the header files.
@c JP
もしconfigヘッダファイル(通常@code{config.h})が@code{cf-config-headers}により
指定されていたなら、入力(通常@code{config.h.in})を処理してヘッダファイルを
生成します。
@c COMMON
@end itemize

@c EN
In general, a @code{configure} script consists of the following parts:
@c JP
一般的に、@code{configure}スクリプトは以下のようなパーツから構成されます:
@c COMMON

@enumerate
@item
@c EN
Extra argument declarations (optional): Declare @code{--with-PACKAGE}
and/or @code{--enable-FEATURE} options you want to handle, by
@code{cf-with-arg} and @code{cf-enable-arg}, respectively.
@c JP
追加の引数の宣言(省略可): @code{--with-PACKAGE}や@code{--enable-FEATURE}で
処理すべきオプションを、それぞれ@code{cf-with-arg}と@code{cf-enable-arg}で
宣言します。
@c COMMON
@item
@c EN
Initialization.  Call to @code{cf-init} or @code{cf-init-gauche-extension}
sets up global context and
parses command-line arguments passed to @code{configure}.
It also process package metainformation in @file{package.scm}, if it exists.
@c JP
初期化。@code{cf-init}か@code{cf-init-gauche-extension}を呼ぶと、
グローバルなコンテキストが設定され、
@code{configure}に与えられた引数がパーズされます。また、
@file{package.scm}が存在していれば、そこからパッケージメタ情報が読み込まれます。
@c COMMON
@item
@c EN
Tests and other substitution parameter settings (optional): Check system
characteristics and sets up substitution parameters and/or
C preprocessor definitions.
@c JP
テストと置換パラメータの設定 (省略可): システムの特性を調べ、
置換すべきパラメータやCプリプロセッサ定義の値を設定します。
@c COMMON
@item
@c EN
Output generation.  Call @code{cf-output} or @code{cf-output-default}
to process template files.
@c JP
出力の生成。@code{cf-output}か@code{cf-output-default}を呼び出し、
テンプレートファイルを処理します。
@c COMMON
@end enumerate

@c EN
Most @code{cf-*} API corresponds to autoconf's @code{AC_*} or
@code{AS_*} macros.   We need argument declarations
before @code{cf-init} so that it can generate help message
including custom arguments in one pass.
@c JP
多くの@code{cf-*} APIは、autoconfの@code{AC_*}もしくは@code{AS_*}マクロに
対応しています。引数の宣言が@code{cf-init}より前になされなければならないのは、
1パスで@code{cf-init}がカスタム引数の説明を含んだヘルプメッセージを
生成する必要があるからです。
@c COMMON

@node Configure API,  , Structure of configure script, Generating build files
@subsection Configure API

@c EN
@subsubheading Initialization
@c JP
@subsubheading 初期化
@c COMMON

@defun cf-init-gauche-extension
@c MOD gauche.configure
@c EN
This is a convenience API that packages several boilerplate @code{cf-*}
function calls in one call.  This must be called exactly once in a
configure script.
@c JP
これはいくつかの定形の@code{cf-*}呼び出しをひとつにまとめた便利関数です。
configureスクリプト中で1回だけ呼び出される必要があります。
@c COMMON

@c EN
Specifically, it calls @code{cf-arg-with} to process @code{--with-local},
then calls @code{cf-init} with no arguments to initialize,
then sets the following substitution parameters:
@c JP
この関数はまず@code{cf-arg-with}関数で@code{--with-local}コマンドライン引数の
処理を登録し、次に@code{cf-init}を引数なしで呼んで初期化し、
さらに以下の置換パラメータをセットします:
@c COMMON
@table @code
@item GOSH
@c EN
Path to @code{gosh}.
@c JP
@code{gosh}へのパス
@c COMMON
@item GAUCHE_CONFIG
@c EN
Path to @code{gauche-config}.
@c JP
@code{gauche-config}へのパス
@c COMMON
@item GAUCHE_PACKAGE
@c EN
Path to @code{gauche-package}.
@c JP
@code{gauche-package}へのパス
@c COMMON
@item GAUCHE_INSTALL
@c EN
Path to @code{gauche-install}.
@c JP
@code{gauche-install}へのパス
@c COMMON
@item GAUCHE_CESCONV
@c EN
Path to @code{gauche-cesconv}.
@c JP
@code{gauche-cesconv}へのパス
@c COMMON
@item GAUCHE_PKGINCDIR
@c EN
Result of @code{gauche-config --pkgincdir}
@c JP
@code{gauche-config --pkgincdir}の結果
@c COMMON
@item GAUCHE_PKGLIBDIR
@c EN
Result of @code{gauche-config --pkglibdir}
@c JP
@code{gauche-config --pkglibdir}の結果
@c COMMON
@item GAUCHE_PKGARCHDIR
@c EN
Result of @code{gauche-config --pkgarchdir}
@c JP
@code{gauche-config --pkgarchdir}の結果
@c COMMON
@end table

@c EN
The @code{--with-local} command-line argument should take a parameter, which is
a colon-separated list of paths.  It becomes a value of substitution parameter
@code{LOCAL_PATHS}.  The default @code{Makefile.in} template passes
its value to @code{gauche-package} via the @code{--local} argument.
When the C extension is compiled and linked, the
@code{include} and @code{lib} subdirectories of the given paths are
searched for headers and libraries, respectively.
For example, if the extension requires a library foo and you install
it under @code{/opt/foo} (that is, headers in @code{/opt/foo/include}
and library objects in @code{/opt/foo/lib}), then you can pass
@code{--with-local=/opt/foo} to configure the extension.
@c JP
@code{--with-local}コマンドライン引数はコロン区切りのパス名をパラメータとして
取ります。その値は置換パラメータ@code{LOCAL_PATHS}にセットされます。
デフォルトの@code{Makefile.in}テンプレートを使っていれば、その値は
@code{gauche-package}の@code{--local}引数に渡され、
C拡張コードがコンパイル・リンクされる際のヘッダファイル、ライブラリオブジェクトが
それぞれ指定されたパス以下の@code{include}、@code{lib}サブディレクトリから探されます。
例えば拡張モジュールがfooライブラリに依存していて、あなたがそれを
@code{/opt/foo}以下にインストールしていたとしましょう(つまり、
ヘッダファイルが@code{/opt/foo/include}に、ライブラリオブジェクトが
@code{/opt/foo/lib}にあります)。その場合、
拡張モジュールをconfigureする際に@code{--with-local=/opt/foo}を渡せばうまくいきます。
@c COMMON

@c EN
If you don't like these default behavior, you can call individual
@code{cf-*} functions instead.  See @code{cf-init} below.
@c JP
デフォルトで行われるこれら余分な動作が邪魔な場合は、
この関数を使わずに個々の@code{cf-*}関数を呼び出すこともできます。
下の@code{cf-init}も参照してください。
@c COMMON
@end defun


@defun cf-init :optional package-name package-version maintainer-email homepage-url
@c MOD gauche.configure
@c EN
Initialize the configure system.  Corresponds to autoconf's @code{AC_INIT}.
This must be called once in the
configure script, before any feature-test procedures.
(If you call @code{cf-init-gauche-extension}, @code{cf-init} is called
from it.)
@c JP
configureシステムを初期化します。autoconfの@code{AC_INIT}に対応します。
これはconfigureスクリプト中で、
全ての機能テスト手続きに先立って必ず1回呼ばれなければなりません。
(@code{cf-init-gauche-extension}を呼んだ場合、その中から@code{cf-init}が
呼ばれています。)
@c COMMON

@c EN
First, it checks if a file named @file{package.scm} is
in the same directory as the configure script,
and reads the Gauche package description from it.  The package description
contains package name, version, dependencies, etc.
@xref{Package metainformation}, for the details.
@c JP
まずこの手続きは、configureスクリプトと同じディレクトリに@file{package.scm}という
ファイルがあるかどうか調べ、あればGaucheパッケージ記述をそこから読み込みます。
パッケージ記述には、パッケージ名、バージョン、依存関係などがかかれています。
詳しくは@ref{Package metainformation}を参照してください。
@c COMMON

@c EN
It then parses the command-line arguments, sets up the configure
environment, and (if @file{package.scm} defines dependencies) check
if the system has required packages.
@c JP
次にこの手続きはコマンドライン引数をパーズし、configureの環境を設定し、
(もし@file{package.scm}が依存関係を定義していれば)必要なパッケージが
既にあるかどうかもチェックします。
@c COMMON

@c EN
The optional arguments are only supported for the backward compatibility
if you don't have @file{package.scm}.  You need at least
to provide @var{package-name} and @var{package-version} to tell
what package you're configuring.  They are used as the value
of substitution parameter @code{PACKAGE_NAME} and @code{PACKAGE_VERSION}.
The other optional arguments, @var{maintainer-email} and
@var{homepage-url}, are used to initialize @code{PACKAGE_BUGREPORT} and
@code{PACKAGE_URL}.  These arguments are compatible to autoconf's
@code{AC_INIT} macro.
@c JP
省略可能引数は以前のバージョンとの互換性のためのものです。@file{package.scm}が
無い場合、少なくとも@var{package-name}と@var{package-version}を与える
必要があります。これらは置換パラメータの@code{PACKAGE_NAME}と@code{PACKAGE_VERSION}
を置換するのに使われます。他の引数@var{maintainer-email}と
@var{homepage-url}は@code{PACKAGE_BUGREPORT}と@code{PACKAGE_URL}に
使われます。これらの引数はautoconfの@code{AC_INIT}マクロと互換です。
@c COMMON

@c EN
We recommend to always use @file{package.scm} and omit all the optional
arguments, because it allows you to maintain the package metainformation
in one place.  When @file{package.scm} is read, @code{PACKAGE_BUGREPORT}
is initialized by the first entry of @code{maintainers} slot of
the package description, and @code{PACKAGE_URL} is initialized
by its @code{homepage} slot.
@xref{Package metainformation}, for description of slots of the package
description.
@c JP
推奨される呼び出し方法は、@file{package.scm}を用意し、@code{cf-init}には
引数を渡さないことです。そうすれば、パッケージのメタ情報を一ヶ所(@file{package.scm})で
管理できます。@file{package.scm}が読まれた場合、@code{PACKAGE_BUGREPORT}は
パッケージ記述の@code{maintainers}の最初のエントリで、また
@code{PACKAGE_URL}はパッケージ記述の@code{homepage}で初期化されます。
パッケージ記述についての詳細は@ref{Package metainformation}を見てください。
@c COMMON

@c EN
Note that if there's @file{package.scm} @emph{and} you provide
the optional arguments, they must match, or @code{cf-init} raises an
error.  It is to catch errors during transition in which you forgot
to update either one.
@c JP
もし@file{package.scm}が存在し、かつ@code{cf-init}に引数が与えられた場合、
それぞれ対応する情報は一致していなければなりません。一致していなかった場合、
@code{cf-init}はエラーを投げます。これは、@file{package.scm}への移行の途中で、
どちらかの情報をアップデートし忘れたケースを捕まえるためです。
@c COMMON

@c EN
This procedure sets up a bunch of standard substitution parameters
such as @code{prefix}, @code{bindir} or @code{srcdir}.   To see what
substitution parameters are set, you can call @code{cf-show-substs}
after @code{cf-init}.
@c JP
この手続きはまた、@code{prefix}、@code{bindir}あるいは@code{srcdir}といった
標準の置換パラメータをたくさん設定します。
どの置換パラメータが設定されるか見たければ、@code{cf-init}の後に
@code{cf-show-substs}を呼んでみてください。
@c COMMON
@end defun

@c EN
@subsubheading Command-line arguments
@c JP
@subsubheading コマンドライン引数
@c COMMON

@defun cf-arg-enable feature help-string :optional proc-if-given proc-if-not-given
@defunx cf-arg-with package help-string :optional proc-if-given proc-if-not-given
@c MOD gauche.configure
@c EN
Make the configure script accept feature selection argument and
package selection argument, respectively.  The corresponding
autoconf macros are @code{AC_ARG_ENABLE} and @code{AC_ARG_WITH}.
@c JP
それぞれ、configureスクリプトが、機能選択引数およびパッケージ選択引数を認識するようにします。
autoconfでの対応するマクロは@code{AC_ARG_ENABLE}と@code{AC_ARG_WITH}です。
@c COMMON

@c EN
Those procedures must be called before calling @code{cf-init}
or @code{cf-init-gauche-extension}.
@c JP
これらの手続きは@code{cf-init}もしくは@code{cf-init-gauhce-extension}の前に
呼ばれなければなりません。
@c COMMON

@c EN
The @var{feature} and @var{package} arguments must be a symbol.
@c JP
@var{feature}と@var{package}引数はシンボルでなければなりません。
@c COMMON

@c EN
A feature selection argument is in a form of either
@code{--enable-@var{feature}=@var{val}},
@code{--enable-@var{feature}}, or @code{--disable-@var{feature}}.
The latter two are equivalent to @code{--enable-@var{feature}=yes}
and @code{--enable-@var{feature}=no}, respectively.
It is to select an optional feature provided with the package itself.
@c JP
機能選択引数は、@code{--enable-@var{feature}=@var{val}}、
@code{--enable-@var{feature}}、もしくは@code{--disable-@var{feature}}という
引数です。後のふたつはそれぞれ
@code{--enable-@var{feature}=yes}および
@code{--enable-@var{feature}=no}と同じです。
このconfigure引数は、パッケージ自体が提供しているオプショナルな機能を選択するのに使います。
@c COMMON

@c EN
A package selection argument is in a form of either
@code{--with-@var{package}=@var{val}},
@code{--with-@var{package}} and @code{--without-@var{package}}.
The latter two are equivalent to @code{--with-@var{package}=yes}
and @code{--with-@var{package}=no}, respectively.
It is to select an external software package to be used with
this package.
@c JP
パッケージ選択引数は、@code{--with-@var{package}=@var{val}}、
@code{--with-@var{package}}、もしくは@code{--without--@var{package}}という
引数です。後のふたつはそれぞれ
@code{--with-@var{package}=yes}および
@code{--with-@var{package}=no}と同じです。
このconfigure引数は、このパッケージが使う外部のパッケージを選択するのに使います。
@c COMMON

@c EN
When @code{cf-init} finds these arguments during command-line processing,
it adds entry of @var{feature}
or @var{package} to the global tables, with the value @var{val}.
Those global tables can be accessed with @code{cf-feature-ref} and
@code{cf-package-ref} procedures below.
@c JP
@code{cf-init}がコマンドライン引数処理中にこれらの形の引数を見つけた場合、
@var{feature}または@var{package}と、与えられた@var{val}をグローバルなテーブルに
保存します。このグローバルテーブルは下の@code{cf-feature-ref}および
@code{cf-package-ref}でアクセスできます。
@c COMMON

@c EN
The @var{help-string} argument must be a string and
is used as is to list the help
of the option in part of usage message displayed by
@code{configure --help}.  You can use @code{cf-help-string} below
to create a help string that fits nicely in the usage message.
@c JP
@var{help-string}は文字列で、@code{configure --help}で表示される
ヘルプメッセージに使われます。
下の@code{cf-help-string}を使ってヘルプ文字列を整形することができます。
@c COMMON

@c EN
If optional @var{proc-if-given} argument is given, it must be a procedure
that accepts one argument, @var{val}.  It is called when @code{cf-init}
finds one of those arguments.
@c JP
省略可能引数@var{proc-if-given}は、与えられたら引数をひとつ取る手続きでなければなりません。
@var{cf-init}が対応するコマンドライン引数を見つけた時に、コマンドラインで与えられた
@var{val}を引数としてこの手続きが呼ばれます。
@c COMMON

@c EN
If optional @var{proc-if-not-given} argument is given, it must be a procedure
that accepts no arguments.  It is called when @code{cf-init}
doesn't find any of those arguments.
@c JP
省略可能引数@var{proc-if-not-given}は、与えられたら引数を取らない手続きでなければなりません。
@var{cf-init}が対応するコマンドライン引数を見つけられなかった時に、
この手続きが呼ばれます。
@c COMMON

@c EN
The following is to accept @code{--with-local=@var{PATH}:@var{PATH}:@dots{}}.
(This @code{cf-arg-with} call is included in @code{cf-init-gauche-extension}).
Note that the help string (the second argument) is generated by
@code{cf-help-string} call.  The command-line parameter followed by
@code{--with-local} is passed as the argument of the procedure
in the third argument:
@c JP
下は、@code{--with-local=@var{PATH}:@var{PATH}:@dots{}}という形式の
コマンドライン引数を受け取る例です
(この@code{cf-arg-with}呼び出しは@code{cf-init-gauche-extension}に含まれています)。
ヘルプ文字列を生成するのに@code{cf-help-string}を使っているのに注目してください。
また、コマンドライン引数で与えられたオプションの値は、
3番めの引数の手続きへと渡されます。
@c COMMON

@example
(cf-arg-with 'local
             (cf-help-string
              "--with-local=PATH:PATH..."
              "For each PATH, add PATH/include to the include search
  paths and PATH/lib to the library search paths.  Useful if you have some
  libraries installed in non-standard places. ")
             (^[with-local]
               (unless (member with-local '("yes" "no" ""))
                 (cf-subst 'LOCAL_PATHS with-local)))
             (^[] (cf-subst 'LOCAL_PATHS "")))
@end example
@end defun

@defun cf-help-string item description
@c MOD gauche.configure
@c EN
Return a string formatted suitable to show as an option's help message.
The result can be passed to @var{help-string} argument of
@code{cf-arg-enable} and @code{cf-arg-with}, to ensure that
@code{configure --help} will produce a consistently formatted output.
This corresponds to autoconf's @code{AS_HELP_STRING}.

Call it as follows, and it'll indent and fill the description nicely.
@c JP
コマンドライン引数のヘルプメッセージにふさわしい形式にフォーマットした文字列を
返します。戻り値を@code{cf-arg-enable}や@code{cf-arg-with}の
@var{help-string}引数に渡すことで、
@code{configure --help}が統一的な出力を生成できます。
autoconfの@code{AS_HELP_STRING}に相当します。
@c COMMON

@example
(cf-help-string "--option=ARG" "Give ARG as the value of option")
@end example
@end defun

@defun cf-feature-ref name
@defunx cf-package-ref name
@c MOD gauche.configure
@c EN
Lookup a symbol @var{name} from the global feature table and the
global package table, respectively.
These can be called after @code{cf-init}.
@c JP
グローバルな機能テーブルおよびパッケージテーブルに@var{name}で登録された値を
返します。これらは@code{cf-init}の後で呼べます。
@c COMMON

@c EN
For example, if you've called @code{cf-arg-enable} with @code{foofeature},
and the user has invoked the @code{configure} script with
@code{--with-foofeature=full}, then @code{(cf-feature-ref 'foofeature)}
returns @code{"full"}.   If the user hasn't given the command-line
argument, @code{#f} is returned.
@c JP
例えば、@code{cf-arg-enable}で@code{foofeature}という機能に関するコマンドライン
引数を登録したとしましょう。ユーザが@code{configure}スクリプトに
@code{--with-foofeature=full}オプションを与えて起動した場合、
@code{(cf-feature-ref 'foofeature)}は@code{"full"}を返します。
コマンドライン引数が与えられなかった場合は@code{#f}が返ります。
@c COMMON

@c EN
If you add or change the value of features or packages,
you can use generalized @code{set!} as
@code{(set! (cf-feature-ref 'NAME) VALUE)} etc.
@c JP
機能テーブルやパッケージテーブルに値を足したり変更したい場合は一般化@code{set!}を使って
@code{(set! (cf-feature-ref 'NAME) VALUE)}と書くことができます。
@c COMMON
@end defun


@c EN
@subsubheading Messages
@c JP
@subsubheading メッセージ
@c COMMON

@c EN
The @code{cf-init} procedure opens the default log drain
that goes to @code{config.log}, and you can use @code{log-format},
@code{log-display} or @code{log-write}
to write to it (@xref{User-level logging}, for the details of logging).
@c JP
@code{cf-init}手続きは@code{config.log}にロギングするデフォルトログドレインを
オープンするので、@code{log-format}、@code{log-display}、@code{log-write}
を使って@code{config.log}にログを残すことができます
(ロギングの詳細については@ref{User-level logging}参照)。
@c COMMON

@c EN
However, to have consistent message format conveniently, the following
procedures are provided.  They emits the message both to log files and
the current output port (in slightly different formats so that the
console messages align nicely visually.)
@c JP
しかし、一貫した形式でメッセージを扱うために、以下の手続きが提供されています。
これらの手続きはログファイルと現在の出力ポートに(見やすいようにそれぞれ若干異なる
形式で)メッセージを出力します。
@c COMMON

@defun cf-msg-checking fmt arg @dots{}
@c MOD gauche.configure
@c EN
Writes out ``checking XXX...'' message.  The @var{fmt} and @var{arg} @dots{}
arguments are passed to @code{format} to produce the ``XXX'' part
(@pxref{Formatting output}).
@c JP
``checking XXX...'' というメッセージを出力します。@var{fmt}と@var{arg} @dots{}
引数は@code{format}に渡されて、``XXX''の部分を生成します
(@ref{Formatting output}参照)。
@c COMMON

@c EN
For the current output port, this does not emit the trailing newline,
expecting @code{cf-msg-result} will be called subsequently.
@c JP
現在の出力ポートに向けては、改行文字は出力されません。
この後で@code{cf-msg-result}が呼ばれることを期待しているからです。
@c COMMON

@c EN
Here's an excerpt of the source that uses @code{cf-msg-checking}
and @code{cf-msg-result}:
@c JP
以下は、@code{cf-msg-checking}と@code{cf-msg-result}を使っているソースからの
抜粋です。
@c COMMON
@example
(define (compiler-can-produce-executable?)
  (cf-msg-checking "whether the ~a compiler works" (~ (cf-lang)'name))
  (rlet1 result ($ run-compiler-with-content
                   (cf-lang-link-m (cf-lang))
                   (cf-lang-null-program-m (cf-lang)))
    (cf-msg-result (if result "yes" "no"))))
@end example

@c EN
This produces a console output like this:
@c JP
この例は、次のような出力を生成します:
@c COMMON
@example
checking whether the C compiler works... yes
@end example
@c EN
while the log file records more info:
@c JP
また、ログファイルに対しては次の情報が記録されます:
@c COMMON
@example
checking: whether the C compiler works
@c EN
... whatever logging message from run-compiler-with-content ...
@c JP
... run-compiler-with-contentのログ出力 ...
@c COMMON
result: yes
@end example

@c EN
This corresponds to autoconf's @code{AC_MSG_CHECKING}.
@c JP
これはautoconfの@code{AC_MSG_CHECKING}に対応します。
@c COMMON
@end defun

@defun cf-msg-result fmt arg @dots{}
@c MOD gauche.configure
@c EN
The @var{fmt} and @var{arg} @dots{} are passed to @code{format}, and
the formatted message and newline is written out
(@pxref{Formatting output}).  Typically, the message is simply
``yes'' or ``no'', or the name (of a library, a header, etc.) that is found.
For the log file, it records ``result: XXX'' where XXX is the
formatted message.  Supposed to be used with @code{cf-msg-checking}; see the
example of @code{cf-msg-checking} above.
This corresponds to autoconf's @code{AC_MSG_RESULT}.
@c JP
@var{fmt}と@var{arg} @dots{}が@code{format}に渡され、フォーマット結果が出力されます。
通常、メッセージは単なる ``yes'' / ``no'' か、見つかった(ライブラリやヘッダの)名前です。
ログファイルに対しては、XXXをフォーマットされたメッセージとして、
``result: XXX''という文字列が記録されます。
@code{cf-msg-checking}と一緒に使うことを想定しています。
上の@code{cf-msg-checking}の例を見てください。
これはautoconfの@code{AC_MSG_RESULT}に対応します。

@c COMMON
@end defun

@defun cf-msg-notice fmt arg @dots{}
@c MOD gauche.configure
@c EN
Produces formatted message to both console and log.  Newline is added.
This corresponds to autoconf's @code{AC_MSG_NOTICE}.
@c JP
フォーマットされたメッセージをコンソールとログファイルの両方に出力します。
最後に改行文字が追加されます。これはautoconfの@code{AC_MSG_NOTICE}に対応します。
@c COMMON
@end defun

@defun cf-msg-warn fmt arg @dots{}
@defunx cf-msg-error fmt arg @dots{}
@c MOD gauche.configure
@c EN
Produces ``Warning: XXX'' and
``Error: XXX'' messages, respectively.
The @var{fmt} and @var{arg} @dots{} are passed to @code{format} to
generate XXX part (@pxref{Formatting output}).

Additionally, @code{cf-msg-error} exits with exit code 1.
@c JP
それぞれ、``Warning: XXX'' および ``Error: XXX'' というメッセージを出力します。
@var{fmt}と@var{arg} @dots{}は@code{format}に渡されて、
XXXの部分の文字列を生成します (@ref{Formatting output}参照)。

さらに、@code{cf-msg-error}は終了コード1でプロセスを終了します。
@c COMMON

@c EN
These corresponds to
autoconf's @code{AC_MSG_WARN} and @code{AC_MSG_ERROR}.
NB: @code{AC_MSG_ERROR} can specify the exit code,
but @code{cf-msg-error} uses fixed exit code (1) for now.
@c JP
これらは、autoconfの@code{AC_MSG_WARN}と@code{AC_MSG_ERROR}に相当します。
註: @code{AC_MSG_ERROR}は終了コードが指定できますが、
@code{cf-msg-error}は今の所1に固定です。
@c COMMON
@end defun

@defun cf-echo arg @dots{} [> file][>> file]
@c MOD gauche.configure
@c EN
Convenience routine to replace shell's @code{echo} command.

If the argument list ends with @code{> @var{file}} or
@code{>> @var{file}}, where @var{file} is a string file name,
then this works just like shell's @code{echo}; that is,
@var{arg}s except the last two are written to @var{file}, space
separated, newline terminated.  Using @code{>} supersedes
@var{file}, while @code{>>} appends to it.

If the argument list doesn't end with those redirection message,
it writes out the argument to both the current output port
and the log file, space separated, newline terminated.
For the log file, the message is prefixed with ``Message:''.
@c JP
シェルの@code{echo}コマンドを置き換える便利手続きです。

引数リストが@code{> @var{file}}もしくは@code{>> @var{file}}で終わっている場合
(@var{file}はファイル名の文字列)、これはシェルの@code{echo}のように動作します。
すなわち、その部分を除く@var{arg} @dots{}が空白文字を間に挟んで
@var{file}に書き出されます。また最後に改行文字も書き出されます。
@code{>}を使った場合は@var{file}は上書きされ、@code{>>}の場合は追記されます。

引数リストが上記リダイレクト指示で終わっていない場合は、
現在の出力ポートとログファイル両方に、@var{arg} @dots{}を空白文字を間に挟んで出力します。
また最後に改行文字も書き出されます。ログファイルに向けては、メッセージの前に
``Message:''が出力されます。
@c COMMON
@end defun

@c EN
@subsubheading Parameters and definitions
@c JP
@subsubheading パラメータと定義
@c COMMON

@c EN
The configure script maintains two global tables, definition tables
and parameter tables.  Definition tables is used for C preprocessor
definitions, and parameter tables are used for @code{@@PARAMETER@@}
substitutions.  (Do not confuse substitution parameters with
Scheme's parameter objects (@pxref{Parameters})).
@c JP
configureスクリプトは、定義テーブルと置換パラメータテーブルという
二つのグローバルなテーブルを持っています。
定義テーブルはCプリプロセッサの定義に使われ、置換パラメータテーブルは
@code{@@PARAMETER@@}の置換に使われます。
(置換パラメータをSchemeのパラメータオブジェクト(@ref{Parameters}参照)と
混同しないように!)。
@c COMMON

@defun cf-define symbol :optional value
@c MOD gauche.configure
@c EN
Registers C preprocessor definition of @var{symbol} with @var{value}.
@var{Value} can be any Scheme objects, but it is emitted to a command
line (in @code{-DSYMBOL=VALUE} form) or in @file{config.h}
(in @code{#define SYMBOL VALUE} form) using @code{display}, so
you want to avoid including funny characters.  If @var{value} is
omitted, @code{1} is assumed.

NB: To @code{#define} a string value, e.g. @code{#define FOO "foo"},
you have to call as @code{(cf-define 'FOO "\"foo\"")}.
@c JP
@var{symbol}を@var{value}とするCプリプロセッサ定義を登録します。
@var{value}には任意のSchemeオブジェクトを渡せますが、
その@code{display}表記がそのままコンパイラのコマンドライン
(@code{-DSYMBOL=VALUE}という形式)あるいは@file{config.h}内の定義
(@code{#define SYMBOL VALUE}という形式)に使われるので、
妙な文字を入れない方が無難でしょう。@var{value}が省略された場合は
@code{1}が使われます。

註: 文字列を値とする定義、例えば @code{#define FOO "foo"} を生成するには、
@code{(cf-define 'FOO "\"foo\"")} とする必要があります。
@c COMMON

@c EN
This corresponds to autoconf's @code{AC_DEFINE}.
@c JP
これはautoconfの@code{AC_DEFINE}に相当します。
@c COMMON
@end defun

@defun cf-defined? symbol
@c MOD gauche.configure
@c EN
Returns @code{#t} iff @var{symbol} is @code{cf-define}d.
@c JP
@var{symbol}が@code{cf-define}されていれば@code{#t}を、
そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun cf-subst symbol :optional value
@c MOD gauche.configure
@c EN
Registers a substitution parameter @var{symbol} with @var{value}.
While processing output files, @var{@@symbol@@} in the template
is substituted with @var{value}.

@var{Value} is usually a string, but can be any Scheme objects;
its @code{display} representation.

If @var{value} is @code{#f} or omitted, it works a bit differently.
If @var{symbol} hasn't been registered as a substitution parameter,
it is registered with an empty string as its value.  If @var{symbol} has
already been registered, however, its value is left intact.
@c JP
置換パラメータ@var{symbol}を値@var{value}で定義します。
出力ファイルを生成する時に、テンプレートの@var{@@symbol@@}が
@var{value}に置換されます。

@var{value}は通常文字列ですが、任意のSchemeオブジェクトで構いません。
@code{display}での印字表現が使われます。

@var{value}が省略されるか@code{#f}の場合はちょっと違った動作になります。
@var{symbol}がまだ置換パラメータとして登録されていない場合は、
空文字列を値として置換パラメータを登録します。既に登録されていた場合は値をそのまま残します。
@c COMMON

@c EN
This corresponds to autoconf's @code{AC_SUBST}, but we require
the value (while autoconf can refer to the shell variable value as default).
@c JP
これはautoconfの@code{AC_SUBST}に相当します。ただ、autoconfeでは値を明示しなくても
同名のシェル変数の値が使われますが、Gaucheでは値を陽に与えなければなりません。
@c COMMON
@end defun

@defun cf-subst-prepend symbol value :optional delim default
@defunx cf-subst-append symbol value :optional delim default
@c MOD gauche.configure
@c EN
Prepend or append @var{value} to the substitution parameter @var{symbol},
using delimiter @var{delim}.  If the substitution parameter isn't
defined, @var{value} becomes the sole value of the parameter,
except when @var{default} is given and not an empty string.
If @var{delim} is omitted, single whitespace is used.
@c JP
置換パラメータ@var{symbol}の値の前もしくは後に、
@var{delim}を挟んで@var{value}を付け足します。
@var{symbol}がまだ定義されていなかった場合な、
@var{default}が与えられ空文字列でなければあたかもそれが既に設定されていた値であるかのように
動作し、そうでなければ@var{value}が最初の値となります(この場合、@var{delim}は使われません)。
@var{delim}が省略された場合は空白1文字の文字列が使われます。
@c COMMON

@c EN
A substitution parameter is often used to accrue command line arguments
(e.g. @code{-I include-dir} for a compiler), and these procedures
comes handy.
@c JP
置換パラメータにはよくコマンドライン引数をつけ足してゆくので
(例:コンパイラの@code{-I include-dir})、これらの手続きが便利に使えるでしょう。
フラグ
@c COMMON
@end defun

@defspec with-cf-subst (binding @dots{}) body @dots{}
@c MOD gauche.configure
@c EN
Temporarily replace substitution parameters with new values. This
could be useful for example to run some compilation checks with
different parameters.
@c JP
一時的に置換パラメータを新たな値に置き換えて@var{body} @dots{}を実行します。
コンパイルチェックを違うパラメータで実行してみたい時に便利です。
@c COMMON

@c EN
@var{Binding} may be one of the following forms:

@table @code
@item (@var{var} @var{value})
Temporarily substitue parameter @var{var}'s value to @var{value}.
@item (@var{var} + @var{value})
Temporarily append @var{value} to the parameter @var{var}, using
a space as a delimiter.  See @code{cf-subst-append} above.
@item (@var{var} @var{value} +)
Temporarily prepend @var{value} to the parameter @var{var}, using
a space as a delimiter.  See @code{cf-subst-prepend} above.
@end table
@c JP
@var{binding}は以下のいずれかの形式です。

@table @code
@item (@var{var} @var{value})
一時的に置換パラメータ@var{var}の値を@var{value}で置き換えます。
@item (@var{var} + @var{value})
一時的に置換パラメータ@var{var}の値の後に空白を挟んで@var{value}を追加します。
追加には上記の@code{cf-subst-append}が使われます。
@item (@var{var} @var{value} +)
一時的に置換パラメータ@var{var}の値の前に空白を挟んで@var{value}を前置します。
追加には上記の@code{cf-subst-prepend}が使われます。
@end table
@c COMMON

@example
(with-cf-subst ((LIBS "-L<path> -l<lib>"))
  (cf-try-compile-and-link @dots{}))
@end example

@c EN
In autoconf, this pattern is realized by saving the current value
of the substituion parameter, modify it, run checks, and restore the old value.
It is tedious.
@c JP
autoconfではこのパターンは、現在の置換パラメータを保存し、
新たなパラメータに変更してチェックを走らせた後で置換パラメータを元に戻しますが、
とても面倒です。
@c COMMON
@end defspec

@defun cf-have-subst? symbol
@c MOD gauche.configure
@c EN
Returns true iff @var{symbol} is registered as a substitution parameter by
@code{cf-subst}.
@c JP
@var{symbol}が@code{cf-subst}で置換パラメータとして登録されていれば@code{#t}を、
そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun cf-arg-var symbol
@c MOD gauche.configure
@c EN
Lookup the environment variable with the name @var{symbol} and if it is found,
use its value as the substitution value.  If it is not found, and
if @var{symbol} hasn't been already registered as a substitution parameter,
register it with an empty string as its value; otherwise, do nothing.

For example,
if you call @code{(cf-arg-var 'MYCFLAGS)}, then the user
can provide the value of @code{@@MYCFLAGS@@} as
@code{MYCFLAGS=-g ./configure}.

This corresponds to autoconf's @code{AC_ARG_VAR}, but we lack the ability
of setting the help string.  That's because @code{cf-arg-var} must
be run after @code{cf-init}, but the help message is constructed
within @code{cf-init}.
@c JP
名前@var{symbol}を持つ環境変数を探し、見つかればそれを置換パラメータ@var{symbol}の
値とします。環境変数が見つからない場合、まだ@var{symbol}が置換パラメータとして登録されて
いなければ、空文字列を値として登録します。そうでなければ何もしません。

例えば、@code{(cf-arg-var 'MYCFLAGS)}を呼び出しておくと、
ユーザは@code{@@MYCFLAGS@@}の置換を@code{MYCFLAGS=-g ./configure}のようにして
与えることができます。

これはautoconfの@code{AC_ARG_VAR}に相当します。
ただし、autoconfと違ってヘルプ文字列を与えることはできません。
@code{cf-arg-var}は@code{cf-init}より後に呼ばれねばならず、
しかしヘルプ文字列は@code{cf-init}内で構築される必要があるからです。
@c COMMON
@end defun

@defun cf-ref symbol :optional default
@c MOD gauche.configure
@c EN
This looks up the value of the substitution parameter @var{symbol}.
If there's no such substitution parameter registered,
it returns @var{default} when it's provided, otherwise
throws an error.
@c JP
置換パラメータ@var{symbol}の値を返します。該当する置換パラメータが登録されていない場合、
@var{default}が与えられていればそれを返し、そうでなければエラーを投げます。
@c COMMON
@end defun

@defun cf$ symbol
@c MOD gauche.configure
@c EN
Looks up the value of the substitution parameter @var{cf-ref},
but it returns empty string if it's unregistered.  Useful
to use within string interpolation, e.g. @code{#"gosh ~(cf$'GOSHFLAGS)"}.
@c JP
@code{cf-ref}と同じように置換パラメータ@var{symbol}の値を返しますが、
該当する置換パラメータが登録されていない場合は空文字列を返します。
文字列補間の中で@code{#"gosh ~(cf$'GOSHFLAGS)"}のように使えるので便利です。
@c COMMON
@end defun

@c EN
@subsubheading Predefined tests
@c JP
@subsubheading 定義済みテスト
@c COMMON

@defun cf-check-prog sym prog-or-progs :key value default paths filter
@defunx cf-path-prog sym prog-or-progs :key value default paths filter
@c MOD gauche.configure
Check if a named executable program exists in search paths, and if it
exists, sets the substitution parameter @var{sym} to the name
of the found program.  The name to search is specified by @var{prog-or-progs},
which is either a string or a list of strings.

The difference of @code{cf-check-prog} and @code{cf-path-prog} is that
@code{cf-check-prog} uses the basename of the found program, while
@code{cf-path-prog} uses its full path.  These corresponds to
autoconf's @code{AC_CHECK_PROG}, @code{AC_CHECK_PROGS},
@code{AC_PATH_PROG} and @code{AC_PATH_PROGS}.

For example, the following
feature test searches either one of @code{cc}, @code{gcc}, @code{tcc}
or @code{pcc} in @code{PATH} and sets the substitution parameter @code{MY_CC}
to the name of the found one.

@example
(cf-check-prog 'MY_CC '("cc" "gcc" "tcc" "pcc"))
@end example

If multiple program names is given, the search is done in the following
order: First, we search for the first item (@code{cc}, in the above
example) for each of paths, then the second, etc.  For example,
if we have @code{/usr/local/bin:/usr/bin:/bin} in @code{PATH} and
we have @code{/usr/local/bin/tcc} and @code{/usr/bin/gcc}, the above
feature test sets @code{MY_CC} to @code{"gcc"}.  If you use @code{cf-path-prog}
instead, @code{MY_CC} gets @code{"/usr/bin/gcc"}.

If no program is found, @var{sym} is set to the keyword argument
@var{default} if it is given, otherwise @var{sym} is left unset.

If the @var{value} keyword argument is given, its value is
used instead of the found program name to be set to @var{sym}.

The list of search paths is taken from @code{PATH} environment
variable.  You can override the list by the @var{paths} keyword
argument, which must be a list of directory names.  It may contain
nonexistent directory names, which are silently skipped.

The @var{filter} keyword argument, if given, must be a predicate
that takes full pathname of the executable program.  It is called
when the procedure finds matching executable; the @var{filter} procedure
may reject it by returning @code{#f}, in which case the procedure
keeps searching.

Note: If the substitution parameter @var{sym} is already set
at the time these procedure is called, these procedures do nothing.
Combined with @code{cf-arg-var}, it allows the configure script caller
to override the feature test.  For example, suppose you have the
following in the @code{configure} script:

@example
(cf-arg-var 'GREP)
(cf-path-prog 'GREP '("egrep" "fgrep" "grep"))
@end example

A user can override the test by calling @code{configure} like this:

@example
$ ./configure GREP=mygrep
@end example

@end defun

@defun cf-prog-cxx
@c MOD gauche.configure
A convenience feature test to find C++ compiler.  This searches
popular names of C++ compilers from the search paths, sets the
substitution parameter @code{CXX} to the compiler's name,
then tries to compile a small
program with it to see it can generate an executable.

This corresponds to autoconf's @code{AC_PROG_CXX}.

@code{CXX} is @code{cf-arg-var}'ed in this procedure.  If a user
provide the value when he calls @code{configure}, the searching
is skipped, but the check of generating an executable is still
performed.

If the substitution parameter @code{CXXFLAGS} is set, its value
is used to check if the compiler can generate an executable.
@code{CXXFLAGS} is @code{cf-arg-var}'ed in this procedure.

This procedure also emulates autoconf's @code{AC_PROG_CXX} behavior---
if @code{CXX} is not set, but @code{CCC} is set, then we set
@code{CXX} by the value of @code{CCC} and skip searching.
@end defun

@defun cf-header-available? header :key includes
@defunx cf-check-header header :key includes
@c MOD gauche.configure
Check if a header file @var{header} exists and usable, by
compiling a source program of the current language
that includes the named header file.
Return @code{#t} if the header is usable, @code{#f} if not.

Both procedure does the same thing.  The name @code{cf-check-header}
corresponds to autoconf's @code{AC_CHECK_HEADER}.

If @var{header} requires other headers being included or
preprocessor symbols defined before it,
you can pass a list of strings to be emitted before the check
in the @var{includes} keyword arguments.  The given strings
are just concatenated and used as a C program fragment.
The default value is provided by @code{cf-includes-default}.

The following example sets C preprocessor symbol @code{HAVE_CRYPT_H} to
1 if @file{crypt.h} is available.  (Note: For this kind of common task,
you can use @code{cf-check-headers} below.  The advantage of using
@code{cf-check-header} is that you can write other actions in Scheme
depending on the result.)

@example
(when (cf-check-header "crypt.h")
  (cf-define "HAVE_CRYPT_H" 1))
@end example
@end defun

@defun cf-check-headers headers :key includes if-found if-not-found
@c MOD gauche.configure
Codify a common pattern of checking the availability of headers and
sets C preprocessor definitions.
This corresponds to autoconf's @code{AC_CHECK_HEADERS}.
This procedure is invoked for the side effects,
and returns an undefined vlaue.

See this example:

@example
(cf-check-headers '("unistd.h" "stdint.h" "inttypes.h" "rpc/types.h"))
@end example

This checks availability of each of listed headers,
and sets C preprocessor definition @code{HAVE_UNISTD_H},
@code{HAVE_STDINT_H}, @code{HAVE_INTTYPES_H} and
@code{HAVE_RPC_TYPES_H} to 1 if the corresponding header
file is available.

A list of strings given to @var{includes} are emitted to the
C source file before the inclusion of the testing header.  You can
give necessary headers and/or C preprocessor definitions there;
if omitted, @code{cf-includes-default} provides
the default list of such headers.

The keyword argument @var{if-found} and @var{if-not-found} are
procedures to be called when a header is found to be available or
to be unavailable, respectively.  The procedure receives the name
of the header.

The name of the C preprocessor definition is derived from the
header name by upcasing it and replacing non-alphanumeric characters
for @code{_}.  Note that this substitution is not injective:
Both @file{gdbm/ndbm.h} and @file{gdbm-ndbm.h} yield
@code{GDBM_NDBM_H}.  If you need to distinguish such files
you have to use @code{cf-check-header}.
@end defun

@defun cf-includes-default
@c MOD gauche.configure
Returns a list of strings that are included in the check program by
default.  It is actually a combination of C preprocessor @code{#ifdef}s
and @code{#include}s, and would probably be better to be called
@code{cf-prologue-default} or something, but the corresponding
autoconf macro is @code{AC_INCLUDES_DEFAULT} so we stick to this name.

Usually you don't need to call this explicitly.  Not giving the
@code{includes} argument to @code{cf-check-header} and
@code{cf-check-headers} will make @code{cf-includes-default}
called implicitly.
@end defun

@defun cf-type-available? type :key includes
@defunx cf-check-type type :key includes
@c MOD gauche.configure
Test if @var{type} is defined as a type name.
Return @code{#t} if @var{type} is defined, @code{#f} otherwise.

Two procedures are the same.  The name @code{cf-check-type}
corresponds to @code{AC_CHECK_TYPE}.

A list of strings given to @var{includes} are emitted to the
C source file before the inclusion of the testing header.  You can
give necessary headers and/or C preprocessor definitions there;
if omitted, @code{cf-includes-default} provides
the default list of such headers.
@end defun

@defun cf-check-types types :key includes if-found if-not-found
@c MOD gauche.configure
For each type in the list @var{types}, call @code{cf-check-type} to
see it is defined as a type.  If it is,
defines @code{HAVE_@var{type}}, and calls @var{if-found} with the
type as an argument if provide.  If the type is not defined and
@var{if-not-found} is provided, calls it with the type as an argument.

The argument @var{includes} is passed to @code{cf-check-type}.

This corresponds to autoconf's @code{AC_CHECK_TYPES}.

Returns an undefiend value.  This procedure is for side effects.

@example
;; May define HAVE_PTRDIFF_T and/or HAVE_UNSIGNED_LONG_LONG_INT
;; depending on its availability:
(cf-check-types '("ptrdiff_t" "unsigned long long int"))

;; Example of using @var{includes} to add an extra header.
(cf-check-types '("float_t")
                :includes `(,@@(cf-includes-default)
                            "#include <math.h>\n"))
@end example
@end defun

@defun cf-decl-available? symbol :key includes
@defunx cf-check-decl symbol :key includes
@c MOD gauche.configure
Test if @var{symbol} is declared as a cpp macro, a variable,
a constant, or a function.
Return @code{#t} if @var{type} is defined,
@code{#f} otherwise.

Two procedures are the same.  The name @code{cf-check-decl} corresponds
to autoconf's @code{AC_CHECK_DECL}.

A list of strings given to @var{includes} are emitted to the
C source file before the inclusion of the testing header.  You can
give necessary headers and/or C preprocessor definitions there;
if omitted, @code{cf-includes-default} provides
the default list of such headers.
@end defun

@defun cf-check-decls symbols :key includes if-found if-not-found
@c MOD gauche.configure
For each symbol in @var{symbols}, call @code{cf-check-decl} to see
if it is declared.  If it is, define @code{HAVE_DECL_@var{symbol}} to
1, and calls @var{if-found} with the symbol if provided.
If it is not declared, define @code{HAVE_DECL_@var{symbol}} to 0,
and calls @var{if-not-found} with the symbol if provided.
This corresponds to autoconf's @code{AC_CHECK_DECLS}.

The argument @var{includes} is passed to @code{cf-check-decl}.

This procedure returns an undefined value.  This procedure is for
side effects.

Note that, unlike other @code{cf-check-*} routines which leave
@code{HAVE_*} macro undefined when the item isn't found, this one
always defines the macro and differentiate the result with its value.
This behavior is the same as @code{AC_CHECK_DECLS}.
@end defun

@defun cf-member-available? aggregate.member :key includes
@defunx cf-check-member aggregate.member :key includes
@c MOD gauche.configure
The @var{aggregate.member} argument is a string of aggregate type name
and its member concatenated by a dot, e.g. @code{"struct password.pw_gecos"}.
It can also be a submember, e.g. @code{"struct foo.bar.baz"}.
The @var{aggregate} part can be any type name (typedef-ed name is ok).

This test checks if @var{member} is a member of @var{aggregate}, and
returns @code{#t} if so, or returns @code{#f} if not.

Two procedures are the same.  The name @code{cf-check-member}
corresponds to autoconf's @code{AC_CHECK_MEMBER}.

A list of strings given to @var{includes} are emitted to the
C source file before the inclusion of the testing header.  You can
give necessary headers and/or C preprocessor definitions there;
if omitted, @code{cf-includes-default} provides
the default list of such headers.
@end defun

@defun cf-check-members members :key includes if-found if-not-found
@c MOD gauche.configure
For each @var{aggregate.member}
in @var{members}, call @code{cf-check-member}.
If the test passes, defines @code{HAVE_@var{aggregate}_@var{member}},
and calls @var{if-found} with @var{aggregate.member} if provided.
If the test fails, calls @var{if-not-found} with @var{aggregate.member}
if provided.

This corresponds to autoconf's @code{AC_CHECK_MEMBERS}.

The @var{include} argument is passed to @code{cf-check-member}.

@example
;; Defines HAVE_STRUCT_ST_RDEV and/or HAVE_STRUCT_ST_BLKSIZE
;; depending on their availability:
(cf-check-members '("struct stat.st_rdev"
                    "struct stat.st_blksize"))
@end example

This procedure is for side effects, and returns an undefined value.
@end defun

@defun cf-func-available? func
@defunx cf-check-func func
@c MOD gauche.configure
See if a function @var{func} is available.  This emits C code
to call @var{func} (with dummy declaration) and tries to compile and link,
using current value of substitution parameter @code{LIBS}.
The value of @code{cf-includes-default} is at the top of the emitted C code.

They return @code{#t} if @var{func} is available, @code{#f} otherwise.

Two procedures are the same.  The name @code{cf-check-func}
corresponds to autoconf's @code{AC_CHECK_FUNC}.
@end defun

@defun cf-check-funcs funcs :key if-found if-not-found
@c MOD gauche.configure
For each function name @var{func} in @var{funcs}, call @code{cf-check-func}
to determine availability.  If it is available, define
@code{HAVE_@var{func}}, and calls @code{if-found} with @var{func}
if provided.  If it is not available, calls @code{if-not-found}
with @var{func} if provided.

This corresponds to autoconf's @code{AC_CHECK_FUNCS}.

This procedure is for side effects, and returns an undefined value.
@end defun

@defun cf-lib-available?  lib fn :key other-libs if-found if-not-found
@defunx cf-check-lib lib fn :key other-libs if-found if-not-found
@c MOD gauche.configure
See if a library @var{lib} can be linked and a function @var{fn} in it
is callable.  Return @code{#t} it is, @code{#t} if not.

Two procedures are the same.  The name @code{cf-check-lib}
corresponds to autoconf's @code{AC_CHECK_LIB}.

Give the name you pass after @code{-l} option to @var{lib};
for example, if you want to check availability of @code{libm}, you can
say as follows:

@example
(cf-check-lib "m" "sin")
@end example

This generates a C source that calls @var{fn} and try to compile and link
it to generate executable.  If linking @var{lib} requires additional
libraries, it should be listed in @var{other-libs}:

@example
(cf-check-lib "Xt" "XtDisplay" :other-libs '("-lX11" "-lSM" "-lICE"))
@end example

If compilation and linking succeeds,
@var{if-found} is called at the
tail position with
the library name (@code{"m"} and @code{"Xt"} in the above examples,
respectively) as the argument.
The default behavior is to add
@code{-l@var{lib}} in the left of substitution parameter @code{LIBS},
and set @code{HAVE_LIB@var{lib}} definition, then
returns @code{#t}.

If compilation or linking fails, @var{if-not-found} is called at
the tail position with the library name.  The default behavior is
to return @code{#f}.

The default behavior of @var{if-found} and @var{if-not-found} allows
@code{cf-check-lib} to be used as predicate as well.  If you merery
want to take an action depending on whether the library is found or
not, you can write like this:

@example
(unless (cf-check-lib "foo" "foo_fn)
  ... do something if libfoo isn't available ...)
@end example

Use @var{if-found} and/or @var{if-not-found} only if you want to
override the default behaviors.
@end defun

@defun cf-search-libs fn libs :key other-libs if-found if-not-found
@c MOD gauche.configure
Like @code{cf-check-lib}, but can be used if you're not sure which
library contains desired function.
This corresponds to autoconf's @code{AC_SEARCH_LIBS}.  Note that
this takes function name first, while @code{cf-check-lib} takes
function name second---blame autoconf for this inconsistency.

First it tests if @var{fn} is available without any library in @var{libs}
(that is, with the ones already in @code{LIBS} and specified in
@var{other-libs}).  If not, it tests each library in @var{libs}
in turn.

If @var{fn} is found, @var{if-found} is called at the tail position,
with the name of
the library as an argument (if @var{fn} is available without any
library, the argument is @code{#f}).  If omitted, and a library
is required, then the library is
added to the substitution parameter @code{LIBS}.
The default procedure returns @code{#t}.

If @var{fn} isn't found in any of the libraries, @var{if-not-found}
is called at the tail position
with @code{#f} as the argument.  The default procedure
does nothing and just returns @code{#f}.

The default behavior of @var{if-found} and @var{if-not-found} allows
@code{cf-search-libs} to be used as predicate as well.  If you give
alternative procedures, keep in mind that their return value
will be returned to @code{cf-search-libs}.
@end defun

@defun cf-path-x
@c MOD gauche.configure
This corresponds to autoconf's @code{AC_PATH_X}.  It checks if
X11 is available, and returns three values.

The first value is a boolean value indicates if X11 is available.
The second and third values are strings for the directory name
to find X11 headers and libraries, respectively.  The second
and third value can be empty strings if the compiler doesn't
need additional flags to find X11 stuff.

This does not set other substituion parameters.
You typically want to use @code{cf-path-xtra} below instead.

(In autoconf, @code{AC_PATH_X} sets shell variables to tell
the results.  In Scheme, it is more natural to use return
values.)
@end defun

@defun cf-path-xtra
@c MOD gauche.configure
Check X11 availability with @code{cf-path-x} above, and
sets up the following substitution parameters:

@table @code
@item X_CFLAGS
Additional CFLAGS needed to build with X11.
@item X_PRE_LIBS
Additional library link flags (@code{-l@var{lib} @dots{}})
that need to come @emph{before} @code{-lX11} flag.
@item X_LIBS
Additional library search flags (@code{-L@var{dir} @dots{}})
to link with X11.  (Note: The name is for the compatibility
with autoconf.  It should really be named as @code{X_LDFLAGS}.)
@item X_EXTRA_LIBS
Additional library search flags (@code{-L@var{dir} @dots{}})
to link with X11.  Those libraries should come after @code{-lX11}
flag.
@end table

This procedure corresponds to autoconf's @code{AC_PATH_XTRA}.

Note that @code{-lX11} is not included in those parameters;
they must be specified explicitly.

If X11 is not available, those parameters get empty strings.
@end defun


@c EN
@subsubheading Running compiler
@c JP
@subsubheading コンパイラを走らせる
@c COMMON

The @code{gauche.configure} module provides a generic mechanism
to construct a small test program, compile it, and run it.
Currently we only support @code{C} and @code{C++}; we'll add support
for other languages as needed.

@deffn {Parameter} cf-lang
@c MOD gauche.configure
Returns a @emph{current language}, which is an opaque object.
Currently C and C++ are supported; see @code{cf-lang-C} and
@code{cf-lang-C++} below.

The current language is used by compiler tests.
@end deffn

@defun cf-lang-C
@defunx cf-lang-C++
@c MOD gauche.configure
Returns an opaque object representing C or C++, respectively.
You can use them to parameterize @code{cf-lang} to run
compiler tests.

@example
(parameterize ([cf-lang (cf-lang-C++)])
  ... run compiler tests ...)
@end example
@end defun


@defun cf-lang-program prologue body
@c MOD gauche.configure
Returns a string tree that consists a stand-alone program for
the current language.  @var{Prologue} and @var{body} must be a
string or a list of strings.  If it is a list, strings are
concatenated with newlines.
@var{Prologue} comes at the beginning of
the source, and @var{body} is included in the part of the program
that's executed.  If the current language is C, the code fragment:

@example
(use text.tree)
(write-tree (cf-lang-program '("#include <stdio.h>"
                               "#include <stdlib.h>")
                             '("printf(\"()\");")))
@end example

would produce something like this:

@example
#include <stdio.h>
#include <stdlib.h>

int main()@{
printf("()");

; return 0;
@}
@end example
@end defun

@defun cf-lang-io-program
@c MOD gauche.configure
This is a convenience routine.  It returns a string tree
of a program in the current language, that creates a file
named @file{conftest.out}, then exits with zero status on
success, or nonzero status on failure.
@end defun

@defun cf-lang-call prologue func-name
@c MOD gauche.configure
Returns a string tree of a program in the current language,
that calls @var{func-name} as a function with no arguments.
@end defun

@defun cf-try-compile prologue body
@c MOD gauche.configure
The arguments must be a string or a list of strings.  If it is
a list, it is taken as a list of lines, concatenated with newlines.

This test generates a program with the given content,
using @code{cf-lang-program}, then try to compile it.
On success, @code{#t} is returned.  On failure, @code{#f} is returned.
The generated program, command line, and the result is logged.
@end defun

@defun cf-try-compile-and-link prologue body
@c MOD gauche.configure
The arguments must be a string or a list of strings.  If it is
a list, it is taken as a list of lines, concatenated with newlines.

This test generates a program with the given content,
using @code{cf-lang-program}, then try to compile and link it.
On success, @code{#t} is returned.  On failure, @code{#f} is returned.
The generated program, command line, and the result is logged.
@end defun


@c EN
@subsubheading Output
@c JP
@subsubheading 出力
@c COMMON

@defun cf-output-default file @dots{}
@c MOD gauche.configure
A convenience routine to produce typical output.
It does the following:

@itemize @bullet
@item
Generate gpd (Gauche package description) file using
@code{cf-make-gpd}.
@item
Generate @code{VERSION} file that contains the value of
@code{PACKAGE_VERSION} substitution parameter.
@item
Search @code{Makefile.in}'s under the source directory
(the value of substitution parameter @code{srcdir}),
and process them to produce @code{Makefile}'s.
If @var{file} @dots{} are given, @code{@var{file}.in} are also
processed as well to produce @var{file}.

See @code{cf-output} below for the details.
@item
If config header is registered by @code{cf-config-headers},
process them as well.
@end itemize
@end defun

@defun cf-output file @dots{}
@c MOD gauche.configure
Generates @var{file}'s from the input templates.
This corresponds to autoconf's @code{AC_OUTPUT}.

For each @var{file}, a file named @file{@var{file}.in} is read
as a template.  Within the file, @code{@@PARAMETER@@} is substituted
with the value of @code{(cf$ 'PARAMETER)}.  If the named parameter
isn't registered, a warning is issued and the parameter is left
unsubstituted.

If config headers are not registered via @code{cf-config-headers},
a substitution parameter @code{DEFS} is replaced with
all the definitions in the form of @code{-D...}.  For example,
if you have checked header files @file{foo/bar.h} and
@file{foo/baz.h}, @code{DEFS} gets the value
@code{-DHAVE_FOO_BAR_H -DHAVE_FOO_BAZ_H}.

If config header is registered by @code{cf-config-headers},
they are processed as well.  In such case, the substitution
parameter @code{DEFS} gets the value @code{-DHAVE_CONFIG_H}.
@end defun

@defun cf-config-headers header-or-headers
@c MOD gauche.configure
Sets up config header files to be processed.  Usually a config header
file is named @file{config.h}, and contains definitions determined
by feature tests.

The @var{header-or-headers} argument may be a string header-spec
or a list of string header-specs, where each header spec is
a header file name (e.g. @code{"config.h"}) or a header name
and a input file name concatenated with a colon
(e.g. @code{"config.h:config.h.templ"}).  If it's just a header name,
input file name is assumed to be the header file name with @code{".in"}
appended.

The input template of config header file contains a bunch of
@code{#undef} directives, such as the following:

@example
/* Gauche ABI version string */
#undef GAUCHE_ABI_VERSION

/* Define if Gauche handles multi-byte character as EUC-JP */
#undef GAUCHE_CHAR_ENCODING_EUC_JP

/* Define if Gauche handles multi-byte character as Shift JIS */
#undef GAUCHE_CHAR_ENCODING_SJIS

/* Define if Gauche handles multi-byte character as UTF-8 */
#undef GAUCHE_CHAR_ENCODING_UTF_8
@end example

Once processed, the generated header file has either
@code{#undef} line is replaced with @code{#define}, or
commented out, depending on the definitions determined by feature
tests.

@example
/* Gauche ABI version string */
#define GAUCHE_ABI_VERSION "0.97"

/* Define if Gauche handles multi-byte character as EUC-JP */
/* #undef GAUCHE_CHAR_ENCODING_EUC_JP */

/* Define if Gauche handles multi-byte character as Shift JIS */
/* #undef GAUCHE_CHAR_ENCODING_SJIS */

/* Define if Gauche handles multi-byte character as UTF-8 */
#define GAUCHE_CHAR_ENCODING_UTF_8 /**/
@end example

Note that the lines other than @code{#undef} are copied as they are.

The substitution parameter @code{DEFS} behaves differently whether
config header is specified or not.  If no config header is registered,
The value of @code{DEFS} is a C command-line arguments for definitions,
e.g. @code{-DGAUCHE_ABI_VERSION=0.97 -DGAUCHE_CHAR_ENCODING_UTF8}.
If config header files are registered, the value of @code{DEFS} becomes
simply @code{-DHAVE_CONFIG_H}.
@end defun


@defun cf-show-substs :key formatter
@c MOD gauche.configure
Print all substitution parameters; this is for debugging.

For each substitution parameter name and value,
@var{formatter} is called with them; the default is
@code{(^[k v] (format #t "~16s ~s" k v))}.
@end defun

@defun cf-make-gpd
@c MOD gauche.configure
Generate gpd (Gauche package description) file,
@file{PACKAGE_NAME.gpd}, where @code{PACKAGE_NAME} is the
package's name either taken form @file{package.scm} or
the argument to @code{cf-init}.
@xref{Package metainformation}, for the package description file format.
@end defun


@c ----------------------------------------------------------------------
@node Connection framework, Dictionary framework, Generating build files, Library modules - Gauche extensions
@section @code{gauche.connection} - Connection framework
@c NODE コネクションフレームワーク, @code{gauche.connection} - コネクションフレームワーク

@deftp {Module} gauche.connection
@mdindex gauche.connection
@c EN
A connection is an abstract class to handle full-duplex
communication channel.  The actual data I/O is done through
Scheme ports; a channel provides an interface to retrieve those
ports.  It also has interface to know endpoint names, and the
way to shutdown the communication.
@c JP
コネクションは双方向コミュニケーションチャネルを抽象化するクラスです。
実際のデータI/OはSchemeポートを使いますが、
コネクションはコミュニケーションに利用できるポートを得るのに使えるほか、
通信相手の名前を得たり、通信をシャットダウンする操作を提供します。
@c COMMON

@c EN
The @code{<socket>} class, for example, implements the connection
framework (@pxref{Networking}).  The @code{<tls>} class, which
wraps a socket to provide TLS communication, also implements it.
That means you can write a client code that works both plain
socket connection and secure connection.
You can also abstract communication to the external process
as a connection (@pxref{Process connection}).
@c JP
例えば@code{<socket>}クラスはコネクションフレームワークを実装しています
(@ref{Networking}参照)。
ソケットをラップしてTLS通信を提供する@code{<tls>}クラスも、
コネクションフレームワークを実装しています。
すると、生のソケットでもTLSソケットでも同じように使えるクライアントコードを書くことができます。
また、外部プロセスとの通信をコネクションとして抽象化することもできます
(@ref{Process connection}参照)。
@c COMMON

@c EN
Each of the connection endpoints (@emph{self} for our side,
and @emph{peer} fo the other side) has @emph{addresses},
some object that identifies the endpoint.  The framework
doesn't specify the actual type of addresses; it only requires
that addresses can be passed to @code{connection-address-name} method
to get its string representation, so that can be used for logging
and monitoring.  The concrete
class can choose suitable address representation.  For example,
@code{<socket>} uses @code{<sockaddr>} for the addresses.
@c JP
コネクションのエンドポイント(自分自身を@emph{self}、相手を@emph{peer}と呼びます)は
それぞれエンドポイントを同定する@emph{アドレス}を持ちます。
このフレームワークではアドレスの具体的な型は指定しません。ただ、
アドレスは@code{connection-address-name}に渡せば
わかりやすい文字列表現を得られるので、ロギングやモニタリングに使えます。
コネクションの具体クラスはアドレスをどう表現するかを選べます。
例えば@code{<socket>}は@code{<sockaddr>}をアドレスとして使います。
@c COMMON

@c EN
A concrete class must implement the following methods.
@c JP
具体クラスは以下のメソッドを実装しなければなりません。
@c COMMON

@example
connection-self-address (c <connection>)
connection-peer-address (c <connection>)
connection-input-port (c <connection>)
connection-output-port (c <connection>)
connection-shutdown (c <connection>) how
connection-close (c <connection>)
connection-address-name obj                ; optional
@end example

@c EN
At this moment this framework doesn't provide a generic way to
@emph{create} a connection, since the way to do it may greatly vary
depending on the concrete implementation.  Each concrete implementation
should provide its own procedure to create and return a new connection.
@c JP
今のところ、このフレームワークはコネクションを作るジェネリックな方法は提供しません。
それは具体的な実装によって大きく異なるからです。
各具体クラスは、新たなコネクションを返す独自の手続きを提供しなければなりません。
@c COMMON
@end deftp


@deffn {Method} connection-self-address connection
@deffnx {Method} connection-peer-address connection
@c MOD gauche.connection
@c EN
Returns the address of this @var{connection}'s endpoint and
its peer's.  For sockets and @code{<tls>}, it is an instance
of @code{<sockaddr>}.  For processes, it is a string
describing the process.
@c JP
@var{connection}のエンドポイントの自分自身と相手のアドレスをそれぞれ返します。
ソケットと@code{<tls>}オブジェクトでは、アドレスは@code{<sockaddr>}のインスタンスです。
プロセスコネクションでは、プロセスを記述する文字列です。
@c COMMON

@c EN
If @var{connection} is not connected, these methods can return @code{#f}.
@c JP
@var{connection}が接続されていなければ@code{#f}が返されるかもしれません。
@c COMMON

@c EN
The returned value (other than @code{#f}) must be able to
be passed to @code{connection-address-name} method.
@c JP
@code{#f}でない返り値は、@code{connection-address-name}に渡すことができます。
@c COMMON

@c EN
Currently addresses are only used for logging purpose within
the connection framework; however, we may enhance the framework
to add ``connect'' operation, for example, so the concrete class
is encouraged to use objects that can be used to create connections.
@c JP
今のところ、アドレスはロギング用途にのみ使われています。
しかし、将来、``connect'' 操作もこのフレームワークで提供することになるかもしれません。
新たな具体クラスを実装する場合は、可能ならコネクションを作るために渡せるオブジェクトを
アドレスにするのが良いでしょう。
@c COMMON
@end deffn

@deffn {Method} connection-address-name address
@c MOD gauche.connection
@c EN
This method returns a string representation of @var{address}, which is
a returned value from @code{connection-self-address} and
@code{connection-peer-address}.  It is for display/logging.
For sockets, a resonable string representation of socket address is
returned.   The default method just uses
@var{address}'s @code{display}-representation.  If a concrete
class chooses aggregate objects to represent addresses, it should
provide this method as well.
@c JP
このメソッドは、@code{connection-self-address}や@code{connection-peer-address}
から返されるアドレスオブジェクトを取り、その文字列表現を返します。ソケットアドレスの場合は、
読みやすい文字列表示が返されます。デフォルトメソッドはアドレスオブジェクトの
display表示になります。具体クラスはより読みやすい表記を返すメソッドを実装すべきです。
@c COMMON
@end deffn

@deffn {Method} connection-input-port connection
@deffnx {Method} connection-output-port connection
@c MOD gauche.connection
@c EN
Returns an input port and an output port of the connection, respectively.
Writing to the output port sends the data to the peer,
and reading from the input port returns the received data.

If the connection is not connected, or already shutdown or closed,
the return value of these methods are unspecified.
@c JP
コネクションの入力ポートと出力ポートをそれぞれ返します。
出力ポートに書き込むことでデータを送信することができ、
また入力ポートから読み込むことで受信したデータを読み出せます。

コネクションがまだ接続されていなかったり、既にクローズしている場合は
これらのメソッドの戻り値は不定です。
@c COMMON
@end deffn

@deffn {Method} connection-shutdown connection :optional how
@c MOD gauche.connection
@c EN
Shutdown the connection.  You can either shutdown the connection
entirely at once, or shutdown only read or write channel of it.

Shutdown is about telling the peer to terminate the communication.
Usually the peer will detect the termination by reading EOF from
their input channel.  The port corresponding to the shutdown channel
is closed so no further communication is possible.

Note that merely closing the connection doesn't shutdown the
connection---the process may fork after creating the connection,
and in that case, one process may close the connection without
shutting down.
@c JP
コネクションを遮断します。送受信を同時に遮断することも、
送信か受信どちらかのみを遮断することもできます。

遮断は、通信相手に通信の終了を通知する操作です。
通常、送信を遮断すると、通信相手側では受信データとしてEOFが返されます。
遮断したコネクションに対応するポートは閉じられ、以降の操作に使うことはきません。

コネクションをクローズするだけでは、必ずしも通信が遮断されるとは限らないことに
注意してください。例えばコネクションを作った後でプロセスがforkした場合、
一方のプロセスがコネクションを閉じてももう一方のプロセスのコネクションは遮断されません。
@c COMMON

@c EN
The @var{how} argument must be one of those symbols:
@c JP
@var{how}引数は次のいずれかのシンボルです。
@c COMMON
@table @code
@item read
@c EN
Shutdown read channel of the connection.
@c JP
読み込み(受信)チャネルを遮断します。
@c COMMON
@item write
@c EN
Shutdown write channel of the connection.
@c JP
書き込み(送信)チャネルを遮断します。
@c COMMON
@item both
@c EN
Shutdown both channels of the connection.
@c JP
送受信両方のチャネルを遮断します。
@c COMMON
@end table

@c EN
If omitted, @code{both} is assumed.
@c JP
省略時は@code{both}と同じです。
@c COMMON

@c EN
Shutting down already shut down channel has no effect.
@c JP
既に遮断されたチャネルを再び遮断しても何も起きません。
@c COMMON

@c EN
Note: Some concrete implementation of connection may not allow
to shutdown each channels independently.  In such case,
the connection is shut down entirely regardless of @var{how} argument.
@c JP
註: 具体的な実装によっては、送信・受信チャネルを独立して遮断できないかもしれません。
その場合は、@var{how}引数に関わらず送受信両方が遮断されます。
@c COMMON

@c EN
The one-argument case is handled by the default method (it calls
two-argument method with @code{both} as @var{how}).  So the
concrete class only need to define two argument method.
@c JP
@var{how}引数が省略された場合はデフォルトメソッドが@var{how}に@code{both}を
指定したメソッドを呼ぶので、具体クラスは2引数のメソッドのみを定義すれば良いです。
@c COMMON
@end deffn

@deffn {Method} connection-close connection
@c MOD gauche.connection
@c EN
Close the connection.  This destroys the connection and frees
local resources.  Note that this does not shutdown the connection
itself.  For example, when a process forks after establishing a connection and
the parent process closes the connection, the child process can still
communicate with the connection.

If this connection is the only endpoint of this side,
the peer will get an error when it tries to communicate.

See @code{connection-shutdown} for the details of shutting down
a connection.
@c JP
コネクションをクローズします。これはローカルのコネクションオブジェクトを破棄して
リソースを開放します。コネクションそのものが遮断されるわけではないことに注意してください。
例えばコネクション接続後にプロセスがforkし、親プロセスがコネクションをクローズしたとしても、
子プロセスは通信を続けることができます。

このコネクションがローカル側の唯一のエンドポイントである場合は、
こちらがクローズした後に相手が通信しようとすると、相手側でエラーになるでしょう。

コネクションの遮断については@code{connection-shutdown}を参照してください。
@c COMMON
@end deffn

@c ----------------------------------------------------------------------
@node Dictionary framework, Low-level file operations, Connection framework, Library modules - Gauche extensions
@section @code{gauche.dictionary} - Dictionary framework
@c NODE ディクショナリフレームワーク, @code{gauche.dictionary} - ディクショナリフレームワーク

@deftp {Module} gauche.dictionary
@mdindex gauche.dictionary
@c EN
A dictionary is an abstract class for objects that can
map a key to a value.  This module provides some useful generic
functions for dictionaries, plus generic dictionary classes
built on top of other dictionary classes.
@c JP
ディクショナリはキーから値への写像ができるオブジェクトを表わす抽象クラ
スです。このモジュールではディクショナリに対してよく使うジェネリック関数、
および他のディクショナリクラスの上に構築される汎用的なディクショナリクラスを
提供します。
@c COMMON
@end deftp

@menu
* Generic functions for dictionaries::
* Generic dictionaries::
@end menu

@node Generic functions for dictionaries, Generic dictionaries, Dictionary framework, Dictionary framework
@subsection Generic functions for dictionaries
@c NODE ディクショナリのためのジェネリック関数

@c EN
The @code{gauche.dictionary} module provides the following
generic functions as the dictionary protocol.
(Note that @code{call-with-iterator} and
@code{size-of} are from @code{gauche.collection}).

The functions marked with * should be
specialized by each dictionary's implementation.
The functions marked with + return default value if not specialized.
Other functions have fallback implementation that uses the *-marked
generic functions, but the implementation may provide specialized
method for efficiency.
@c JP
@code{gauche.dictionary}モジュールは、ディクショナリプロトコルとして
以下のジェネリックファンクションを提供します
(@code{call-with-iterator}と@code{size-of}は@code{gauche.collection}
のものです)。

これらのジェネリックファンクションのうち、*がついているものは
各ディクショナリの実装が特定化したメソッドを提供しなければなりません。
+がついているものは、ディクショナリの実装が特定化したメソッドを定義しなければ
適切なデフォルト値が返されます。
それ以外のジェネリックファンクションは、*がついているメソッドを使って
実装されていますが、ディクショナリ実装は効率化のために
特定化されたメソッドを定義しているかもしれません。
@c COMMON

@table @b
@item Predicates
@code{dict-immutable?}(+),
@code{dict-transparent?}(+)

@item Accessors
@code{dict-get}(*), @code{dict-exists?}, @code{size-of}(*),
@code{dict-comparator}(*)

@item Mutators
@code{dict-put!}(*), @code{dict-delete!}(*),
@code{dict-push!}, @code{dict-pop!}, @code{dict-update!},
@code{dict-clear!}
@c EN
(If the dictionary is immutable, these methods are not specialized
and the default methods throw an error.)
@c JP
(変更不可なディクショナリの実装では、これらのメソッドは特定化されず、
デフォルトメソッドはエラーを投げます)。
@c COMMON

@item Walkers
@code{call-with-iterator}(*),
@code{dict-find}, @code{dict-any},
@code{dict-fold}, @code{dict-fold-right}, @code{dict-for-each},
@code{dict-map}, @code{dict-keys}, @code{dict-values},
@code{dict->alist}
@end table

@c EN
These generic functions are useful to implement algorithms
common to any dictionary-like objects, a data structure
that maps discrete, finite set of keys to values.
(Theoretically we can think of continuous and/or infinite set of
keys, but implementation-wise it is cleaner to limit the dictionary

Among built-in classes, @code{<hash-table>} and @code{<tree-map>}
implement the dictionary interface.  All the @code{<dbm>} classes
provided by @code{dbm} module also implement it.
@c JP
これらのジェネリック関数は、ディクショナリ(離散的で有限なキーの集合から値の集合への
写像を表現するデータ構造)に対して共通するアルゴリズムを書くのに便利です。
(理論的には連続した、また無限なキーの集合を考えることもできますが、
実装上は有限集合に限る方がずっと簡潔になります。)

組み込みクラスでは、@code{<hash-table>}と@code{<tree-map>}が
ディクショナリのインタフェースを実装しています。@code{dbm}モジュール群の
提供する@code{<dbm>}クラスもそうです。
@c COMMON

@subsubheading Predicates

@deffn {Generic fucntion} dict-immutable? (dict @code{<dictionary>})
@c MOD gauche.dictionary
@c EN
Returns @code{#t} if @var{dict} is immutable, @code{#f} otherwise.
Methods that tries to mutate an immutable dictionary throws an error.
@c JP
@var{dict}が変更不可なら@code{#t}を、変更可能なら@code{#f}を返します。
変更不可なディクショナリに対して変更を加えるメソッドを呼ぶとエラーが投げられます。
@c COMMON

@c EN
If the dictionary implementation does not specialize this method,
the default method returns @code{#t}.
@c JP
ディクショナリの実装がこのメソッドを特殊化しなければ、
デフォルトメソッドは@code{#t}を返します。
@c COMMON
@end deffn

@deffn {Generic Function} dict-transparent? (dict @code{<dictionary>})
@c MOD gauche.dictionary
@c EN
If this method returns a true value, the pretty printer displays
the dictionary with their contents.
Built-in hashtables, for example, are transparent:
@c JP
このメソッドが真の値を返した場合、プリティプリンタがディクショナリを表示する時に
その内容も一緒に表示されます。例えば組み込みのハッシュテーブルはtransparentです。
@c COMMON

@smallexample
gosh$ (alist->hash-table (map-with-index cons "abcdefghijkl") eqv-comparator)
#<hash-table eqv[12]( (1 . #\b) (8 . #\i) (9 . #\j) (2 . #\c) (3 . #\d)
  (10 . #\k) (11 . #\l) (4 . #\e) (5 . #\f) (0 . #\a) (6 . #\g) (7 . #\h))>
@end smallexample

@c EN
Not all dictionaries are like this.  For example, a database-backed
dictionary may not want to run the query every time the instance is
printed.
@c JP
全てのディクショナリがこうではありません。例えばデータベースに基づいたディクショナリ
では、インスタンスを表示する度にクエリを走らせたくはないかもしれません。
@c COMMON

@c EN
If the dictionary implementation does not specialize this method,
the default method returns @code{#f}.
@c JP
ディクショナリの実装がこのメソッドを特殊化しなければ、
デフォルトメソッドは@code{#f}を返します。
@c COMMON
@end deffn

@subsubheading Accessors

@deffn {Generic function} dict-get (dict @code{<dictionary>}) key :optional default
@c MOD gauche.dictionary
@c EN
Returns the value corresponding to the @var{key}.
If the dictionary doesn't have an entry with @var{key},
returns @var{default} when it is provided, or raises an error
if not.
@c JP
@var{key}に関連付けられた値を返します。もし@var{key}を持つエントリが
ディクショナリに無い場合、@var{default}が与えられていればそれを返し、
そうでなければエラーが通知されます。
@c COMMON
@end deffn

@deffn {Generic function} dict-exists? (dict @code{<dictionary>}) key
@c MOD gauche.dictionary
@c EN
Returns @code{#t} if the dictionary has an entry with @var{key},
@code{#f} if not.
@c JP
ディクショナリが@var{key}をキーに持つエントリを保持していれば@code{#t}を、
そうでなければ@code{#f}を返します。
@c COMMON
@end deffn

@deffn {Generic function} dict-comparator (dict @code{<dictionary>})
@c MOD gauche.dictionary
@c EN
Should return a comparator used to compare keys.
@c JP
キーを比較するのに使われるcomparatorを返します。
@c COMMON

@c EN
Note: This method may return @code{#f} if a dictionary implementation
doesn't need to compare keys as a whole (e.g. @code{<trie>} compares
keys element-wise, so no direct key comparator is used.
@xref{Trie}).  The caller need to handle such cases.
@c JP
註: このメソッドは@code{#f}を返すことがあります。ディクショナリが、
キー同士を直接比較しない場合があるからです
(例: @code{<trie>}はキーの各要素ごとに比較するので、キーまるごとの比較器というのは
使いません。@ref{Trie}参照)。呼び出し側は@code{#f}が返る可能性を常に念頭に置いてください。
@c COMMON
@end deffn

@subsubheading Mutators

@deffn {Generic function} dict-put! (dict @code{<dictionary>}) key value
@c MOD gauche.dictionary
@c EN
Puts the mapping from @var{key} to @var{value} into the dictionary.
@c JP
@var{key}から@var{value}への関連づけをディクショナリに追加します。
@c COMMON
@end deffn

@deffn {Generic function} {(setter dict-get)} (dict @code{<dictionary>}) key value
@c MOD gauche.dictionary
@c EN
This works the same as @code{dict-put!}.
@c JP
@code{dict-put!}と同じ動作です。
@c COMMON
@end deffn

@deffn {Generic function} dict-delete! (dict @code{<dictionary>}) key
@c MOD gauche.dictionary
@c EN
Removes an entry with @var{key} form the dictionary.
If the dictionary doesn't have such an entry, this function is noop.
@c JP
ディクショナリから@var{key}をキーに持つエントリを除去します。
@var{key}を持つエントリが無ければ何もしません。
@c COMMON
@end deffn

@deffn {Generic function} dict-clear! (dict @code{<dictionary>})
@c MOD gauche.dictionary
@c EN
Empties the dictionary.  Usually this is much faster than looping
over keys to delete them one by one.
@c JP
ディクショナリを空にします。通常、全キーをループしてひとつづつ消していくよりも
ずっと高速です。
@c COMMON
@end deffn

@deffn {Generic function} dict-push! (dict @code{<dictionary>}) key value
@c MOD gauche.dictionary
@c EN
A shorthand way to say @code{(dict-put! dict key (cons value (dict-get dict key '())))}.  A concrete implementation may be more efficient
(e.g. it may not search @var{key} twice.)
@c JP
@code{(dict-put! dict key (cons value (dict-get dict key '())))} と同じ動作をするメソッドです。具体的な実装によってはもっと効率が良いかもしれません
(@var{key}を2度検索しなくても良い、など)。
@c COMMON
@end deffn

@deffn {Generic function} dict-pop! (dict @code{<dictionary>}) key :optional fallback
@c MOD gauche.dictionary
@c EN
If @code{(dict-get dict key)} is a pair @var{p},
the entry value is replaced with @code{(cdr p)} and the procedure
returns @code{(car p)}.  If no entry for @var{key} is in the table,
or the entry isn't a a pair, the table isn't modified, and
@var{fallback} is returned if given, or an error is raised.
@c JP
@code{(dict-get dict key)}がペア@var{p}であれば、
そのエントリの値が@code{(cdr p)}で置き換えられ、@code{(car p)}の値が
戻り値となります。@var{key}に該当するエントリが無かったり、ペアで無かった場合は
ディクショナリは変更されず、@var{fallback}があればそれが戻り値となり、
無ければエラーが報告されます。
@c COMMON
@end deffn

@deffn {Generic function} dict-update! (dict @code{<dictionary>}) key proc :optional fallback
@c MOD gauche.dictionary
@c EN
Works like the following code, except that the concrete implementation
may be more efficient by looking up @var{key} only once.
@c JP
次のコードのような動作をしますが、具体的な実装は@var{key}を一度しかルックアップ
しないなどより効率良くなっている場合があります。
@c COMMON
@example
(rlet1 x (proc (dict-get dict key fallback))
  (dict-put! dict key x))
@end example
@end deffn

@subsubheading Walkers

@deffn {Generic function} dict-fold (dict @code{<dictionary>}) proc seed
@c MOD gauche.dictionary
@c EN
Calls a procedure @var{proc} over each entry in a dictionary @var{dict},
passing a seed value.  Three arguments are given to @var{proc};
an entry's key, an entry's value, and a seed value.  Initial
seed value is @var{seed}.  The value returned from @var{proc} is used
for the seed value of the next call of @var{proc}.  The result of the
last call of @var{proc} is returned from @var{dict-fold}.
@c JP
@var{dict}の各要素に対して@var{proc}を呼びシード値を次に渡します。
@var{proc}は引数を3つとります。エントリーのキー、エントリーの値、それ
にシード値です。最初のシード値は@var{seed}です。@var{proc}からの返り値
は次の@var{proc}の呼び出しでシード値として使われます。最後の@var{proc}
の呼び出しの結果が@var{dict-fold}の返り値として返されます。
@c COMMON

@c EN
If @var{dict} is @code{<ordered-dictionary>}, @var{proc} is called
in the way to keep the following associative order, where
the key is ordered from @var{K0} (minimum) to @var{Kn} (maximum), and
the corresponding values is from @var{V0} to @var{Vn}:
@c JP
@var{dict}が@code{<ordered-dictionary>}であれば、@var{proc}は以下のよ
うな結合で呼ばれます。ここで、キーは@var{K0}(最小)から@var{Kn}(最大)ま
でで、それに対応する値が@var{V0}から@var{Vn}までであるとします。
@c COMMON
@example
(proc Kn Vn (proc Kn-1 Vn-1 ... (proc K0 V0 seed)))
@end example
@end deffn

@deffn {Generic function} dict-fold-right (dict @code{<ordered-dictionary>}) proc seed
@c MOD gauche.dictionary
@c EN
Like @code{dict-fold}, but the associative order of applying @var{proc}
is reversed as follows:
@c JP
@code{dict-fold}と同じですが、@var{proc}を適用する結合の順が以下のよう
に逆になります。
@c COMMON
@example
(proc K0 V0 (proc K1 V1 ... (proc Kn Vn seed)))
@end example

@c EN
This generic function is only defined on @code{<ordered-dictionary>}.
@c JP
このジェネリック関数は@code{<ordered-dictionary>}上にのみ定義されてい
ます。
@c COMMON
@end deffn

@deffn {Generic function} dict-for-each (dict @code{<dictionary>}) proc
@c MOD gauche.dictionary
@c EN
Calls @var{proc} with a key and a value of every entry in
the dictionary @var{dict}.  For ordered dictionaries, @var{proc}
is guaranteed to be called in the increasing order of keys.
@c JP
ディクショナリ@var{dict}の各エントリーのキーと値に対して@var{proc}を呼
びます。順序付きディクショナリに対しては@var{proc}がキーの昇順に呼ばれ
ることが保証されています。
@c COMMON
@end deffn

@deffn {Generic function} dict-map (dict @code{<dictionary>}) proc
@c MOD gauche.dictionary
@c EN
Calls @var{proc} with a key and a value of every entry in
the dictionary @var{dict}, and gathers the result into a list
and returns it.  For ordered dictionaries, the result is in
the increasing order of keys (it doesn't necessarily mean @var{proc}
is called in that order).
@c JP
ディクショナリ@var{dict}の各エントリーのキーと値に対して@var{proc}を呼
び、結果をリストにまとめて返します。順序付きディクショナリに対しては結
果が最初のキーの順にならびます(が、@var{proc}がキーの昇順に呼ばれるこ
とを保証するものではありません)。
@c COMMON
@end deffn

@deffn {Generic function} dict-keys (dict @code{<dictionary>})
@deffnx {Generic function} dict-values (dict @code{<dictionary>})
@c MOD gauche.dictionary
@c EN
Returns a list of all keys or values of a dictionary @var{dict},
respectively.  For ordered dictionaries, the returned list is
in the increasing order of keys.
@c JP
それぞれ@var{dict}内にあるすべてのキーのリスト、すべての値のリストを返
します。順序付きディクショナリについてはリストの要素はキーの昇順になら
んでいます。
@c COMMON
@end deffn

@deffn {Generic function} dict->alist (dict @code{<dictionary>})
@c MOD gauche.dictionary
@c EN
Returns a list of pairs of key and value in the dictionary.
The order of pairs is undefined.
@c JP
ディクショナリ中の各キーと値の対のリストを返します。対の順番は未定義です。
@c COMMON
@end deffn

@subsubsection Defining dictionary protocol

@defmac define-dict-interface dict-class method proc method2 proc2 @dots{}
@c MOD gauche.dictionary
@c EN
Many dictionary-like datatypes already has their own procedures
that directly corresponds to the generic dictionary API, and adding
dictionary interface tends to become a simple repetition of
@code{define-method}s, like this:
@c JP
ディクショナリ的な性質を持つデータ型はそれぞれ独自の操作手続きを持っていて、
しかもその多くはジェネリックなディクショナリAPIに直接対応しています。
そうなると、ディクショナリインタフェースを実装するコードは
ひたすら@code{define-method}で以下のような似たようなコードを並べてゆくことになりがちです。
@c COMMON

@example
(define-method dict-put! ((dict <my-dict>) key value)
  (my-dict-put! key value))
@end example

@c EN
The @code{define-dict-interface} macro is a convenient way to
define those methods in a batch.  Each @var{method} argument is
a keyword that corresponds to @code{dict-@var{method}}, and @var{proc}
is the name of the datatype-specific procedure.  Here's the definition
of dict interface for @code{<tree-map>} and you'll get the idea.
You don't need to provide every dictionary interface.
@c JP
@code{define-dict-interface}はこれらのメソッドを一気に定義する簡単な方法です。
各@var{method}引数は対応する@code{dict-@var{method}}メソッドに対応し、
@var{proc}がそのメソッドの操作を提供するデータ型特有の手続きです。
例えば@code{<tree-map>}のディクショナリインタフェース定義は以下の通りです。
これを見れば要領はわかるでしょう。全てのディクショナリインタフェースをこのマクロで
定義する必要はありません。
@c COMMON

@smallexample
(define-dict-interface <tree-map>
  :get        tree-map-get
  :put!       tree-map-put!
  :delete!    tree-map-delete!
  :clear!     tree-map-clear!
  :comparator tree-map-comparator
  :exists?    tree-map-exists?
  :fold       tree-map-fold
  :fold-right tree-map-fold-right
  :for-each   tree-map-for-each
  :map        tree-map-map
  :keys       tree-map-keys
  :values     tree-map-values
  :pop!       tree-map-pop!
  :push!      tree-map-push!
  :update!    tree-map-update!
  :->alist    tree-map->alist
  :transparent? (^_ #t))
@end smallexample
@end defmac


@node Generic dictionaries,  , Generic functions for dictionaries, Dictionary framework
@subsection Generic dictionaries
@c NODE 汎用ディクショナリ

@subsubheading Bimap

@deftp {Class} <bimap>
@clindex bimap
@c MOD gauche.dictionary
@c EN
Provides a bidirectional map (@emph{bimap}), a relation between two
set of values, of which you can lookup both ways.
@c JP
2つの値のセットを持ち、一方の値をもう一方の値にマップする
双方向マップ(@emph{bimap})を提供します。
@c COMMON

@c EN
Internally, a bimap consists of two dictionaries, @emph{left} map
and @emph{right} map.  Think a bimap as a relation between @var{x}s
and @var{y}s.  The left map takes an @var{x} as a key and returns
corresponding @var{y} as its value.  The right map takes an @var{y}
as a key and returns corresponding @var{x} as its value.
@c JP
内部的には、bimapは二つのディクショナリ、@emph{left}マップと@emph{right}マップを
持っています。bimapが@var{x}と@var{y}の関係を保持しているとすれば、
leftマップは@var{x}をキーとして対応する@var{y}を返し、
rightマップは@var{y}をキーとして対応する@var{x}を返します。
@c COMMON

@c EN
Currently, @code{<bimap>} only supports strict one-to-one mapping.
Mutating interface (@code{bimap-*-put!}, @code{bimap-*-delete!} etc.)
modifies both left and right maps to maintain this one-to-one mapping.
(In future, we may provide an option to make many-to-one and
many-to-many mappings).
@c JP
@code{<bimap>}は今のところ、厳密な1対1対応のみを扱います。
マップを変更する手続き(@code{bimap-*-put!}, @code{bimap-*-delete!}等)
は両方のマップを変更し、1対1対応が保たれるようにします。
(将来的に、1対nやn対mの対応もサポートするかもしれません)。
@c COMMON

@c EN
A bimap can be used as a dictionary, with the generic dictionary
functions such as @code{dict-get}.  In such cases, the left map takes
precedence; that is, the key given to @code{dict-get} etc. is
regarded as the key to the left map.
@c JP
bimapは単なるディクショナリとして、
@code{dict-get}等のディクショナリインタフェースを使って操作することもできます。
その場合はleftマップが見えます。すなわち@code{dict-map}に渡されるキーは
leftマップへのキーとなります。
@c COMMON
@end deftp

@defun make-bimap left-map right-map :key on-conflict
@c MOD gauche.dictionary
@c EN
Creates a new bimap consists of two dictionaries, @var{left-map}
and @var{right-map}.   It is the caller's responsibility to
choose appropriate type of dictionaries; for example, if you want
to create a relation between a string and a number, you man want
to create it like this:
@c JP
二つのディクショナリ、@var{left-map}と@var{right-map}から新たなbimapを作って
返します。用途に応じた適切なディクショナリを選ぶのは呼出側の責任です。
例えば文字列と数値の関係を保持したいなら、一つの方法は以下のとおりです。
@c COMMON

@example
(make-bimap (make-hash-table 'string=?)  ; string -> number
            (make-hash-table 'eqv?))     ; number -> string
@end example

@c EN
The keyword argument @var{on-conflict} specifies what will happen
when the added entry would conflict the existing entries.
The following values are allowed:
@c JP
キーワード引数@var{on-conflict}は、追加されたエントリが既存のエントリと
衝突する場合の振る舞いを指定します。以下の値が有効です。
@c COMMON

@table @code
@item :supersede
@c EN
This is the default behavior.  Duplicate relations are silently
removed in order to maintain one-to-one mapping.  For example,
suppose a bimap between strings and numbers has had
@code{("foo", 1)} and @code{("bar", 2)}.  When you try to
put @code{("bar", 1)} with this option, the first two entries
are removed.  Returns @code{#t}.
@c JP
デフォルトの振る舞いです。重複するエントリは、1対1対応を維持するために取り除かれます。
例えば文字列と数値のbimapが、@code{("foo", 1)}および@code{("bar", 2)}という
組み合わせを保持していたとします。ここで@code{("bar", 1)}を追加しようとすると、
最初の2つのエントリは黙って削除され、@code{("bar", 1)}だけがbimapに残ります。
このオプションを与えた場合、変更手続きは常に@code{#t}を返します。
@c COMMON

@item :error
@c EN
Raises an error when duplicate relations can occur.
@c JP
重複エントリが発生する場合はエラーが投げられます。
@c COMMON

@item #f
@c EN
When duplicate relations can occur, does nothing and returns @code{#f}.
@c JP
重複エントリが発生し得る場合は、何も変更を行わず、変更手続きは@code{#f}を返します。
@c COMMON
@end table
@end defun

@defun bimap-left bimap
@defunx bimap-right bimap
@c MOD gauche.dictionary
@c EN
Returns the left or right map of @var{bimap}, respectively.
Do not mutate the returned map, or you'll break
the consistency of the bimap.
@c JP
bimapのleftマップとrightマップをそれぞれ返します。
返されたディクショナリを呼出側で変更してはなりません。
@c COMMON
@end defun

@defun bimap-left-get bimap key :optional default
@defunx bimap-right-get bimap key :optional default
@c MOD gauche.dictionary
@c EN
Lookup the value corresponding to the @var{key} in the left or right
map of @var{bimap}.   If no entry is found for @var{key},
@var{default} is returned if provided, otherwise an error is
raised.
@c JP
それじれ、@var{bimap}のleftマップまたはrightマップから@var{key}をルックアップして
対応する値を返します。@var{key}を持つエントリが無い場合、
@var{default}が与えられていればその値を返し、そうでなければエラーを投げます。
@c COMMON
@end defun

@defun bimap-left-exists? bimap key
@defunx bimap-right-exists? bimap key
@c MOD gauche.dictionary
@c EN
Returns @code{#f} if the left or right map of @var{bimap} has an entry of
the key, @code{#t} otherwise.
@c JP
それぞれ、@var{key}が@var{bimap}のleftマップまたはrightマップに存在すれば
@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun bimap-put! bimap x y :key on-conflict
@c MOD gauche.dictionary
@c EN
Put a relation (@var{x}, @var{y}) into the bimap.
After this, @code{(bimap-left-get @var{x})} will return @var{y},
and @code{(bimap-right-get @var{y})} will return @var{x}.
@c JP
関係(@var{x}, @var{y})をbimapに格納します。
この呼び出しの後では、@code{(bimap-left-get @var{x})}が@var{y}を、
@code{(bimap-right-get @var{y})}が@var{x}を返すようになります。
@c COMMON

@c EN
If the bimap already have relations with @var{x} and/or @var{y},
the conflict is handled according to the value of @var{on-conflict};
see @code{make-bimap} for the possible values and their meanings.
The @var{on-conflict} keyword argument can override the
bimap's default setting specified at its creation time.
@c JP
bimapの中に既に関係 (@var{x}, _) もしくは関係 (_, @var{y}) が
含まれていた場合、その衝突の解決は@var{on-conflict}引数によって指定できます。
可能な値は@code{make-bimap}の項を参照してください。@var{on-conflict}引数が
与えられなければbimap作成時の@var{on-conflict}の値が使われます。
@c COMMON
@end defun

@defun bimap-left-delete! bimap key
@defunx bimap-right-delete! bimap key
@c MOD gauche.dictionary
@c EN
Deletes an relation with the given left key or right key from @var{bimap}.
Both left and right maps are modified so that the consistency is maintained.
If there's no relations with given key, these are noop.
@c JP
それぞれ、leftマップもしくはrightマップで@var{key}を持つエントリを@var{bimap}から
削除します。エントリが削除されたら、もう逆方向のマップでも対応するエントリが削除され、
一貫性が保たれます。与えられたキーに対応するエントリが無ければ何もしません。
@c COMMON
@end defun

@c EN
@subsubheading Stacked map
@c JP
@subsubheading スタックマップ
@c COMMON

@deftp {Class} <stacked-map>
@c MOD gauche.dictionary
@c EN
Stacked map allows you to stack (layer) multiple maps (dictionaries)
and treat as if they are a single map.
The upper map "shadows" the lower maps.  Think of nested scopes, for
example.
@c JP
スタックマップは、複数のマップ(ディクショナリ)を積み重ねてひとつのマップのように見せます。
上にあるマップがより下のマップを「シャドウ」します。
例えばネストしたスコープを思い浮かべてください。
@c COMMON

@c EN
As a dictionary, it behaves as follows:
@c JP
ディクショナリとしては、次のように振る舞います。
@c COMMON

@itemize @bullet
@item
@c EN
The @code{dict-get} operation searches the given key from the top
dictionary to the bottom dictionary, returns the first found entry.
@c JP
@code{dict-get}は与えれたキーを一番上のマップから順に探し、
エントリが見つかれば直ちにその値を返します。
@c COMMON
@item
@c EN
The @code{dict-put!} operation always put the entry to the topmost
dictionary.  If there's an entry with the same key exists in a
lower dictionary, it will be shadowed.
If you want to alter the existing entry of non-top dictionary,
use @code{stacked-map-entry-update!}.
@c JP
@code{dict-put!}は常に最上位のマップにエントリを追加します。
より下のマップに同じキーを持つエントリがあった場合、それはシャドウされることになります。
最上位以外のマップのエントリを変更したい場合は、
下の@code{stacked-map-entry-update!}を使ってください。
@c COMMON
@item
@c EN
The @code{dict-delete!} operations deletes all the entries with the
given key from all the dictionaries.  This is for consistency as
a dictionary---you don't want an entry pop up after deleting it.
If you want to delete only from the first entry in the stack,
use @code{stacked-map-entry-delete!}.
@c JP
@code{dict-delete!}は、全てのマップから指定のキーを持つエントリを削除します。
これはディクショナリとしての一貫性のためです。最初に見つかったエントリだけを
削除した場合、より下層のマップに同じキーがあれば、消したはずのキーが消えてないという
ことになってしまいます。最初に見つかったエントリだけを消したい場合は
@code{stacked-map-entry-delete!}を使ってください。
@c COMMON
@item
@c EN
The @code{dict-fold} operation traverse all the dictionaries
from top to bottom.  When there are duplicate keys, the second and after
will be skipped.
@c JP
@code{dict-fold}は、全てのディクショナリを最上位から順に辿ります。
ただし、複数のマップに同じキーがあった場合、最初のエントリ以外は無視します。
@c COMMON
@end itemize
@end deftp

@defun make-stacked-map dic dic2 @dots{}
@defunx make-stacked-map key-comparator dic dic2 @dots{}
@c MOD gauche.dictionary
@c EN
Creates a new stacked map with the given dictionaries
@var{dic} @var{dic2} @dots{}, where @var{dic} is the topmost dictionary.
You can give a comparator
@var{key-comparator} to be used to compare keys during
traversal with @code{dict-fold}.  If @var{key-comparator} is
omitted, the comparator from @var{dic} is used.
The key comparator is returned from @code{dict-comparator}
on the stacked map.
@c JP
与えられたディクショナリ@var{dic} @var{dic2} @dots{}からなる新たなスタックマップを
作って返します。最初に指定されたディクショナリが一番上のディクショナリとなります。
@code{dict-fold}で使われるキーの比較には@var{key-comparator}が使われます。
@var{key-comparator}が省略された場合には、@var{dic}の比較器が使われます。
@code{dict-comparator}をスタックマップに適用するとこのキー比較器が返されます。
@c COMMON
@end defun

@deffn {Method} stacked-map-stack (smap <stacked-map>) (dic <dictionary>)
@c MOD gauche.dictionary
@c EN
Creates a new stacked map, adding @var{dic} on top of the existing
stacked map @var{smap}.  The key comparator is inherited from
@var{smap}.
@c JP
スタックマップ@var{smap}の上に@var{dic}を追加した新たなスタックマップを作って返します。
キー比較器は@var{smap}から引き継がれます。
@c COMMON
@end deffn

@deffn {Method} stacked-map-push! (smap <stacked-map>) (dic <dictionary>)
@c MOD gauche.dictionary
@c EN
Adds @var{dic} on top of the dictionaries @var{smap} holds.
@c JP
スタックマップ@var{smap}の保持するディクショナリスタックの一番上に@var{dic}を追加します。
@c COMMON
@end deffn

@deffn {Method} stacked-map-pop! (smap <stacked-map>)
@c MOD gauche.dictionary
@c EN
Remove the topmost dictionary @var{smap} holds.  An error is signaled
if you attempt to pop from an @var{smap} that has no dictionaries.
@c JP
スタックマップ@var{smap}の一番上のディクショナリを取り除きます。
@var{smap}のディクショナリリストが空の場合はエラーが投げられます。
@c COMMON
@end deffn

@deffn {Method} stacked-map-depth (smap <stacked-map>)
@c MOD gauche.dictionary
@c EN
Returns a number of dictionaries @var{smap} has.
@c JP
@var{smap}の持つディクショナリの数を返します。
@c COMMON
@end deffn

@deffn {Method} stacked-map-entry-update! (smap <stacked-map>) key proc :optional fallback
@c MOD gauche.dictionary
@c EN
Run @code{(dict-update! d @var{key} @var{proc} @var{fallback})} on the
first dictionary @code{d} that has the given key.
@c JP
与えられたキー@var{key}を持つ最初のディクショナリ@code{d}に対して
@code{(dict-update! d @var{key} @var{proc} @var{fallback})}を呼び出します。
@c COMMON

@c EN
This differs from running @code{dict-update!} on @var{smap}; if the topmost
dictionary doesn't have an entry with @var{key} but some lower dictionary has,
@code{dict-update!} takes the existing value and applies @var{proc} to it,
then insert the result to the topmost dictionary, while the original entry
remains intact.
@c JP
これは@var{smap}に@code{dict-update!}を適用するのとは異なります。
@var{key}が一番上のディクショナリにはなく、しかし他のディクショナリにあった場合、
@code{dict-update!}は@var{proc}を呼び出した後、その結果を
一番上のディクショナリに挿入し、他のエントリはそのままにします。
@c COMMON
@end deffn

@deffn {Method} stacked-map-entry-delete! (smap <stacked-map>) key
@c MOD gauche.dictionary
@c EN
Deletes the first entry with @var{key}.  If there's another entry
with @var{key} in a lower dictionary, it will become visible.
@c JP
@var{key}を持つ最初のエントリを削除します。もし他のディクショナリに@var{key}を持つ
エントリがあった場合、以降はそれが見えることになります。
@c COMMON

@c EN
This differs from running @code{dict-delete!} on @var{smap}; it
deletes all entries with @var{key}, so that @code{dict-exists?}
after @code{dict-delete!} is guaranteed to return @code{#f}.
@c JP
これは@var{smap}に@code{dict-delete!}を適用するのとは異なります。
@code{dict-delete!}は@var{key}を持つ全てのエントリを削除します。
従って@code{dict-delete!}の後に@code{dict-exists?}でキーを問い合わせると
必ず@code{#f}が返ります。
@c COMMON
@end deffn


@c ----------------------------------------------------------------------
@node Low-level file operations, Foreign function interface, Dictionary framework, Library modules - Gauche extensions
@section @code{gauche.fcntl} - Low-level file operations
@c NODE 低レベルファイル操作, @code{gauche.fcntl} - 低レベルファイル操作

@deftp {Module} gauche.fcntl
@mdindex gauche.fcntl
@c EN
Provides interface for low-level filesystem operations,
including @code{fcntl(2)}.
@c JP
@code{fcntl(2)}を含む、低レベルのファイルシステム操作のインタフェースを提供します。
@c COMMON
@end deftp

@defun sys-fcntl port-or-fd operation :optional arg
@c MOD gauche.fcntl
@c EN
Performs certain operation on the file specified by @var{port-or-fd},
which should be a port object or an integer
that specifies a system file descriptor.  If it is a port, it must
be associated to the opened file (i.e. @code{port-type}
returns @code{file}, see @ref{Common port operations}).

The operation is specified by an integer @var{operation}.
Several variables are defined for valid @var{operation}.
@c JP
@var{port-or-fd} で指定されたファイルに対して特定の操作をおこないます。
ファイル指定は、ポートオブジェクトもしくはシステムのファイルディスクリプタ
である整数でなくてはなりません。それがポートである場合には、すでにオープン
されたファイルを結びついていなければなりません。
(@code{port-type} が @code{file} を返すようなポートということです。
@ref{Common port operations}参照。)

操作は整数 @var{operation} で指定します。
いくつかの変数が定義されいて、@var{operation} に使用できます。
@c COMMON

@table @code
@item F_GETFD
@vindex F_GETFD
@vindex FD_CLOEXEC
@c EN
Returns flags associated to the file descriptor of @var{port-or-fd}.
The optional argument @var{arg} is not used.   The return value is
an integer whose definition is system specific, except one flag,
@code{FD_CLOEXEC}, which indicates the file descriptor should be
closed on @code{exec}.  See the manual entry of @code{fcntl(2)} of
your system for the details.
@c JP
@var{port-or-fd} のファイルディスクリプタに結びついているフラグを返します。
オプション引数の@var{arg}は使われません。返り値は整数で、その定義はシステム
によります。ただし、@code{FD_CLOEXEC}だけは例外で、これは@code{exec}で
クローズされたことを示しています。
詳しくはあなたのシステムの@code{fcntl(2)}のマニュアルエントリを
参照してください。
@c COMMON

@item F_SETFD
@vindex F_SETFD
@c EN
Sets the file descriptor flags given as @var{arg} to @var{port-or-fd}.
For example, the portable way of setting @code{FL_CLOEXEC} flag is
as follows:
@c JP
@var{port-or-fd}のファイルディスクリプタのフラグを与えられた@var{arg}に
します。たとえば、@code{FL_CLOEXEC}フラグを設定する、互換性のある方法では
次のようにします。
@c COMMON
@example
(sys-fcntl port F_SETFD
          (logior FD_CLOEXEC
                  (sys-fcntl port F_GETFD)))
@end example

@item F_GETFL
@vindex F_GETFL
@c EN
Returns flags associated to the open files specified by @var{port-or-fd}.
The flags includes the following information:
@c JP
@var{port-or-fd}によって指定されたオープンしたファイルに結びついている
フラグを返します。このフラグには以下のような情報が含まれています。
@c COMMON

@itemize @bullet
@item
@vindex O_ACCMODE
@vindex O_RDONLY
@vindex O_WRONLY
@vindex O_RDWR
@c EN
File access mode.  When masked by @code{O_ACCMODE},
it's either one of @code{O_RDONLY}, @code{O_WRONLY} or @code{O_RDWR}.
@c JP
ファイルのアクセスモード。@code{O_ACCMODE} でマスクしたとき、
これは、@code{O_RDONLY}、@code{O_WRONLY}、@code{O_RDWR}のうちどれかひとつです。
@c COMMON
@item
@vindex O_CREAT
@vindex O_EXCL
@vindex O_TRUNC
@c EN
File creation options.  @code{O_CREAT}, @code{O_EXCL} and/or
@c JP
ファイルの作成オプション。@code{O_CREAT}、@code{O_EXCL}のどちらか、または両方。
@c COMMON
@code{O_TRUNC}.
@item
@vindex O_APPEND
@c EN
Whether appending is allowed or not, by @code{O_APPEND}
@c JP
@code{O_APPEND}でマスクしたとき、追記が許されているかどうか。
@c COMMON
@item
@vindex O_CLOEXEC
@c EN
Whether the file is closed automatically on @code{fork}.
@c JP
@code{fork}した時にファイルが自動的にクローズされるかどうか。
@c COMMON
@item
@vindex O_NONBLOCK
@c EN
Whether I/O is blocking or non-blocking, by @code{O_NONBLOCK}.
@c JP
@code{O_NONBLOCK}でマスクしたとき、I/O が非ブロックモードかブロックモードか。
@c COMMON
@item
@vindex O_NOCTTY
@c EN
Whether it grabs terminal control, by @code{O_NOCTTY}.
@c JP
@code{O_NOCTTY}でマスクしたとき、端末制御を切離しているかどうか。
@c COMMON
@item
@vindex O_NOFOLLOW
@c EN
Let the system call fail with @code{ELOOP}
when the pathname is a symbolink link.
@c JP
パス名が指しているものがシンボリックリンクなら、システムコールが@code{ELOOP}で
失敗するようにする。
@c COMMON
@end itemize

@c EN
The system may define system-specific flags.
@c JP
システムが、そのシステム特有のフラグを定義していることがあります。
@c COMMON

@item F_SETFL
@vindex F_SETFL
@c EN
Sets flags to the open files specified by @var{port-or-fd}.
Among the flags listed above, only @code{O_NONBLOCK} and @code{O_APPEND}
can be changed.

Note that @code{F_GETFD}/@code{F_SETFD} concern flags associated
to the file descriptor itself, while @code{F_GETFL}/@code{F_SETFL}
concern flags associated to the opened file itself.  This makes difference
when more than one file descriptor points to the same opened file.
@c JP
@var{port-or-fd}で指定したオープンされたファイルのフラグを設定します。
上に列挙されたフラグのうち、@code{O_NONBLOCK} と @code{O_APPEND} だけが
変更可能です。

@code{F_GETFD}/@code{F_SETFD} はファイルディスクリプタそのものに結びついた
フラグについてであり、一方、@code{F_GETFL}/@code{F_SETFL} はオープンされた
ファイルそのものに結びついているフラグについての操作であることに注意して
ください。この違いは、2つ以上のファイルディスクリプタが同じオープンされた
ファイルを指しているような場合にあらわれます。
@c COMMON

@item F_DUPFD
@vindex F_DUPFD
@c EN
Creates new file descriptor that points to the same file referred by
@var{port-or-fd}.
An integer must be provided as @var{arg}, and that specifies
the minimum value of file descriptor to be assigned.
@c JP
@var{port-or-fd}で参照しているのと同じファイルを指す新しいファイル
ディスクリプタを生成します。
@var{arg}で整数を与えなければなりません。この数は割り当てられる
ファイルディスクリプタの最小値を指定します。
@c COMMON

@item F_GETLK
@vindex F_GETLK
@c EN
The third argument must be provided and be an instance of @code{<sys-flock>}
object described below.  It searches the lock information specified by
@var{arg}, and modifies @var{arg} accordingly.
@c JP
3つめの引数を与えなければなりません。これは、以下に述べる@code{<sys-flock>}
オブジェクトのインスタンスでなければなりません。@var{arg}で指定された
ロック情報を検索し、それにしかるべく変更します。
@c COMMON

@item F_SETLK
@itemx F_SETLKW
@vindex F_SETLK
@vindex F_SETLKW
@c EN
The third argument must be provided and be an instance of @code{<sys-flock>}
object described below.  Sets the advisory file lock according to
@var{arg}.   If the lock is successfully obtained, @code{#t} is returned.
If the other process has the lock conflicting the request,
@code{F_SETLK} returns @code{#f}, while @code{F_SETLKW} waits until
the lock is available.
@c JP
3つめの引数を与えなければなりません。これは、以下に述べる@code{<sys-flock>}
オブジェクトのインスタンスでなければなりません。@var{arg}にしたがって、
アドバイザリロックを設定します。ロックの取得に成功すれば、@code{#t}が
返ります。もし、別のプロセスがロックをもっていて要求したものと衝突した
場合には @code{F_SETLK} のときは @code{#f} を返します。一方、@code{F_SETLKW}
のときはロックが利用可能になるまで待ちます。
@c COMMON

@item F_GETOWN
@vindex F_GETOWN
@c EN
Returns the process id or process group that will receive
SIGIO and SIGURG signals for events on the file descriptor.
Process group is indicated by a negative value.
This flag is only available on the systems that has this
feature (BSD and Linux have this).
@c JP
当該ファイルディスクリプタ上のイベント用シグナル、SIGIO および SIGURG を
受けとることになるプロセスのプロセスIDあるいはプロセスグループを返します。
プロセスグループは負の値で表示されます。このフラグはシステムにこのような
機能がある場合にのみ利用可能です(BSD や Linux にはこの機能があります)。
@c COMMON

@item F_SETOWN
@vindex F_SETOWN
@c EN
Sets the process id or process group that will receive SIGIO
and SIGURG signals for events on the file descriptor.
Process group is indicated by a negative value.
This flag is only available on the systems that has this
feature (BSD and Linux have this).
Check out fcntl(2) manpage of your system for the details.
@c JP
当該ファイルディスクリプタ上のイベント用シグナル、SIGIO および SIGURG を
受けとることになるプロセスのプロセスIDあるいはプロセスグループを設定します。
プロセスグループは負の値で表示されます。このフラグはシステムにこのような
機能がある場合にのみ利用可能です(BSD や Linux にはこの機能があります)。
詳細については、お使いのシステムの fcntl(2) のマニュアルページをチェック
してください。
@c COMMON

@end table

@c EN
Other value for @var{operation} causes an error.
@c JP
これ以外の値を @var{operation} で指定しようとするとエラーになります。
@c COMMON
@end defun

@deftp {Builtin Class} <sys-flock>
@clindex sys-flock
@c MOD gauche.fcntl
@c EN
A structure represents POSIX advisory record locking.
Advisory record locking means the system may not prevents the process
from operating on files that it doesn't have an appropriate lock.
All the processes are expected to use @code{fcntl} to check locks
before it operates on the files that may be shared.

The following slots are defined.
@c JP
POSIX のアドバイザリレコードロックを表わす構造体です。アドバイザリレコードロック
というのは、適切なロックをもたないプロセスが対象ファイルを操作しても
システムは関知しない、ということです。すべてのプロセスが、共有される可能性
のあるファイルを操作する前にロックを@code{fcntl}を使って検査することが
期待されています。
@c COMMON

@c EN
Note that @code{fcntl} lock is per-process, per-file.  If you try
to lock the same file more than once within the same process, it always
succeeds.  But it's not a recursive lock, so the process loses
any locks to the file as soon as any of such lock is released,
or any of such file is closed.   It makes @code{fcntl} lock difficult
to use in libraries.  See @code{with-lock-file} (@pxref{Lock files}) for
an alternative way to realize inter-process locks.
@c JP
@code{fcntl}によるロックは、プロセスごと、ファイルごとであることに注意してください。
同一プロセス内で同じファイルを複数回ロックすることはできますが、再帰ロックではないので
いずれかのロックがアンロックされるか、どこかでそのファイルがクローズされるかすると
プロセスはそのファイルに対するロックを失います。これは、@code{fcntl}ロックを
ライブラリで使うことを難しくします。プロセス間排他制御を実現する別の方法として
@code{with-lock-file} (@ref{Lock files}参照) があります。
@c COMMON

@defivar {<sys-flock>} type
@c EN
An integer represents lock type.  Following variables are predefined
for the valid values:
@c JP
ロックのタイプを表す整数です。利用可能な値として以下の変数があらかじめ
定義されています。
@c COMMON

@table @code
@item F_RDLCK
@vindex F_RDLCK
@c EN
Read locking
@c JP
読み込みのロック
@c COMMON
@item F_WRLCK
@vindex F_WRLCK
@c EN
Write locking
@c JP
書き込みのロック
@c COMMON
@item F_UNLCK
@vindex F_UNLCK

@c EN
To remove a lock by @code{F_SETLK}, or to indicate the record is not
locked by @code{F_GETLK}.
@c JP
@code{F_SETLK}によるロックを除去するか、あるいはレコードが@code{F_GETLK}
でロックされていないことを示す。
@c COMMON
@end table
@end defivar

@defivar {<sys-flock>} whence
@c EN
Indicates from where @code{start} is measured.
@c JP
@code{start}の計測が開始される位置を示す。
@c COMMON
@end defivar

@defivar {<sys-flock>} start
@c EN
The offset of beginning of the locked region.
@c JP
ロックされる領域の開始位置オフセット
@c COMMON
@end defivar

@defivar {<sys-flock>} len
@c EN
The number of bytes to lock.  Zero means ``until EOF''.
@c JP
ロックされるバイト数。ゼロは「EOFまで」という意味。
@c COMMON
@end defivar

@defivar {<sys-flock>} pid
@c EN
An integer process id that holding the lock; used only by @code{F_GETLK}.
@c JP
当該のロックをもっている整数のプロセスID。@code{F_GETLK}でのみ使用。
@c COMMON
@end defivar
@end deftp


@defun sys-open path flags :optional mode
@c MOD gauche.fcntl
@c EN
A low-level interface corresponds to POSIX open().
Open a file named by @var{path}, and returns an integer file descriptor.
The file descriptor should be closed with @code{sys-close},
or can be turned into a port by @code{open-@{input|output@}-fd-oprt}
and to be closed when the port is closed.

This is provided for the code that needs to deal with low-level fd.
Unless absolutely necessary, user code should use
high-level @code{open-@{input|output@}-file}.

The @var{flags} argument is a logical ior of
bitmasks @code{O_RDONLY}, @code{O_WRONLY}, @code{O_RDWR},
@code{O_APPEND}, @code{O_CREAT}, @code{O_EXCL}, @code{O_TRUNC},
@code{O_CLOEXEC}, @code{O_NOCTTY}, @code{O_NOFOLLOW},
@code{O_NONBLOCK} and @code{O_ASYNC}.  Either one of
@code{O_RDONLY}, @code{O_WRONLY} or @code{O_RDWR} must present.

The @var{mode} argument specifies the permission bits
when a new file is created.  The default is @code{#o664}.
@c JP
POSIX open()への低レベルインタフェースです。
@var{path}で指定されるファイルをオープンして、整数のファイルディスクリプタを返します。
ファイルディスクリプタは@code{sys-close}でクローズするか、
@code{open-@{input|output@}-fd-oprt}でポートに変換して
ポートがクローズされた時に一緒にクローズすることができます。

この手続きはfdを直接触る必要がある低レベルコードのために提供されています。
どうしても必要な場合以外には、高レベルの@code{open-@{input|output@}-file}を使ってください。

@var{flags}引数は次のビットマスクの論理和です:
@code{O_RDONLY}, @code{O_WRONLY}, @code{O_RDWR},
@code{O_APPEND}, @code{O_CREAT}, @code{O_EXCL}, @code{O_TRUNC},
@code{O_CLOEXEC}, @code{O_NOCTTY}, @code{O_NOFOLLOW},
@code{O_NONBLOCK}, @code{O_ASYNC}。
このうち@code{O_RDONLY}, @code{O_WRONLY}, @code{O_RDWR}のどれかひとつは
指定しなければなりません。

@var{mode}引数はファイルが新たに作られた時のパーミッションです。
デフォルトは@code{#o664}です。
@c COMMON
@end defun


@defun sys-statvfs path
@defunx sys-fstatvfs port-or-fd
@c MOD gauche.fcntl
@c EN
Interface to POSIX @code{statvfs} and @code{fstatvfs}.

Returns information about the filesystem where @var{path}, or
a file associated to @var{port-or-fd}, as @code{<sys-statvfs>} instance
described below.

These procedures are only defined if the system supports them.
You can use the feature identifier @code{gauche.sys.statvfs}
for the availability (@pxref{Feature conditional}).
@c JP
POSIX @code{statvfs}および@code{fstatvfs}へのインタフェースです。

@var{path}、もしくは@var{port-or-fd}に結びついたファイルが存在するファイルシステムの情報を
下に説明する@code{<sys-statvfs>}のインスタンスとして返します。

これらの手続きは対応するPOSIXシステムコールが提供されているシステムでのみ
定義されます。使えるかどうかは、機能識別子@code{gauche.sys.statvfs}で
検査できます (@ref{Feature conditional}参照)。
@c COMMON

@example
(cond-expand
  [gauche.sys.statvfs
    (... code using sys-statvfs ...)]
  [else
    (... alternative code ...)])
@end example
@end defun

@deftp {Builtin Class} <sys-statvfs>
@clindex sys-statvfs
@c MOD gauche.fcntl
@c EN
POSIX @code{struct statvfs}.
This class is only defined if a feature @code{gauche.sys.statvfs} is
provided.
@c JP
POSIXの@code{struct statvfs}です。
機能識別子 @code{gauche.sys.statvfs}が提供されている場合のみ定義されます。
@c COMMON

@defivar {<sys-statvfs>} bsize
@c EN
Filesystem block size.
@c JP
ファイルシステムのブロックサイズ。
@c COMMON
@end defivar

@defivar {<sys-statvfs>} frsize
@c EN
Fragment size.
@c JP
フラグメントサイズ。
@c COMMON
@end defivar

@defivar {<sys-statvfs>} blocks
@defivarx {<sys-statvfs>} bfree
@defivarx {<sys-statvfs>} bavail
@c EN
Number of blocks, number of free blocks, and number of free blocks
for unprivileged users, in @code{frsize} units.
@c JP
ファイルシステムが格納できるブロック数、未使用ブロック数、
非特権ユーザが使える未使用ブロック数を、@code{frsize}を単位として表します。
@c COMMON
@end defivar

@defivar {<sys-statvfs>} files
@defivarx {<sys-statvfs>} ffree
@defivarx {<sys-statvfs>} favail
@c EN
Number of inodes, number of free inodes, and number of free inodes
for unprivileged users.
@c JP
ファイルシステム中の全inode数、未使用inode数、非特権ユーザが使える未使用inode数です。
@c COMMON
@end defivar

@defivar {<sys-statvfs>} fsid
@c EN
An exact integer filesystem ID.
@c JP
ファイルシステムID。正確な整数です。
@c COMMON
@end defivar

@defivar {<sys-statvfs>} flag
@c EN
An exact integer, logical IOR of the bitflags.
Portable bitflag values is provided with constants
@code{ST_NOSUID} a @code{ST_RDONLY}.
@c JP
正確な整数。ビットフラグのORです。
ポータブルなビットフラグ値として、定数@code{ST_NOSUID}と@code{ST_RDONLY}が定義されています。
@c COMMON
@end defivar

@defivar {<sys-statvfs>} namemax
@c EN
Maximum filename length.
@c JP
ファイル名の長さの上限。
@c COMMON
@end defivar
@end deftp

@defvr {Constant} ST_NOSUID
@defvrx {Constant} ST_RDONLY
@c MOD gauche.fcntl
@c EN
Bitflag values that can be used in @code{flag} slot of @code{<sys-statvfs>}.
These constants are only defined if a feature @code{gauche.sys.statvfs} is
provided.

If @code{ST_NOSUID} bit is on, suid and sgid bits of the files on this
filesystem are ignored by @code{exec(3)}.

If @code{ST_RDONLY} bit is on, the filesystem is mounted read-only.
@c JP
@code{<sys-statvfs>}の@code{flag}スロットに使えるビットフラグ値です。
これらは機能識別子 @code{gauche.sys.statvfs}が提供されている場合のみ定義されます。

@code{ST_NOSUID}ビットが立っていたら、@code{exec(3)}はこのファイルシステム中のファイルの
suidビットとsgidビットを無視します。

@code{ST_RDONLY}ビットが立っていたら、このファイルシステムは読み取り専用でマウントされています。
@c COMMON
@end defvr

@c ----------------------------------------------------------------------
@node Foreign function interface, Generators, Low-level file operations, Library modules - Gauche extensions
@section @code{gauche.FFI} - Foreign function interface
@c NODE FFI, @code{gauche.ffi} - FFI

@deftp {Module} gauche.ffi
@mdindex gauche.ffi
This module provides the means to call compiled functions in other
langauges via C ABI.  It allows user programs to use external libraries
without writing a custom extension.

Although it is convenient, you need to keep in mind that
the external libraries does not necessarily aligns Gauche's runtime
conventions, therefore you cannot rely on Gauche's guardrails.
You can easily pass arguments of incorrect types, interpret
the result incorrectly, or access objects outside of its lifetime.
Small mistakes can eaisly cause access violation or memory corruption.

We adopt pluggable subsystems; you can choose the underlying FFI layer
depending on the architecture and your particular needs.
For the time being, @code{stubgen} subsystem is available on
all the architecture, and @code{native} subsystem on x86_64 with
with Unix-like systems and MinGW/Windows.  Native subsytem will
be enhanced to Aarch64 soon.

The code that uses FFI looks like the following:

@example
(use gauche.ffi)
(use gauche.native-type)

(with-ffi (dynamic-load "/path/to/library") ()
  ;; Define C functions and callbacks
  (define-c-function foo '(int c-string) 'int)
  ...
  )

;; Call the defined C function
(foo 4 "bar")
@end example

Foreign functions are defined within the form `with-ffi`.
Inside the form, you can define C functions and C callbacks.
The defined C functions are visible from the rest of the code,
and you can call it as a Scheme function.
@end deftp





@c ----------------------------------------------------------------------
@node Generators, Hooks, Foreign function interface, Library modules - Gauche extensions
@section @code{gauche.generator} - Generators
@c NODE ジェネレータ, @code{gauche.generator} - ジェネレータ

@deftp {Module} gauche.generator
@mdindex gauche.generator
@c EN
A generator is merely a procedure with no arguments and works
as a source of a series of values.  Every time it is called,
it yields a value.  The EOF value indicates the generator is exhausted.
For example, @code{read-char} can be seen as a generator that
generates characters from the current input port.

It is common practice to abstract the source of values in such a way,
so it is useful to define utility procedures that work on the
generators.  This module provides them.
@c JP
ジェネレータは、値の列の生成器として動作する、引数を取らない手続きです。
呼ばれる度に列の次の値を返します。列の終端に達した場合はEOFが返されます。
例えば、@code{read-char}は、現在の入力ポートからの入力を一文字づつ返す
ジェネレータと考えることができます。

値の列の生成源を手続きによってジェネレータとして抽象化するのは広く使われるテクニックなので、
このようなジェネレータに共通して使えるユーティリティがあると便利です。
このモジュールはそのために作られました。
@c COMMON

@c EN
SRFI-121 (Generators) is a subset of this module.
Since @code{gauche.generator} predates SRFI-121, we have different
names for some procedures; for the compatibility, we provide
both names.  SRFI-151 (Generators and accumulators) adds some more
generator procedures, which is also included (but accumulator procedures
are left to SRFI-158. @xref{R7RS generators}.)
@c JP
SRFI-121 (Generators) はこのモジュールのサブセットです。
@code{gauche.generator}はSRFI-121より前からあったので、
いくつかの手続きについては異なる名前を使っていました。互換性のため、
それらの手続きは両方の名前を定義しています。
SRFI-158 (Generators and accumulators)はさらに追加のジェネレータ手続きを
定義していますが、それらもこのモジュールに含まれています
(ただし、アキュムレータについてはSRFI-158モジュールに分けてあります。
@ref{R7RS generators}参照)。
@c COMMON
@end deftp

@c EN
A generator is very lightweight, and handy to implement simple
on-demand calculations.  However, keep in mind that it is
side-effecting construct; you can't safely backtrack, for example.
For more functional on-demand calculation, you can use
lazy sequences (@pxref{Lazy sequences}), which is actually
built on top of generators.
@c JP
ジェネレータは、必要になったら計算を行うようなシステムを簡単に実現でき、
効率も極めて良いですが、副作用に頼った抽象化であることには注意が必要です。
例えば、途中まで列を生成した後に、最初にもどってやり直す、といったことはできません。
より関数的にオンデマンドの計算を行うためには、ジェネレータを使って
構築された、遅延シーケンスを使うのが便利です (@ref{Lazy sequences}参照)。
@c COMMON

@c EN
The typical pattern of using generator is as follows: First you
create a source or sources of the values,
using one of generator constructors
(@pxref{Generator constructors}) or rolling your own one.  You
may connect generator operators that modifies the stream of
generated items as you wish (@pxref{Generator operations}).
Eventually you need to extract actual values from the generator
to consume; there are utility procedures provided
(@pxref{Generator consumers}).  Overall, you create a pipeline
(or DAG) of generators that works as lazy value-propagation network.
@c JP
ジェネレータの典型的な使い方は次の通りです。まず値の源となる
ジェネレータを作ります。これはジェネレータの生成手続きを使っても良いですし
(@ref{Generator constructors}参照)、自分で一から定義しても良いでしょう。
次に、生成される値を流れの途中で加工するジェネレータ操作手続きを
必要に応じて繋いでゆきます(@ref{Generator operations}参照)。
最終的には、ジェネレータから具体的な値を取り出して消費する必要があります。
そのために便利なジェネレータ消費手続きも用意してあります
@ref{Generator consumers}参照)。このように、ジェネレータ手続きを組み合わせた
パイプライン(あるいは有向非循環グラフ)を作ることで、怠惰な値伝搬ネットワークを
実現できます。
@c COMMON

@menu
* Generator constructors::
* Generator operations::
* Generator consumers::
@end menu

@node Generator constructors, Generator operations, Generators, Generators
@subsection Generator constructors
@c NODE ジェネレータの生成

@c EN
A generator isn't a special datatype but just an ordinary procedure,
so you can make a generator with lambdas.  This module provides
some common generator constructors for the convenience.
@c JP
ジェネレータは特別なデータタイプではなく、普通の手続きに過ぎません。つ
まり、ジェネレータはlambdaを使って作ることができます。
このモジュールは、あると便利な
良く使われるジェネレータの構築子を提供します。
@c COMMON

@c EN
If you want to use your procedure as a generator, note that a
generator can be invoked many times even after it returns EOF once.
You have to code it so that once it returns EOF, it keeps returning
EOF for the subsequent calls.
@c JP
自分で定義した手続きをジェネレータとして使うこともできますが、
ジェネレータを扱う手続きは、
一度EOFを返したジェネレータを繰り返して呼び出す可能性があることに注意してください。
その手続きがいったんEOFを返したら、それ以降の呼び出しに対してEOFを
返し続けるよう書かなければなりません。
@c COMMON

@c EN
The result of generator constructors is merely a procedure,
and printing it doesn't show much.  In the examples in this section
we use @code{generator->list} to convert the generator to the list.
See @ref{Generator consumers} for the description of @code{generator->list}.
@c JP
ジェネレータ構築子が返すのは単なる手続きであり、そのまま印字しても
中身が何かはわかりません。この節の例では、@code{generator->list}を使って
ジェネレータをリストに変換しています。@code{generator->list}の説明は、
@ref{Generator consumers}を参照してください。
@c COMMON

@defun null-generator
@c MOD gauche.generator
@c EN
An empty generator.  Returns just an EOF object when called.
@c JP
空ジェネレータです。呼ばれるたびにEOFオブジェクトを返します。
@c COMMON
@end defun

@defun circular-generator arg @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns an infinite generator that repeats the given arguments.
@c JP
与えられた引数を繰り返し生成する、無限ジェネレータを返します。
@c COMMON

@example
(generator->list (circular-generator 1 2 3) 10)
  @result{} (1 2 3 1 2 3 1 2 3 1)
@end example

@c EN
Note that the above example limits the length of
the converted list by 10; otherwise
@code{generator->list} won't return.
@c JP
この例では、変換後のリストの長さを10に制限しています。そうしなければ、
@code{generator->list}は制御を返さないでしょう。
@c COMMON
@end defun

@defun giota :optional (count +inf.0) (start 0) (step 1)
@c MOD gauche.generator
@c EN
Like @code{iota} (@pxref{List constructors}), creates a generator
of a series of @var{count} numbers, starting from @var{start}
and increased by @var{step}.
@c JP
@code{iota} (@pxref{List constructors})のような、@var{start}で始まり
@var{step}ずつ増加する、@var{count}個の級数のジェネレータを作成します。
@c COMMON

@example
(generator->list (giota 10 3 2))
  @result{} (3 5 7 9 11 13 15 17 19 21)
@end example

@c EN
If both @var{start} and @var{step} are exact, the generator
yields exact numbers; otherwise it yields inexact numbers.
@c JP
@var{start}と@var{step}がともに正確数であれば、ジェネレータは
正確数を生成します。そうでなければ非正確数を生成します。
@c COMMON

@example
(generator->list (giota +inf.0 1/2 1/3) 6)
  @result{} (1/2 5/6 7/6 3/2 11/6 13/6)
(generator->list (giota +inf.0 1.0 2.0) 5)
  @result{} (1.0 3.0 5.0 7.0 9.0)
@end example
@end defun

@defun grange start :optional (end +inf.0) (step 1)
@c MOD gauche.generator
@c EN
Similar to @code{giota}, creates a generator of a series of
numbers.  The series begins with @var{start}, increased by @var{step},
and continues while the number is below @var{end}.
@c JP
@code{giota}と同様、級数ジェネレータを作成します。この級数は
@var{start}に始まり、@var{step}ずつ増加して@var{end}直前まで続きます。
@c COMMON

@example
(generator->list (grange 3 8))
  @result{} (3 4 5 6 7)
@end example

@c EN
If both @var{start} and @var{step} are exact,
it generates exat numbers. Otherwise, it generates inexact
numbers.  (The exactness of @var{end} does not affect the exactness
of generated numbers.)
@c JP
@var{start}と@var{step}がともに正確数であれば正確数が、
そうでなければ非正確数が生成されます。
(@var{end}の正確性は結果には影響しません。)
@c COMMON
@end defun

@defun generate proc
@c MOD gauche.generator
@c EN
Creates a generator from coroutine.
@c JP
コルーチンからジェネレータを作成します。
@c COMMON

@c EN
The @var{proc} argument is a procedure that takes one argument,
@var{yield}.   When called, @code{generate} immediately returns
a generator @var{G}.  When @var{G} is called, the @var{proc} runs
until it calls @var{yield}.  Calling @var{yield} causes to suspend
the execution of @var{proc} and @var{G} returns the value passed
to @var{yield}.  Calling @var{G} again resumes the calculation
in @var{proc}.
@c JP
引数@var{proc}は、引数@var{yield}ひとつを取る手続きです。
@code{generate}は、呼ばれるとジェネレータ@var{G}をただちに返します。
@var{G}は呼ばれると、その中で@var{yield}が呼ばれるまで@var{proc}を
実行します。@var{yield}が呼ばれると@var{proc}の実行は中断され、
@var{yield}に渡した値が@var{G}から返ります。
@var{G}を再び呼び出すと、中断された@var{proc}の実行が再開されます。
@c COMMON

@c EN
Once @var{proc} returns, it is the end of the series---@var{G} returns
eof object from then on.  The return value of @var{proc} is ignored.
@c JP
いったん@var{proc}が返ると、それが列の終端となります---それ以降、
@var{G}はEOFオブジェクトを返します。@var{proc}が返す値は無視されます。
@c COMMON

@c EN
The following code creates a generator that produces a series
0, 1, and 2 (effectively the same as @code{(giota 3)} and binds
it to @code{g}.
@c JP
次に挙げるコードは、0、1、2からなる級数を生成するジェネレータを作成し
(事実上、@code{(giota 3)}と同じ)、@code{g}に束縛しています。
@c COMMON

@example
(define g
  (generate
   (^[yield] (let loop ([i 0])
               (when (< i 3) (yield i) (loop (+ i 1)))))))

(generator->list g) @result{} (0 1 2)
@end example
@end defun

@defun list->generator lis :optional start end
@defunx vector->generator vec :optional start end
@defunx reverse-vector->generator vec :optional start end
@defunx string->generator str :optional start end
@defunx uvector->generator uvec :optional start end
@defunx bytevector->generator u8vector :optional start end
[SRFI-158+]
@c MOD gauche.generator
@c EN
Returns a generator that yields each item in the given argument.
A generator returned from @code{reverse-*} procedures runs in
reverse order.
SRFI-121 defines these except @code{uvector->generator}, which can
take any type of uniform vectors.  The SRFI-121 version,
@code{bytevector->generator}, limits the argument to @code{u8vector}.
@c JP
実引数の各要素を生成するジェネレータを返します。
@code{reverse-*}は、逆順で値を生成します。
SRFI-121は@code{uvector->generator}以外の手続きを定義しています。
@code{uvector->generator}は全ての種類のユニフォームベクタを取ることができます。
一方、SRFI-121も定義する@code{bytevector->generator}は@code{u8vector}だけを
対象とします。
@c COMMON

@example
(generator->list (list->generator '(1 2 3 4 5)))
  @result{} (1 2 3 4 5)
(generator->list (vector->generator '#(1 2 3 4 5)))
  @result{} (1 2 3 4 5)
(generator->list (reverse-vector->generator '#(1 2 3 4 5)))
  @result{} (5 4 3 2 1)
(generator->list (string->generator "abcde"))
  @result{} (#\a #\b #\c #\d #\e)
(generator->list (uvector->generator '#u8(1 2 3 4 5)))
  @result{} (1 2 3 4 5)
@end example

@c EN
The generator is exhausted once all items are retrieved;
the optional @var{start} and @var{end} arguments can limit the range
the generator walks across; @var{start} specifies the left bound
and @var{end} specifies the right bound.
@c JP
いったん全ての要素を取り出してしまえば
そのジェネレータは空になります;省略可能引数@var{start}と@var{end}で
ジェネレータがたどる範囲を制限することができます;@var{start}で
左の境界を、@var{end}で右の境界を指定します。
@c COMMON

@c EN
For forward generators, the first value the generator yields
is @var{start}-th element, and it ends right before @var{end}-th element.
For reverse generators, the first value is the item right next
to the @var{end}-th element, and the last value is the @var{start}-th
element.
at the last element, and reverse generators ends at the first element.
@c JP
正順のジェネレータでは、最初の値としてジェネレータが生成するのは
@var{start}番目の要素であり、@var{end}番目の要素の直前の要素が最後に生成する
値となります。逆順のジェネレータでは、最初の値は@var{end}番目の要素の
すぐ隣の要素であり、最後の値が@var{start}番目の要素となります。
@c COMMON

@example
(generator->list (vector->generator '#(a b c d e) 2))
  @result{} (c d e)
(generator->list (vector->generator '#(a b c d e) 2 4))
  @result{} (c d)
(generator->list (reverse-vector->generator '#(a b c d e) 2))
  @result{} (e d c b)
(generator->list (reverse-vector->generator '#(a b c d e) 2 4))
  @result{} (d c)
(generator->list (reverse-vector->generator '#(a b c d e) #f 2))
  @result{} (b a)
@end example
@end defun

@defun bits->generator n :optional start end
@defunx reverse-bits->generator n :optional start end
@c MOD gauche.generator
@c EN
These procedures take an exact integer and treat it as a sequence of
boolean values (0 for false and 1 for true), as @code{bits->list} does
(@pxref{R7RS bitwise operations}).  @code{Bits->generator} takes bits from
LSB, while @code{reverse-bits->generator} takes them from MSB.
@c JP
これらの手続きは正確な整数を引数に取り、
@code{bits->list}と同様に(@ref{R7RS bitwise operations}参照)、
それを真偽値のシーケンス(0が偽、1を真)として扱います。
@code{bits->generator}はLSBから、@code{reverse-bits->generator}は
MSBからビットを取り出します。
@c COMMON

@example
(generator->list (bits->generator #b10110))
 @result{} (#f #t #t #f #t)
(generator->list (reverse-bits->generator #b10110))
 @result{} (#t #f #t #t #f)
@end example

@c EN
The optional @var{start} and/or @var{end} arguments are used to specify
the range of bitfield, LSB being 0.  Unlike @code{list->generator} etc,
@var{start} specifies the rightmost position (inclusive) and
@var{end} specifies the leftmost position (exclusive).  It is consistent
with other procedures that accesses bit fields in integers
(@pxref{R7RS bitwise operations}).
@c JP
省略可能引数@var{start}と@var{end}はビットフィールドの範囲を指定します
(LSBが0)。@code{list->generator}等の同名の引数と違って、
@var{start}が右端(含まれる)、@var{end}が左端(含まれない)を指定します。
この指定方法は整数のビットフィールドにアクセスする他の手続きと一貫しています
(@ref{R7RS bitwise operations}参照)。
@c COMMON

@example
(generator->list (bits->generator #x56 0 4)
  @result{} (#f #t #t #f)  ; takes bit 0, 1, 2 and 3
(generator->list (bits->generator #x56 4 8)
  @result{} (#t #f #t #f)  ; takes bit 4, 5, 6 and 7

(generator->list (reverse-bits->generator #x56 4 8)
  @result{} (#f #t #f #t)  ; takes bit 7, 6, 5 and 4
@end example

@c EN
Note: SRFI-151's @code{make-bitwise-generator} is similar to
@code{bits->generator}, except that it produces an infinite generator.
@xref{R7RS bitwise operations}.
@c JP
註: SRFI-151の@code{make-bitwise-generator}は
@code{bits->generator}と似ていますが、生成されるジェネレータは無限ジェネレータになります。
@ref{R7RS bitwise operations}参照。
@c COMMON
@end defun

@defun port->sexp-generator input-port
@defunx port->line-generator input-port
@defunx port->char-generator input-port
@defunx port->byte-generator input-port
@c MOD gauche.generator
@c EN
Returns a generator that reads characters or bytes from the given
port, respectively.  They're just
@code{(cut read input-port)},
@code{(cut read-line input-port)},
@code{(cut read-char input-port)}
and @code{(cut read-byte input-port)}, respectively,
but we provide them for completeness.
@c JP
それぞれ文字、バイトを与えられた入力ポートから読み取るジェネレータを
返します。つまり、それぞれ
@code{(cut read input-port)}、
@code{(cut read-line input-port)}、
@code{(cut read-char input-port)}、
@code{(cut read-byte input-port)}
と同じですが、完全性のために提供されています。
@c COMMON
@end defun

@deffn {Generic function} x->generator obj
@c MOD gauche.generator
@c EN
A generic version to convert any collection @var{obj} to a generator
that walks across the @var{obj}.  Besides, if @var{obj} is an input port,
@code{port->char-generator} is called.
@c JP
任意のコレクション@var{obj}を、@var{obj}をたどるジェネレータに変換する
ジェネリック関数版です。さらに、@var{obj}が入力ポートである場合は、
@code{port->char-generator}を呼びます。
@c COMMON
@end deffn

@defun file->generator filename reader . open-args
@c MOD gauche.generator
@c EN
Opens a file @var{filename}, and returns a generator
that reads items from the file
by a procedure @var{reader}, which takes one argument, an input port.
The arguments @var{open-args} are passed to @code{open-input-file}
@c JP
ファイル@var{filename}をオープンし、入力ポートを引数に取る手続き
@var{reader}によってそのファイルから読み取るジェネレータを返す。
引数@var{open-args}は、@code{open-input-file}に渡されます
(@ref{File ports}参照)。
@c COMMON

@c EN
The file is closed when the generator is exhausted.  If a generator
is abandoned before being read to the end, then the file is kept
open until the generator is garbage-collected.  If you want to
make sure the file is closed by a certain point of time, you might want
to use a reader procedure as a generator within the dynamic extent
of @code{with-input-from-file} etc.
@c JP
ファイルは、ジェネレータが尽きたところで閉じられます。最後
まで読み取る前にジェネレータが破棄された場合は、そのジェネレータ
がガベージコレクタに回収されるまでファイルは開かれたままです。
特定の時点までにファイルが確実にクローズしたい場合は、@code{with-input-from-file}
の動的なエクステントの中で、リーダー手続きをジェネレータとして
使うのが良いでしょう。
@c COMMON
@end defun

@defun file->sexp-generator filename . open-args
@defunx file->char-generator filename . open-args
@defunx file->line-generator filename . open-args
@defunx file->byte-generator filename . open-args
@c MOD gauche.generator
@c EN
Returns a generator that reads a series
of sexps, characters, lines and bytes from a file @var{filename},
respectively.  These are versions
of @code{file->generator} specialized by @code{read},
@code{read-char}, @code{read-line} and @code{read-byte} as the
@var{reader} argument.
@c JP
ファイル@var{filename}からそれぞれS式、文字、行、バイトの列を読むジェネ
レータを返します。これらは、@code{file->generator}の@var{reader}引数に@code{read}、
@code{read-char}、@code{read-line}、@code{read-byte}を渡して特定化したものです。
@c COMMON

@c EN
Like @code{file->generator}, @var{open-args}
are passed to @code{open-input-file} (@pxref{File ports}).
The file is closed when the generator is exhausted.
@c JP
@code{file->generator}同様、@var{open-args}はそのまま@code{open-input-file}に
引き渡されます(@ref{File ports}参照)。ジェネレータが使い切られると、
ファイルは閉じられます。
@c COMMON
@end defun

@defun gunfold p f g seed :optional tail-gen
@c MOD gauche.generator
@c EN
A generator constructor similar to @var{unfold} (@pxref{R7RS lists}).
@c JP
@var{unfold}に似たジェネレータの構築子です (@ref{R7RS lists}参照)。
@c COMMON

@c EN
@var{P} is a predicate that takes a seed value and determines
where to stop.  @var{F} is a procedure that calculates a value
from a seed value.  @var{G} is a procedure that calculates the
next seed value from the current seed value.  @var{Tail-gen}
is a procedure that takes the last seed value and returns a generator
that generates the tail.
@c JP
@var{P}はシード値を引数に取り、いつ止まるかを決める述語です。
@var{F}はシード値から値を計算する手続きです。@var{G}は現在の
シード値から次のシード値を計算する手続きです。@var{Tail-gen}
は最後のシード値を取り、残りを生成するジェネレータを返します。
@c COMMON

@c EN
For each call of the resulting generator, @var{p} is called with
the current seed value.  If it returns a true, then we see we've
done, and @code{tail-gen} is called (if it is given) to get a
generator for the tail.  Otherwise,
we apply @var{f} on the current seed value to get the value to
generate, and use @var{g} to update the seed value.
@c JP
この関数から返されたジェネレータが呼ばれるたびに、@var{p}が現在の
シード値とともに呼ばれます。これが真を返せば、やるべき事が終わっ
たことがわかり、(もし与えられていたなら)@code{tail-gen}が残りを
生成するジェネレータを得るために呼ばれます。さもなければ、生成する
値を得るために現在のシード値に@var{f}が適用され、シード値を更新
するために@var{g}が使われます。
@c COMMON

@example
(generator->list (gunfold (^s (> s 5)) (^s (* s 2)) (^s (+ s 1)) 0))
  @result{} '(0 2 4 6 8 10)
@end example
@end defun

@defun giterate f seed
@defunx giterate1 f seed
@c MOD gauche.generator
@c EN
Returns a generator of
an infinite sequence of values where the next value is computed
by applying @var{f} on the current value.  The first value generated
by @code{giterate} is @var{seed} itself, while the first one by
@code{giterate1} is @code{(@var{f} @var{seed})}.
@c JP
要素が、一つ前の要素に@var{f}を適用して計算されるような値の列を無限に生成する
ジェネレータを返します。@code{giterate}では最初の値は@var{seed}そのものですが、
@code{giterate1}では@code{(@var{f} @var{seed})}が最初の値になります。
@c COMMON

@example
(generator->list (giterate (pa$ * 2) 1) 10)
  @result{} (1 2 4 8 16 32 64 128 256 512)
(generator->list (giterate1 (pa$ * 2) 1) 10)
  @result{} (2 4 8 16 32 64 128 256 512 1024)
@end example

@c EN
The reason we have @code{giterate1} is that it's pretty efficient
(up to 10% faster than @code{giterate}).

See also @code{literate} in @code{gauche.lazy}
(@pxref{Lazy sequence utilities}).
@c JP
@code{giterate1}を別に用意しているのは、それが極めて速いからです
(@code{giterate}に比べても10%ほど速いです)。

@code{gauche.lazy}の@code{literate}も参照
(@ref{Lazy sequence utilities})。
@c COMMON
@end defun

@c EN
@subsubheading SRFI-158 compatible procedures
@c JP
@subsubheading SRFI-158互換の手続き
@c COMMON

@defun generator item @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns a generator that generates @var{item} @dots{}.
@c JP
@var{item} @dots{} を返すジェネレータを作成します。
@c COMMON
@end defun

@defun make-iota-generator count :optional start step
[SRFI-158]
@c MOD gauche.generator
@c EN
Same as @code{giota}, except that the @var{count} argument is
required.
@c JP
@code{giota}とほぼ同じですが、@var{count}引数は必須です。
@c COMMON
@end defun

@defun make-range-generator start :optional end stop
[SRFI-158]
@c MOD gauche.generator
@c EN
Same as @code{grange}.
@c JP
@code{grange}と同じです。
@c COMMON
@end defun

@defun make-coroutine-generator proc
[SRFI-158]
@c MOD gauche.generator
@c EN
Same as @code{generate}.
@c JP
@code{generate}と同じです。
@c COMMON
@end defun

@defun make-for-each-generator for-each obj
[SRFI-158]
@c MOD gauche.generator
@c EN
Given collection @var{obj} and walker @var{for-each}, creates a
generator that retrieves one item at a time from the collection.
Trivially defined as follows:
@c JP
コレクション@var{obj}と、それを一要素づつ処理する@var{for-each}手続きから、
コレクションの要素を一つづつ生成するジェネレータを作って返します。
次の定義を考えると良いでしょう。
@c COMMON

@example
(define (make-for-each-generator for-each coll)
  (generate (^[yield] (for-each yield coll))))
@end example

@c EN
If @var{obj} is mutated before the returned generator walks all the values,
the behavior depends on how the @var{for-each} procedure handles the
situation; it may or may not be safe.  In general it's better to avoid
mutation until the generator returns EOF.  Once the generator is exhausted,
though, it is safe to mutate @code{obj}.
@c JP
作られたジェネレータが全ての値を取り出す前に@var{obj}が変更された場合の振る舞いは、
渡された@var{for-each}手続きがそのケースをどのように処理するかに依存します。
それは安全かもしれないし、安全でないかもしれません。一般的に、ジェネレータが
EOFを返す前に@var{obj}を変更することは避けるのが賢明です。
ジェネレータがEOFを返した後に@var{obj}を変更するのは安全です。
@c COMMON
@end defun

@defun make-unfold-generator stop? mapper successor seed
[SRFI-158]
@c MOD gauche.generator
@c EN
This is the same as @code{gunfold}, except it doesn't take
optional @var{tail-gen} argument.
@c JP
省略可能な@var{tail-gen}引数を取らないことを除けば、
@code{gunfold}と同じです。
@c COMMON
@end defun


@node Generator operations, Generator consumers, Generator constructors, Generators
@subsection Generator operations
@c NODE ジェネレータの操作


@c EN
The following procedures take generators (noted as @var{gen} and
@var{gen2}) and return a generator.  For the convenience, they
also accept any collection to @var{gen} and @var{gen2} parameters;
if a collection is passed where a generator is expected,
it is implicitly coerced into a generator.

(NB: This is Gauche's extension.  For portable SRFI-121/SRFI-158 programs,
you shouldn't rely on this behavior; instead, explicitly convert
collections to generators.)
@c JP
以下に挙げる手続きは、どれもジェネレータ(@var{gen}や@var{gen2}と記述されて
います)を受け取ってジェネレータを返します。便宜上、これらの手続きは
@var{gen}や@var{gen2}としてコレクションも受けつけます;ジェネレータが
想定されているところにコレクションが渡されると、暗黙のうちにジェネレータ
へと変換されるのです。

(註：これはGauche独自の拡張です。ポータブルなSRFI-121/158プログラムは、
この振る舞いに依存してはいけません。明示的にコレクションをジェネレータに
変換してください。)
@c COMMON

@defun gcons* item @dots{} gen
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns a generator that adds @var{item}s in front of @var{gen}.
@c JP
@var{gen}の前に@var{item}を追加するジェネレータを返します。
@c COMMON

@example
(generator->list (gcons* 'a 'b (giota 2)))
 @result{} (a b 0 1)
@end example
@end defun

@defun gappend gen @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns a generator that yields the items from the first given
generator, and once it is exhausted, use the second generator, and so on.
@c JP
最初に与えたジェネレータが生成する値を生成し、それが尽きたら2番目に与えた
ジェネレータが生成する値を生成し、という具合に、与えられたジェネレータが
生成する値を順番に生成するジェネレータを返します。
@c COMMON

@example
(generator->list (gappend (giota 3) (giota 2)))
 @result{} (0 1 2 0 1)

(generator->list (gappend))
 @result{} ()
@end example
@end defun

@defun gconcatenate gen
@c MOD gauche.generator
@c EN
The @var{gen} argument should generate generators and/or sequences.
Returns a generator that yields elements from the first generator/sequence,
then the second one, then the third, etc.

It is similar to @code{(apply gappend (generator->list gen))}, except
that @code{gconcatenate} can work even @var{gen} generates infinite
number of generators.
@c JP
@var{gen}引数は、ジェネレータやシーケンスを生成するジェネレータです。
この関数は、@var{gen}が生成する最初のジェネレータ/シーケンスの要素を次々に
生成し、それが尽きたら二番目のジェネレータ/シーケンスの要素を次々に生成し…
というジェネレータを作って返します。

@code{(apply gappend (generator->list gen))}と似た動作ですが、
@code{gconcatenate}は@var{gen}が無限ジェネレータであっても動作するという
利点があります。
@c COMMON

@example
($ generator->list $ gconcatenate
   $ list->generator `(,(giota 3) ,(giota 2)))
 @result{} (0 1 2 0 1)
@end example
@end defun

@defun gflatten gen
[SRFI-158]
@c MOD gauche.generator
@c EN
The argument @var{gen} is a generator that yields lists.
This procedure returns a generator that's yield each element of the lists
one at a time.
@c JP
引数@var{gen}はリストを生成するジェネレータです。
この手続きは、入力が生成するリストの各要素をひとつづつ生成するようなジェネレータを
作成して返します。
@c COMMON

@c EN
Example: The game Tetris determines the next
dropping piece (tetrimino) by the following algorithm: Take a
bag of tetriminos with one for each kind (O, I, T, S, Z, L, J),
permute it, and draw one by one; once the bag is empty, take another
bag and repeat.  The algorithm can be implemented by a pipeline
of generates as follows.  (Tetris is a registered trademark of
The Tetris Company).
@c JP
例: ゲームのテトリスは、次に落ちてくるピース (テトリミノ) を次の
アルゴリズムで決めています: 各種類(O, I, T, S, Z, L, J)のテトリミノが
一つづつ入った袋をとり、そこからランダムに一つづつ取り出す。袋が空になったら
新たにテトリミノの袋をとり繰り返す。このアルゴリズムは次に示すとおり
ジェネレータのパイプラインで実装できます。(テトリスはThe Tetris Companyの
登録商標です)
@c COMMON

@example
(use gauche.generator)
(use data.random) ; for permutations-of

(define g
  ($ gflatten $ permutations-of
     $ (circular-generator '(O I T S Z L J))))

(generator->list g 21)
  @result{}
  (L O Z T J S I J L Z T I O S T L Z S I J O)
@end example

@c EN
Note the subtle difference of this example and the example
in @code{gconcatenate} above---@code{gconcatenate} takes
a generator of generators, while @code{gflatten} takes
a generator of lists.

If we use Haskell-ish type notation, you can see the subtle differences
of those similar procedures:
@c JP
この例と、上のの@code{gconcatenate}の例を比べてみてください。微妙な違いが
あります。@code{gconcatenate}は、ジェネレータを生成するジェネレータを取りますが、
@code{gflatten}はリストを生成するジェネレータを取ります。

Haskell風の型表記を使うと、これら似た手続きの違いをわかりやすく整理することができるでしょう：
@c COMMON

@example
gappend             :: (Generator a, Generator a, ...) -> Generator a
(pa$ apply gappend) :: [(Generator a)] -> Generator a
gconcatenate        :: Generator Generator a -> Generator a
gflatten            :: Generator [a] -> Generator a
@end example
@end defun

@defun gmerge less-than gen gen2 @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
Creates a generator that yields elements out of input generators,
with the order determined by a procedure @code{less-than}.
The procedure is called as
@code{(less-than a b)} and
must return @code{#t} iff the element @code{a} must precede
the element @code{b}.

Each input generator must yield an ordered elements by itself;
otherwise the result won't be ordered.

If only one generator is given, it is just returned (after coercing the
input to a generator).  In that case, @code{less-than} won't be called at all.
@c JP
入力ジェネレータから生成される要素を、手続き@code{less-than}で決められる順
に生成するジェネレータを作って返します。
@code{less-than}は入力ジェネレータの二つの要素@code{a}, @code{b}に対して
呼び出され、@code{a}が@code{b}に先行すべき時のみ@code{#t}を返します。

入力のジェネレータはそれぞれが要素を正しい順で生成しなければなりません。
そうでない場合、出力が正しい順になっていることは保証されません。

入力が一つだけ渡された場合は、(それをジェネレータへと型変換した後で)それがそのまま
返され、@code{less-than}は呼ばれません。
@c COMMON

@example
(generator->list (gmerge < '(1 3 8) '(5) '(2 4)))
  @result{} '(1 2 3 4 5 8)
@end example
@end defun

@defun gmap proc gen gen2 @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns a generator that yields a value returned by @var{proc}
applied on the values from given generators.  The returned generator
terminates when any of the given generator is exhausted.
@c JP
与えられたジェネレータから得られる値に@var{proc}を適用して得られる値を
生成するジェネレータを返します。返り値となるジェネレータは、引数として
与えられたジェネレータのどれかが尽きたら終了します。
@c COMMON

@c EN
NB: This differs from @code{generator-map} (@pxref{Folding generated values})
which consumes all
values at once and returns the results as a list, while @code{gmap}
returns a generator immediately without consuming input.
@c JP
注意: この手続きは、@code{generator-map} (@ref{Folding generated values}参照)
とは違います。@code{generator-map}は一度に全ての値を消費し、結果をリストとして返しますが、
@code{gmap}はすぐには入力を消費せずにジェネレータを返すのです。
@c COMMON
@end defun

@defun gmap-accum proc seed gen gen2 @dots{}
@c MOD gauche.generator
@c EN
A generator version of @code{map-accum} (@pxref{Mapping over collection}),
mapping with states.
@c JP
状態を持つマッピングを行う@code{map-accum} (@pxref{Mapping over collection})のジェネレータ版
です。
@c COMMON

@c EN
The @var{proc} argument is a procedure that takes as many arguments
as the input generators plus one.  It is called as
@code{(proc v v2 @dots{} seed)} where @code{v}, @code{v2}, @dots{} are
the values yielded from the input generators, and @var{seed} is the
current seed value.  It must return two values, the yielding value
and the next seed.
@c JP
引数@var{proc}は、入力となるジェネレータの個数プラス1個の引数を取る
手続きで、@code{(proc v v2 @dots{} seed)}のように呼ばれます。
@code{v}, @code{v2}, @dots{} は、入力ジェネレータが生成する値であり、
@var{seed}は現在のシード値です。この手続きは2つの値を返さなければい
けません。生成する値と、次のシード値です。
@c COMMON

@c EN
NB: This is called @code{gcombine} in SRFI-121.
@c JP
註：これはSRFI-121の@code{gcombine}と同じものです。
@c COMMON
@end defun

@defun gcombine proc seed gen gen2 @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
An alias of @code{gmap-accum}, provided for the compatibility of SRFI-121.
@c JP
@code{gmap-accum}の別名です。SRFI-121との互換性のため提供されています。
@c COMMON
@end defun

@defun gfilter pred gen
@defunx gremove pred gen
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns a generator that yields the items from the source generator
@var{gen}, except those who makes @var{pred} answers false (@code{gfilter})
or those who makes @var{pred} answers a true value (@code{gremove})
@c JP
ソースジェネレータ@var{gen}が生成する値のうち、
@var{pred}がfalseを返すもの(@code{gfilter}の場合)、
または@var{pred}が真の値を返すもの(@code{gremove}の場合)を
除いた値を生成するジェネレータを返します。
@c COMMON

@example
(generator->list (gfilter odd? (grange 0)) 6)
 @result{} (1 3 5 7 9 11)
(generator->list (gremove odd? (grange 0)) 6)
 @result{} (0 2 4 6 8 10)
@end example
@end defun

@defun gdelete item gen :optional =
[SRFI-158]
@c MOD gauche.generator
@c EN
Return a generator that yields the items from the source generator
@var{gen}, except those are the same as @var{item}.  The comparison
is done by the procedure passed to @var{=}, which defaults to @code{equal?}.
@c JP
ソースジェネレータ@var{gen}が生成する値のうち、@var{item}と等しいものを
取り除いた値を生成するジェネレータを返します。
比較は省略可能引数@var{=}に渡す手続きで行われ、省略時には@code{equal?}が使われます。
@c COMMON

@example
;; Note: This example relies on auto-coercing list to generator.
;; SRFI-121 requires list->generator for the second argument.
(generator->list (gdelete 3 '(1 2 3 4 3 2 1)))
  @result{}  (1 2 4 2 1)
@end example
@end defun

@defun gdelete-neighbor-dups gen :optional =
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns a generator that yields the items from the source generator
@var{gen}, but the consecutive items of the same value is omitted.
The comparison
is done by the procedure passed to @var{=}, which defaults to @code{equal?}.
@c JP
ソースジェネレータ@var{gen}が生成する値を生成するジェネレータを返します。
但し、連続して等しいものはそのうち1つだけが生成されます。
比較は省略可能引数@var{=}に渡す手続きで行われ、省略時には@code{equal?}が使われます。
@c COMMON

@example
;; Note: This example relies on auto-coercing list to generator.
;; SRFI-121 requires string->generator for the second argument.
(generator->list (gdelete-neighbor-dups "mississippi"))
  @result{} (#\m #\i #\s #\i #\s #\i #\p #\i)
@end example
@end defun

@defun gfilter-map proc gen gen2 @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
Works the same as @code{(gfilter values (gmap proc gen gen2 @dots{}))},
only slightly efficiently.
@c JP
@code{(gfilter values (gmap proc gen gen2 @dots{}))}
と同様に動作しますが、若干効率的です。
@c COMMON
@end defun

@defun gstate-filter proc seed gen
[SRFI-158]
@c MOD gauche.generator
@c EN
This allows stateful filtering of a series.  The @var{proc} argument
must be a procedure that takes a value @var{V} from the source generator and
a seed value.  It should return two values, a boolean flag and the next
seed value.  If it returns true for the boolean flag, the generator
yields @var{V}.  Otherwise, the generator keeps calling @var{proc},
with updating the seed value, until it sees the true flag value
or the source generator is exhausted.
@c JP
この手続きは、一連の値に対するステートフルなフィルタリングを可能にします。
引数@var{proc}はソースジェネレータからの値@var{v}と、シード値を取る手続きでなければ
なりません。この手続きが真を返す場合に、返り値となるジェネレータは
@var{v}を生成します。そうでない場合、ジェネレータは@var{proc}が真を返すか、ソース
ジェネレータが尽きるまで、シード値を更新しながら@var{proc}を呼び出し続けます。
@c COMMON

@c EN
The following example takes a generator of oscillating values
and yields only values that are greater than their previous value.
@c JP
次に挙げる例は、振動する値を生成するジェネレータを受け取り、直前の値よりも
大きな値のみを生成するジェネレータを返します。
@c COMMON

@example
(generator->list
 (gstate-filter (^[v s] (values (< s v) v)) 0
                (list->generator '(1 2 3 2 1 0 1 2 3 2 1 0 1 2 3))))
 @result{} (1 2 3 1 2 3 1 2 3)
@end example
@end defun

@defun gbuffer-filter proc seed gen :optional tail-gen
@c MOD gauche.generator
@c EN
This procedure allows n-to-m mapping between elements in input and output---
that is, you can take a look at several input elements to generate
one or more output elements.
@c JP
この手続きは入力と出力がn対mで対応するようなフィルタを作ります。つまり、
入力のいくつかを見て、それに応じて1個以上の出力を生成するようなフィルタです。
@c COMMON

@c EN
The procedure @var{proc} receives the next input element and accumulated
seed value.  It returns two values: A list of output values, and the next
seed value.  If you need to look at more input to generate
output, you can return an empty list as the first value.
@c JP
手続き@var{proc}は、次の入力およびシード値を受け取り、
二つの値を返します:出力値のリスト、及び次のシード値です。
出力を決定するためにもっと入力を読むことが必要なら、
第一の返り値を()にします。
@c COMMON

@c EN
If the input reaches the end, @var{tail-gen} is called with the
current seed value; it should return a list of last output values.
If omitted, the output ends when the output of the last call to @var{proc}
is exhausted (the last seed value is discarded).
@c JP
入力が終端に達したら、手続き@var{tail-gen}が、その時点でのシード値を引数として
呼び出されます。@var{tail-gen}は出力の終端となる値のリストを返します。
@var{tail-gen}が省略された場合は、入力がなくなった時点で最後の@var{proc}が
返した出力のリストが終端となります(最後のシード値は捨てられます)
@c COMMON

@c EN
Suppose you have a text file.  Each line contains a command,
but if the line ends with backslash, next line is treated as a
continuation of the current line.  The following code creates
a generator that returns @emph{logical} lines, that is,
the lines after such line continuations are taken care of.
@c JP
例えば、テキストファイルがあり、各行にコマンドがかかれているとしましょう。
ただし行がバックスラッシュで終わった場合、次の行へと継続しているものとみなします。
以下のコードは、入力ファイルの各行を読むジェネレータから、
@emph{論理行}(継続行をくっつけたもの)をひとつづつ返すジェネレータを生成します。
@c COMMON

@example
(gbuffer-filter (^[v s]
                  (if-let1 m (#/\\$/ v)
                    (values '() (cons (m 'before) s))
                    (values `(,(string-concatenate-reverse (cons v s))) '())))
                '()
                (file->line-generator "input-file.txt")
                (^[s] `(,(string-concatenate-reverse s))))
@end example
@end defun

@defun gtake gen k :optional padding
@defunx gdrop gen k
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns a generator that takes or drops initial @var{k} elements
from the source generator @var{gen}.
@c JP
それぞれ、ソースジェネレータ@var{gen}が生成する値のうち最初から@var{k}個の値を生成する、
および最初から@var{k}個の値を除いた次の値から生成するようなジェネレータを
作成して返します。
@c COMMON

@c EN
Those won't complain if the source generator is exhausted before generating
@var{k} items.  By default, the generator returned by @code{gtake}
terminates as the source ends, but if you give the optional @var{padding}
argument, then the returned generator does yield @var{k} items, using the
value given to @var{padding} to fill the rest.
@c JP
これらの手続きはソースジェネレータが@var{k}個の値を生成する前に尽きたとしても、
何も文句を言いません。デフォルトでは、@code{gtake}が返すジェネレータはソース
ジェネレータが終端に達した時点で終了します。しかし、省略可能引数@code{padding}を与えた
場合、返されるジェネレータは足りない分を@code{padding}で補うことで
常に@var{k}個の値を生成します。
@c COMMON

@c EN
Note: If you pass @var{padding}, @code{gtake} always returns a generator
that generates exactly @var{k} elements even the input generator is already
exhausted---there's no general way to know whether you've reached
the end of the input.  If you need to take @var{k} items repeatedly
from the input generator, you may want to use @code{gslices} below.
@c JP
註: @var{fill}引数を渡した場合、たとえ入力ジェネレータが終端に達していたとしても
@code{gtake}が返すジェネレータは@var{k}個の値を生成します。つまりその場合、
入力が使い尽くされたかどうかを判定する汎用的な方法はありません。
「入力が尽きるまで@var{k}個の要素を次々に取り出したい」という場合は
下に説明する@code{gslices}の方が使い勝手が良いかもしれません。
@c COMMON

@c EN
Note for the compatibility: Until 0.9.4, @code{gtake} takes two optional
arguments, @var{fill?} and @var{padding}.  That is consistent with
Gauche's builtin @code{take*}, but incompatible to SRFI-121's @code{gtake}.
We think SRFI-121's interface is more compact and intuitive, so we
renamed the original one to @code{gtake*} (emphasizing
the similarity to @code{take*}), and made @code{gtake} compatible to
SRFI-121.
To ease transition, the current @code{gtake} allows two optional arguments
(four in total),
in which case we assume the caller wants to call @code{gtake*}; so
the code that gives two optional arguments to @code{gtake} would work in
both pre-0.9.4 and 0.9.5.
@c JP
互換性への註: 0.9.4までは、@code{gtake}は@var{fill?}と@var{padding}の
ふたつの省略可能引数を取りました。これはもともとGauche組み込み@code{take*}に合わせて
いたのですが、SRFI-121に採用された@code{gtake}とは非互換になりました。
SRFI-121の方が簡潔で直感的なので、0.9.5からは元の@code{gtake}を(@code{take*}との
類似性を強調して)@code{gtake*}とリネームし、@code{gtake}はSRFI-121に合わせることと
しました。
移行をスムースにするため、@code{gtake}は二つの省略可能引数(合計4つの引数)を取ることを
許します。その場合、@code{gtake*}が呼ばれたのと同じ動作になります。
従って、@code{gtake}に4引数を渡している従来のコードは、0.9.5以前でも以降でも
動作します。
@c COMMON
@end defun

@defun gtake* gen k :optional fill? padding
@c MOD gauche.generator
@c EN
A variation of @code{gtake}; instead of single optional @var{padding}
argument, this takes two optional arguments just like @code{take*}
(@xref{List accessors and modifiers}.)  Up to 0.9.4 this version
is called @code{gtake}.  This is provided for the backward compatibility.
@c JP
@code{gtake}のバリエーションで、一つの省略可能引数@var{padding}のかわりに、
@code{take*}と同じように二つの省略可能引数を取ります
(@ref{List accessors and modifiers}参照)。
0.9.4まではこれが@code{gtake}と呼ばれていました。
互換性のために名前を変えて残してあります。
@c COMMON
@end defun

@defun gtake-while pred gen
@defunx gdrop-while pred gen
[SRFI-158]
@c MOD gauche.generator
@c EN
The generator version of @code{take-while} and @code{drop-while}
(@pxref{List accessors and modifiers}).  The generator returned
from @code{gtake-while} yields items from the source generator
as far as @var{pred} returns true for each.  The generator returned
from @code{gdrop-while} first reads items from the source generator
while @var{pred} returns true for them, then start yielding items.
@c JP
ジェネレータ版の @code{take-while} と @code{drop-while}
(@ref{List accessors and modifiers}参照) です。
@code{gtake-while}が返すジェネレータは、ソースジェネレータが生成する値に対して
@var{pred}が真を返す限り、その値を生成します。@code{gdrop-while}が返す
ジェネレータは、まずソースジェネレータから値を読み取り、その値に対して
@var{pred}が真を返したら、値の生成を開始します。
@c COMMON
@end defun

@defun gslices gen k :optional (fill? #f) (padding #f)
@c MOD gauche.generator
@c EN
The generator version of @code{slices} (@pxref{List accessors and modifiers}).
This returns a generator, that yields a list of @var{k} items from
the input generator @var{gen} at a time.
@c JP
@code{slices}のジェネレータ版です (@ref{List accessors and modifiers}参照。
入力のジェネレータ@var{gen}から@var{k}要素づつ読み出して、そのリストを生成する
ジェネレータを返します。
@c COMMON

@example
(generator->list (gslices (giota 7) 3))
  @result{} ((0 1 2) (3 4 5) (6))
@end example

@c EN
The @var{fill?} and @var{padding} arguments controls how the end
of input is handled, just like @code{gtake}.  When @var{fill?} is
@code{#f} (default), the last item from output generator may not
have @var{k} items if the input is short to fill them, as shown
in the above example.  If @var{fill?} is true and the input is
short to complete @var{k} items, @var{padding} argument is used
to fill the rest.
@c JP
@var{fill?}引数と@var{padding}引数は、@code{gtake}のそれと同様に、
入力が足りなかった場合の処理を指定します。デフォルトの、@var{fill?}が
@code{#f}の場合、入力が@var{k}要素に満たなければ、出力の要素も
切り詰められます (上の例参照)。@var{fill}が真の値であれば、
入力が足りない分は@var{padding}が当てられ、出力の最後のリストも@var{k}要素になります。
@c COMMON

@example
(generator->list (gslices (giota 6) 3 #t 'x))
  @result{} ((0 1 2) (3 4 5))
(generator->list (gslices (giota 7) 3 #t 'x))
  @result{} ((0 1 2) (3 4 5) (6 x x))
@end example
@end defun

@defun ggroup gen k :optional padding
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns a generator lists of @var{k} elements taken from @var{gen}.
If @var{padding} is omitted, it works just as @code{(gslices gen k)}.
If @var{padding} is given, it works just as @code{(gslices gen k #t padding)}.

This is defined in SRFI-158, and more portable than @code{gslices}.
@c JP
@var{gen}から@var{k}要素づつ取って作ったリストを次々と生成するジェネレータを返します。
@var{padding}が省略された時は@code{(gslices gen k)}と同じ、
@var{padding}が与えられた時は@code{(gslices gen k #t padding)}と同じになります。

この手続きはSRFI-158で定義されたので、@code{gslices}よりポータブルでしょう。
@c COMMON
@end defun

@defun grxmatch regexp gen
@c MOD gauche.generator
@c EN
The @var{gen} argument must be, after coerced, a generator that
yields characters.
@c JP
@var{gen}は暗黙の変換後、文字を生成するジェネレータでなければなりません。
@c COMMON

@c EN
A generator returned from this procedure
tries to match @var{regexp} from the character sequence
generated by @var{gen}, and once it matches, remember the position after
the match and returns @code{#<rxmatch>} object.  If no more match
is found, the generator is exhausted.
@c JP
この手続きが返すジェネレータは、@var{gen}が生成する文字のシーケンスに対して、
@var{regexp}をマッチさせようとする。そして一度マッチすると、その位置を記憶して
@code{#<rxmatch>}オブジェクトを返します。さらにマッチすることがなければ、
ジェネレータは尽きます。
@c COMMON

@example
($ generator->list
   $ gmap rxmatch-substring
   $ grxmatch #/\w+/ "The quick brown fox jumps over the lazy dog.")
 @result{} ("The" "quick" "brown" "fox" "jumps" "over" "the" "lazy" "dog")
@end example

@c EN
Note: This procedure is efficient if @var{gen} is a string, in which
case we actually bypass coercing it to a generator.  If @var{gen} is other
than a string, the current implementation may need to apply @var{regexp}
as many times as O(n^2) where n is the entire length of the character
sequence generated by @var{gen}, although the coefficient is small.
This may be improved in future, but be careful using this function
on very large input.
@c JP
注意: この手続きは@var{gen}が文字列の場合、ジェネレータへの変換がバイパスされるため
効率的です。@var{gen}が文字列ではない場合、現在の実装では、@var{gen}が生成する文字の
シーケンス全体の長さがnの場合に、係数が小さいとはいえ、必要となる@var{regexp}の適用
回数は、O(n^2)となるかもしれません。この点について、将来改良されるかもしれませんが、
大きな入力に対してこの関数を使う場合は、注意してください。
@c COMMON

@c EN
Note also that, when @var{gen} is not a string, @var{rxmatch} is applied
on some buffered partial input.  So @code{rxmatch-after} of the returned
match does not represents the whole ``rest of input'' after the match,
but merely the rest of strings within the buffer.
@c JP
もう一点注意: @var{gen}が文字列でない場合、@var{rxmatch}はバッファリングされた
部分的な入力に対して適用されます。このため、返されたマッチの@code{rxmatch-after}
は、マッチ後の``入力の残り全部''を表現しません。単にバッファの中にある文字列の
残りになります。
@c COMMON
@end defun

@defun gindex vgen igen
[SRFI-158]
@c MOD gauche.generator
@c EN
Both arguments are generators.  The @var{igen} generator must
yield monotonically increasing series of exact nonnegative integers.

Returns a generator that generates items from @var{vgen}
indexed by the numbers from @var{igen}, exhausted when either
source generator is exhausted.

An error is thrown when @var{igen} yields a value that doesn't
conform the condition.
@c JP
引数はどちらもジェネレータです。@var{igen}は単調増加する正確な非負整数を
生成しなければなりません。

@var{vgen}から生成される値のうち、@var{igen}からの数字をインデックスとする
値のみを取り出して返すようなジェネレータを作成して返します。
どちらかの入力ジェネレータが終端に達したら、返されるジェネレータも終端に達します。

@var{igen}が条件を満たさない値を生成した場合はその時点でエラーが投げられます。
@c COMMON

@example
;; This example takes advantage of Gauche's auto-coercing
;; list to generator.  For portable SRFI-121 programs,
;; you need list->generator for each argument:
(generator->list (gindex '(a b c d e) '(0 2 3)))
  @result{} (a c d)
@end example
@end defun

@defun gselect vgen bgen
[SRFI-158]
@c MOD gauche.generator
@c EN
Both arguments are generators.  Creates and returns a
generator that yields a value from @var{vgen} but only
the corresponding value from @var{bgen} is true.

The returned generator is exhausted when one of the
source generators is exhausted.
@c JP
引数はどちらもジェネレータです。@var{vgen}からの要素のうち、
対応する@var{bgen}の要素が真の値であるものだけを選んで返す
ようなジェネレータを作成して返します。

ソースジェネレータの一つが終端に達した時に、作成された
ジェネレータも終端に達します。
@c COMMON

@example
;; This example takes advantage of Gauche's auto-coercing
;; list to generator.  For portable SRFI-121 programs,
;; you need list->generator for each argument:
(generator->list (gselect '(a b c d e) '(#t #t #f #t #f)))
  @result{} (a b d)
@end example

@c EN
Combined with a bitgenerator, you can use @code{gselect}
to extract items using bitmask:
@c JP
ビットジェネレータと一緒に使うと、@code{gselect}でビットマスク
により要素を抽出することができます。
@c COMMON

@example
(generator->list (gselect '(a b c d e)
                           (reverse-bits->generator #x1a)))
  @result{} (a b d)
@end example
@end defun



@node Generator consumers,  , Generator operations, Generators
@subsection Generator consumers
@c NODE ジェネレータの消費

@c EN
Some generator consumers are built-in.
@xref{Folding generated values}, for @code{generator-fold},
@code{generator-fold-right}, @code{generator-for-each},
@code{generator-map}, and @code{generator-find}.
@c JP
いくつかのジェネレータ消費手続きは組み込みになっています。
@code{generator-fold}、@code{generator-fold-right}、 @code{generator-for-each}、
@code{generator-map}、@code{generator-find}については、
@ref{Folding generated values}を参照してください。
@c COMMON

@defun generator->list generator :optional k
@defunx generator->reverse-list generator :optional k
[SRFI-158]
@c MOD gauche.generator
@c EN
Reads items from @var{generator} and returns a list of them
(or a reverse list, in case of @code{generator->reverse-list}).
By default, this reads until the generator is exhausted.  If
an optional argument @var{k} is given, it must be a nonnegative
integer, and the list ends either @var{k} items are read,
or the generator is exhausted.
@c JP
@var{generator}から項目を読み取り、それらを要素とするリストを返します
(@code{generator->reverse-list}では要素が逆順になります)。
デフォルトでは、ジェネレータを使い切るまで読み取ります。省略可能
引数@var{k}を与える場合、それは非負整数でなければならず、結果のリスト
は、@var{k}個の項目を読み取るか、ジェネレータを使い切ったところで終わり
となります。
@c COMMON

@c EN
Be careful not to pass an infinite generator to this without
specifying @var{k}---this procedure won't return but hogs
all the memory before crash.
@c JP
無限ジェネレータを渡す時は必ず@var{k}を指定しましょう。
さもなくば、この手続きは制御を返さず、全てのメモリを食い尽して
クラッシュするでしょう。
@c COMMON
@end defun

@defun generator-map->list proc gen gen2 @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
The @var{proc} argument must be a procedure that takes as many arguments
as the number of given generators.

Returns a list, each of whose element is created by applying @var{proc}
on each element from given generators @var{gen} @var{gen2} @dots{}.
The list ends when any of the generator is exhausted.

Note that the list is created eagerly---if all of the generators are
infinite, this procedure never returns.
@c JP
@var{proc}は与えられたジェネレータの数と同じだけの引数を取る手続きです。

@var{gen} @var{gen2} @dots{}から要素をひとつづつ取ってそれらに@var{proc}を
適用した結果のリストを作って返します。
どれかのジェネレータが終端に達したらリストも終わります。

リストは積極的に作られます。全てのジェネレータが無限だと、この手続きは戻ってきません。
@c COMMON
@end defun

@defun generator->vector gen :optional k
@defunx generator->string gen :optional k
[SRFI-158]
@c MOD gauche.generator
@c EN
Extracts items from the generator @var{gen} up to @var{k} items
or until it exhausts, and create a fresh
vector or string from the extracted items.

When @var{k} is omitted, @var{gen} is called until it exhausts;
note that if @var{gen} is infinite generator this procedure won't return.

For @code{generator->string}, @var{gen} must yield a character, or
an error is reported.
@c JP
@var{gen}から、@var{k}要素もしくは@var{gen}が終端に達するまで要素を読み出し、
それらの要素からなるベクタまたは文字列を作って返します。

@var{k}が省略された場合は@var{gen}が終端に達するまで呼ばれますが、
@var{gen}が無限ジェネレータだと返って来なくなるので注意してください。

@code{generator->string}の場合、@var{gen}が文字以外のものを生成したら
エラーが報告されます。
@c COMMON
@end defun

@defun generator->uvector gen :optional k class
@defunx generator->bytevector gen :optional k
[SRFI-158]
@c MOD gauche.generator
@c EN
Extracts items from the generator @var{gen} up to @var{k} items
or until it exhausts, and create a fresh uniform vector
of class @var{class} filled with those items.
If @var{k} is omitted or @code{#f}, @var{gen} is read until it exhausts.

If @var{class} is specified, it must be one of the uniform vector
classes (@pxref{Uniform vectors}).  When omitted, @code{<u8vector>} is
assumed.

@code{Generator->bytevector} works like @code{generator->uvector}
except that the class is fixed to @code{<u8vector>}.

The generator must always produce numeric values acceptable to be an
element of the specified uvector; otherwise an error is signalled.
@c JP
ジェネレータ@var{gen}から、@var{k}個の要素、あるいは@var{gen}が終端に達するまで
要素を読み出し、それらの要素からなるユニフォームベクタを作って返します。
@var{k}が省略されるか@code{#f}の場合、@var{gen}は常に最後まで読まれます。

@var{class}が指定された場合、それはユニフォームベクタのクラスのいずれかで
なければなりません(@ref{Uniform vectors}参照)。省略された場合は
@code{<u8vector>}が使われます。

@code{generator->bytevector}は、@var{class}が@code{<u8vector>}に固定されている
以外は@code{generator->uvector}と同じです。

ジェネレータ@var{gen}は、指定されたユニフォームベクタの要素となり得る数値を
生成しなければなりません。それ以外の値が生成された場合はエラーが報告されます。
@c COMMON
@end defun

@defun generator->vector! vector at gen
[SRFI-158]
@c MOD gauche.generator
@c EN
Fill @var{vector} from index @var{at} with the value yielded
from @var{gen}.  It terminates when @var{gen} is exhausted or the index
reaches at the end of the vector.  Returns the number of items
generated.
@c JP
@var{vector}を、インデックス@var{at}から、@var{gen}が生成する値によって
埋めてゆきます。@var{gen}が終端に達するか、ベクタの最後まで埋められた時点で
終了し、生成された要素の個数が返されます。
@c COMMON

@example
(define v (vector 'a 'b 'c 'd 'e))

(generator->vector! v 2 (giota))
  @result{} 3

v @result{} #(a b 0 1 2)
@end example
@end defun

@defun generator->uvector! uvector at gen
@defunx generator->bytevector! u8vector at gen
@c MOD gauche.generator
@c EN
Like @var{generator->vector!}, fill a uniform vector @var{uvector}
starting from index @var{at} with elements read from a generator
@var{gen}.  It terminates when @var{gen} is exhausted or the index
reaches at the end of the vector.  Returns the number of items
generated.

Any type of uvector can be passed to @code{generator->uvector!}, while
@code{generator->bytevector!} can only accept @code{u8vector}.

The generator must always produce numeric values acceptable to be an
element of the specified uvector; otherwise an error is signalled.
@c JP
@code{generator->vector!}と同様、@var{gen}から読み出した値で、
@var{uvector}を、インデックス@var{at}から順に埋めてゆきます。
ベクタの終端に達するか、@var{gen}が終端に達するまで続けられ、
読み出された要素の個数が戻り値となります。

@code{generator->uvector!}はどんなユニフォームベクタでも取ることができます。
@code{generator->bytevector!}は@code{u8vector}限定です。

ジェネレータ@var{gen}は、指定されたユニフォームベクタの要素となり得る数値を
生成しなければなりません。それ以外の値が生成された場合はエラーが報告されます。
@c COMMON
@end defun

@defmac glet* (binding @dots{}) body body2 @dots{}
@c MOD gauche.generator
@c EN
This captures a monadic pattern frequently appears in the generator
code.  It is in a similar spirit of @code{and-let*}, but returns
as soon as the evaluating expression returns EOF, instead of @code{#f}
as @code{and-let*} does.
@c JP
これは、ジェネレータコードに頻繁に現れるモナド的なパターンを表現
するものです。@code{and-let*}の発想に似ていますが、@code{#f}のかわりにEOFを
返す式を評価すると直ちに返ります。
@c COMMON

@c EN
The @var{binding} part can be either @code{(var expr)} or @code{( expr )}.
The actual definition will explain this syntax clearly.
@c JP
@var{binding}部分は@code{(var expr)}か@code{( expr )}の形をとります。
実際の定義を見れば、この構文が明解に理解できるでしょう。
@c COMMON

@example
(define-syntax glet*
  (syntax-rules ()
    [(_ () body body2 ...) (begin body body2 ...)]
    [(_ ([var gen-expr] more-bindings ...) . body)
     (let1 var gen-expr
       (if (eof-object? var)
         var
         (glet* (more-bindings ...) . body)))]
    [(_ ([ gen-expr ] more-bindings ...) . body)
     (let1 var gen-expr
       (if (eof-object? var)
         var
         (glet* (more-bindings ...) . body)))]))
@end example
@end defmac

@defmac glet1 var expr body body2 @dots{}
@c MOD gauche.generator
@c EN
This is to @code{glet*} as @code{let1} is to @code{let*}.  In other words,
it is @code{(glet* ([var expr]) body body2 @dots{})}.
@c JP
これと@code{glet*}の関係は、@code{let1}と@code{let*}のそれと同じです。言葉を
変えれば、これは@code{(glet* ([var expr]) body body2 @dots{})}と同じです。
@c COMMON
@end defmac

@defmac do-generator (var gexpr) body @dots{}
@c MOD gauche.generator
@c EN
This is a generator version of @code{dolist} and @code{dotimes}
(@pxref{Binding constructs}).
@c JP
これは、ジェネレータ版の@code{dolist}であり@code{dotimes}です(@ref{Binding constructs}参照)。
@c COMMON

@c EN
@var{Gexpr} is an expression that yields a generator.  It is
evaluated once.  The resulting generator is called repeatedly
until it returns EOF.  Every time the generator is called,
@var{body} @dots{} are evaluated in the scope
where @var{var} is bound to the value yielded from the generator.
@c JP
@var{gexpr}はジェネレータを生成する式であり、一度だけ評価されます。
結果となるジェネレータはEOFを返すまで繰り返し呼ばれます。ジェネレータ
が呼ばれる毎に、ジェネレータが生成する値に束縛される@var{var}の
スコープ内で@var{body} @dots{}が評価されます。
@c COMMON

@c EN
Like @code{dolist} and @code{dotimes}, this macro exists for
side-effects.  You can write the same thing with @code{for-each} families,
but sometimes this macro makes the imperative code more readable:
@c JP
@code{dolist}や@code{dotimes}がそうであるように、このマクロも副作用のため
のものです。同じことは@code{for-each}族を使っても書けますが、このマクロを
使って命令的に記述したコードの方が読みやすいこともあるのです。
@c COMMON

@example
(do-generator [line (file->line-generator "filename")]
@c EN
  ;; do some side-effecting stuff with line
@c JP
  ;; lineを使って何か副作用のある作業をする
@c COMMON
  )
@end example
@end defmac

@defun generator-any pred gen
@defunx generator-every pred gen
[SRFI-158]
@c MOD gauche.generator
@c EN
Like @code{any} and @code{every} (@pxref{Walking over lists}), but
works on a generator.
@c JP
@code{any}、@code{every} (@pxref{Walking over lists}) と同じですが、
ジェネレータに対して使えます。
@c COMMON
@end defun

@defun generator-count pred gen
[SRFI-158]
@c MOD gauche.generator
@c EN
Returns the number of items in a generator @var{gen}
that satisfies @var{pred}.
As a side effect, @var{gen} is exhausted.
@c JP
@var{gen}が生成する要素ののうち、@var{pred}を満たすものの個数を返します。
副作用として@var{gen}は使い尽くされます。
@c COMMON
@end defun

@defun generator-unfold gen unfold arg @dots{}
[SRFI-158]
@c MOD gauche.generator
@c EN
Apply @var{unfold} using the values generated from a generator @var{gen}
as seeds.  It is equivalent to the following expression:
@c JP
@var{gen}が生成する値をseedとして@var{unfold}を適用します。次の式と同じです:
@c COMMON

@code{(@var{unfold} eof-object? identity (^_ (@var{gen})) (@var{gen}) @var{arg} @dots{})}

@c EN
The @var{unfold} procedure must have the signature
@code{(unfold stop? mapper successor seed arg @dots{})}, like @code{unfold}
in @code{scheme.list} (@pxref{R7RS lists}).
@c JP
@var{unfold}手続きは、
@code{scheme.list}モジュールの@code{unfold}(@pxref{R7RS lists}参照)のように、
次のとおり引数を取らなければなりません:
@code{(unfold stop? mapper successor seed arg @dots{})}。
@c COMMON

@c EN
It can be seen as a general method to convert a generator to a sequence,
an inverse of @code{x->generator}.
@c JP
これはジェネレータをシーケンスに変換する一般的な方法と見ることができます。
@code{x->generator}の反対です。
@c COMMON

@example
(generator-unfold (x->generator "abc") string-unfold)
  @result{} "abc"
@end example
@end defun


@c ----------------------------------------------------------------------
@node Hooks, Interactive session, Generators, Library modules - Gauche extensions
@section @code{gauche.hook} - Hooks
@c NODE フック, @code{gauche.hook} - フック

@deftp {Module} gauche.hook
@mdindex gauche.hook
@c EN
Provides a hook object, which manages a list of closures to be
called at certain time.

This API of hooks are upper-compatible of Guile's, with the
following extensions.
@c JP
フックオブジェクトを提供します。これは、特定のタイミングで
呼び出されるクロージャのリストを管理するものです。

フックのAPIはGuileのそれと上方互換で、下記のように拡張されています。
@c COMMON
@itemize @bullet
@item
@c EN
Based on Gauche's object system.  Most APIs are methods
so you can extend the hook features.
@c JP
Gaucheのオブジェクトシステムをベースにしています。
ほとんどのAPIはメソッドなので、フックの機能を拡張することが
できます。
@c COMMON
@item
@c EN
Hook object itself is applicable.  You don't need to use @code{run-hook}.
@c JP
フックオブジェクトはそれ自身適用可能です。@code{run-hook}を使う必要は
ありません。
@c COMMON
@item
@c EN
The method to remove a procedure from a hook is called @code{delete-hook!},
for consistency with SRFI-1 and others.  @code{remove-hook!} is
defined as an alias of @code{delete-hook!} for compatibility with Guile.
@c JP
フックから手続きを削除するメソッドは、SRFI-1やその他との一貫性の
ために@code{delete-hook!}と呼ばれます。
Guileとの互換性のために、@code{remove-hook!}が@code{delete-hook!}の
エイリアスとして定義されています。
@c COMMON
@end itemize

@c EN
If you're writing portable code, SRFI-173 provides the basic
hook functionality (@pxref{Hooks (srfi)}).
@c JP
ポータブルなコードを書いているなら、SRFI-173が基本的なフック機能を
提供しています (@ref{Hooks (srfi)}参照)。
@c COMMON
@end deftp

@deftp {Class} <hook>
@clindex hook
@c MOD gauche.hook
@c EN
A hook class, which keeps a list of procedures to be called at once.

The @code{object-apply} method is defined on @code{<hook>} class,
so you can "apply" a hook object as if it were a procedure---which
causes all the registered procedure to be invoked.
@c JP
フックのクラスで、一度に呼び出される手続きのリストを保持しています。

@code{<hook>}クラスには@code{object-apply}メソッドが定義されているので、
あたかもそれが手続きであるかのようにフックオブジェクトを``適用''できます。
フックオブジェクトを適用すると、登録されている全ての手続きが呼び出されます。
@c COMMON
@end deftp

@defun make-hook :optional (arity 0)
@c MOD gauche.hook
@c EN
Creates a new hook object with given arity, which should be a
non-negative integer.
@c JP
与えられたアリティ(正の整数でなければなりません)とともに新しい
フックオブジェクトを作成します。
@c COMMON
@end defun

@defun hook? obj
@c MOD gauche.hook
@c EN
Returns true if @var{obj} is a hook object.
@c JP
@var{obj}がフックオブジェクトであれば、真を返します。
@c COMMON
@end defun

@defun hook-empty? hook
@c MOD gauche.hook
@c EN
Returns true if @var{hook}'s procedure list is empty.
@c JP
@var{hook}の手続きリストが空なら、真を返します。
@c COMMON
@end defun

@deffn {Method} add-hook! (hook <hook>) proc :optional (append? #f)
@c MOD gauche.hook
@c EN
Adds a procedure @var{proc} to @var{hook}.  If @var{append?}
is given and true, @var{proc} is added at the end of the list.
Otherwise, @var{proc} is added at the front of the list.
The @var{proc} has to be called with the arity given
at the @code{make-hook}.
@c JP
手続き@var{proc}を@var{hook}に追加します。
@var{append?}が与えられ真であれば、@var{proc}はリストの最後に
追加されます。そうでなければ、@var{proc}はリストの最初に追加
されます。
@var{proc}は、@code{make-hook}時に与えられたアリティとともに
呼ばれなければなりません。
@c COMMON
@end deffn

@deffn {Method} delete-hook! (hook <hook>) proc
@deffnx {Method} remove-hook! (hook <hook>) proc
@c MOD gauche.hook
@c EN
Removes @var{proc} from the procedure list of @var{hook}.
@code{Remove-hook!} is an alias of @code{delete-hook!} just for
compatibility with Guile.
@c JP
@var{hook}の手続きリストから@var{proc}を削除します。
Guileとの互換性のためだけに、@code{remove-hook!}が@code{delete-hook!}の
エイリアスとなっています。
@c COMMON
@end deffn

@deffn {Method} reset-hook! (hook <hook>)
@c MOD gauche.hook
@c EN
Empties @var{hook}'s procedure list.
@c JP
@var{hook}の手続きリストを空にします。
@c COMMON
@end deffn

@deffn {Method} hook->list (hook <hook>)
@c MOD gauche.hook
@c EN
Returns a copy of @var{hook}'s procedure list.
@c JP
@var{hook}の手続きリストのコピーを返します。
@c COMMON
@end deffn

@deffn {Method} run-hook (hook <hook>) arg @dots{}
@c MOD gauche.hook
@c EN
Calls @var{hook}'s procedures in order, with arguments @var{arg} @dots{}.
The number of arguments must match the arity given at @code{make-hook}.
@c JP
@var{hook}の手続きを、@var{arg} @dots{}を引数として順番に呼び出します。
引数の数は、@code{make-hook}時に与えられたアリティにマッチしなければ
なりません。
@c COMMON
@end deffn

@c ----------------------------------------------------------------------
@node Interactive session, Lazy sequence utilities, Hooks, Library modules - Gauche extensions
@section @code{gauche.interactive} - Utilities for interactive session
@c NODE インタラクティブセッション, @code{gauche.interactive} - インタラクティブセッション

@deftp {Module} gauche.interactive
@mdindex gauche.interactive
@c EN
Provides useful utilities for the interactive session.

This module is automatically loaded when you run @code{gosh}
interactively.

This module also sets autoloads for functions defined in
@code{gauche.reload} module
(see @ref{Reloading modules}), so that
those functions can be used by default in interactive development.
@c JP
インタラクティブセッションで便利なユーティリティ手続きを提供します。

@code{gosh}をインタラクティブモードで起動した場合、
このモジュールは自動的にロードされます。

また、このモジュールは@code{gauche.reload}
(@ref{Reloading modules}参照)で定義される
手続きに対してautoloadを設定し、それらの手続きが
インタラクティブな開発時にデフォルトで使えるようにします。
@c COMMON
@end deftp

@defmac apropos pattern :optional module
@c MOD gauche.interactive
@c EN
Show a list of defined variables whose name matches @var{pattern}.
If you give a module or a module name @var{module}, only the variables
defined in that module are listed.  Without @var{module},
the variables "visible" from the current module are listed.
@c JP
名前が@var{pattern}にマッチするような定義された変数のリストを表示します。
@var{module}にモジュールオブジェクトまたはモジュール名を与えた場合は、
そのモジュール内で定義されている変数のみが表示されます。@var{module}が
省略された場合は、カレントモジュールから「見える」変数が全て表示されます。
@c COMMON

@c EN
@var{pattern} may be a symbol or a regexp object.
If it is a symbol, the variables whose name contains the
substring that matches the symbol's name are listed.
If it is a regexp object, the variables whose name matches
the regexp are listed.
@c JP
@var{pattern}はシンボルか正規表現オブジェクトでなければなりません。
シンボルの場合、そのシンボル名を部分文字列として名前に含むような変数が
リストされます。正規表現オブジェクトの場合は、その正規表現にマッチする
名前を持つ変数がリストされます。
@c COMMON

@c EN
Some examples:
@c JP
いくつか例を示します。
@c COMMON
@example
@c EN
;; @r{List variables that contains "string" in their name}
@c JP
;; @r{"string"を名前に含む変数を表示}
@c COMMON
(apropos 'string)

@c EN
;; @r{Search in srfi.14 module}
@c JP
;; @r{srfi.14モジュールの中のみを検索}
@c COMMON
(apropos 'char 'srfi.14)
@end example
@end defmac

@defun d :optional obj
@c MOD gauche.interactive
@c EN
This is defined as an alias of @code{describe}
(@pxref{Describing instance}, for the details).
The short name is for the convenience, but in REPL you may find
use @code{,d} toplevel command more convenient now.
@c JP
これは@code{describe}の別名として定義されています
(詳しくは@ref{Describing instance}参照)。
短い名前の方がREPLで打ちやすいからですが、
今ではREPLトップレベルコマンド@code{,d}の方が使いやすいでしょう。
@c COMMON
@end defun

@c EN
This module also adds some methods to the generic function @code{describe}
for built-in objects.
@c JP
このモジュールはまた、ジェネリックファンクション@code{describe}にいくつか
組み込みオブジェクト向けのメソッドを追加します。
@c COMMON

@deffn {Method} describe
@c EN
When called without arguments, it describes the object bound to @code{*1},
the last result of REPL.
@c JP
引数なしで呼ばれた場合、REPLでの直近の評価値が束縛されている@code{*1}の値を
describeします。
@c COMMON
@end deffn

@deffn {Method} describe (s <symbol>)
@c EN
Customized describe method for symbols.  It shows known bindings
for the symbol as well (it is looked for in the loaded modules).
@c JP
シンボル用にカスタマイズされたdescribeです。
ロードされているモジュール中からそのシンボルへの束縛を探して表示します。
@c COMMON
@example
gosh$ ,d 'filter
filter is an instance of class <symbol>
Known bindings for variable filter:
  In module `gauche.collection':
    #<generic filter (2)>
  In module `gauche':
    #<closure (filter pred lis)>
@end example
@end deffn

@deffn {Method} describe (c <char>)
@c EN
Customized describe method for characters.
It shows its Unicode codepoint and general category.
@c JP
文字用にカスタマイズされたdescribeです。
Unicodeコードポイントとジェネラルカテゴリを表示します。
@c COMMON
@example
gosh$ ,d #\π
#\π is an instance of class <char>
  (U+03c0, Ll)
@end example
@end deffn

@deffn {Method} describe (n <integer>)
@c EN
Customized describe method for exact integers.
Depending on the value range, it shows several informations: A hexadecimal
notation, 1024-base approximated value (useful for memory and storage
size), character as Unicode codepoint, and
time as Unix time.
@c JP
正確な整数用にカスタマイズされたdescribeです。
値の範囲に応じて、いくつかの情報を示します。
16進数表示、1024単位の概数(メモリやストレージのサイズに便利です)、
Unicodeコードポイントとして見た場合の文字、
そしてUnix timeとして見た場合の時刻です。
@c COMMON
@example
gosh$ ,d 1234
1234 is an instance of class <integer>
  (#x4d2, ~ 1.2Ki, #\Ӓ as char, 1970-01-01T00:20:34Z as unix-time)
gosh$ ,d 12345678
12345678 is an instance of class <integer>
  (#xbc614e, ~ 11Mi, 1970-05-23T21:21:18Z as unix-time)
gosh$ ,d 12345678901234567890
12345678901234567890 is an instance of class <integer>
  (#xab54a98c_eb1f0ad2, ~ 10Ei)
@end example
@end deffn

@deffn {Method} describe (r <rational>)
@c EN
Customized describe method for exact rationals.
It shows the floating point number as coerced into inexact.
@c JP
正確な有理数用にカスタマイズされたdescribeです。
非正確数に変換された場合の小数表示も示します。
@c COMMON
@example
gosh$ ,d 1234/5678
617/2839 is an instance of class <rational>
  inexact: 0.2173300457907714
@end example
@end deffn

@deffn {Method} describe (d <real>)
@c EN
Customized describe method for inexact reals.
It shows binary representation of the flonum, and
rational representation as coerced into exact.
@c JP
不正確な実数用にカスタマイズされたdescribeです。
浮動小数点数としてのバイナリ表現と、
正確数に変換された場合の有理数表示も示します。
@c COMMON
@example
gosh$ ,d 3.14159265358979
3.14159265358979 is an instance of class <real>
  mantissa: #x+19_21fb_5444_2d11   exponent: -51    hex: #x4009_21fb_5444_2d11
  exact: 144029661/45846065
@end example
@end deffn

@deffn {Method} describe (c <complex>)
@c EN
Customized describe method for complex numbers.
It shows polar representation as well.
@c JP
複素数用にカスタマイズされたdescribeです。
極座標形式も表示します。
@c COMMON
@example
gosh$ ,d (expt -2 1/4)
0.8408964152537146+0.8408964152537146i is an instance of class <complex>
  polar: 1.1892071150027212@@0.7853981633974483  (@@0.25pi)
@end example
@end deffn

@deffn {Method} describe (p <procedure>)
@deffnx {Method} describe (p <macro>)
@c EN
Customized describe method for procedures and macros,
showing the source location if avaiable.
For the procedure, its type signature is shown as well
(@code{procedure-type}, @pxref{Procedure class and applicability}).
@c JP
手続きとマクロ用にカスタマイズされたdescribeで、
ソースコード位置を(分かれば)表示します。
また、手続きについてはその型も表示します
(@code{procedure-type}、@ref{Procedure class and applicability}参照)。
@c COMMON
@example
gosh> ,d display-filled-text
#<closure (display-filled-text text :key (port (current-output-port))
(indent 0) (hanging 0) (width 65) (lead-in #f) (start-column #f))> is
an instance of class <procedure>
Defined at "/usr/share/gauche-0.98/0.9.15-p1/lib/text/fill.scm":111
type: #<^ <top> * -> *>
slots:
  required  : 1
  optional  : #t
  optcount  : 1
  locked    : #f
  currying  : #f
  constant  : #f
  info      : (display-filled-text text :key (port (current-output-port))
  setter    : #f
@end example
@end deffn


@deffn {Method} describe (g <generic>)
@c EN
Customized describe method for generic functions.
It shows the list of known methods, with the specializer list
and the source location of definition if known.
@c JP
ジェネリックファンクション用にカスタマイズされたdescribeです。
メソッドのリストも表示します。
メソッドは、スペシャライザーのリストと、わかれば定義のソース情報が示されます。
@c COMMON
@example
gosh$ ,d describe
#<generic describe (11)> is an instance of class <generic>
slots:
  name      : describe
  sealed    : #f
  info      : describe
  methods   : (#<method (describe <macro>)> #<method (describe <procedure>
methods:
  (<macro>)            ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":223
  (<procedure>)        ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":215
  (<method>)           ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":208
  (<generic>)          ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":189
  (<real>)             ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":172
  (<rational>)         ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":160
  (<integer>)          ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":128
  (<char>)             ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":123
  (<symbol>)           ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":118
  ()                   ; "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":116
  (<top>)
@end example
@end deffn

@deffn {Method} describe (m <method>)
@c EN
Customized describe method for methods.
It shows the source code location if available.
@c JP
メソッド用にカスタマイズされたdescribeです。
ソースコード位置が分かればそれも表示します。
@c COMMON
@example
gosh$ ,d (car (~ describe'methods))
#<method (describe <macro>)> is an instance of class <method>
Defined at "/usr/share/gauche-0.98/0.9.15-p1/lib/gauche/interactive.scm":223
slots:
  required  : 1
  optional  : #f
  method-locked: #f
  leaf?     : #t
  generic   : #<generic describe (11)>
  specializers: (#<class <macro>>)
  info      : (describe <macro>)
@end example
@end deffn


@defun info symbol
@c MOD gauche.interactive
@c EN
Displays an entry of the named function, syntax, module or class
from Gauche's info document.
If an environment variable @code{INFOPATH} is defined,
this function searches for the info file from the directories in it.
Otherwise, this function guesses info file location from the
@code{gosh}'s library directory.   If the info file can't be
found, an error is signaled.
So this function doesn't work if you haven't installed info file.
@c JP
Gaucheのinfoドキュメント中から、
@var{symbol}で指定される手続き、構文要素、モジュールもしくはクラスの
エントリを表示します。
もし環境変数@code{INFOPATH}が定義されていればそこに
示されるディレクトリ中から探され、そうでなければ@code{gosh}のライブラリディレクトリ
から推測されるディレクトリ中から探されます。
infoドキュメントが見付からなかった場合はエラーとなります。
つまり、この手続きはinfoファイルがインストールされていないと動作しません。
@c COMMON

@c EN
If no entry exactly matching with @var{symbol} is found, the procedure tries
to look for similar named entries:
@c JP
もし@var{symbol}に完全に一致するエントリが見つからなかった場合、
類似するエントリがあればそれらがリストされます:
@c COMMON

@example
gosh> (info 'stirng)
There is no entry for stirng.
Did you mean:
  string>
  string?
  string=
  string<
  string
  :string
@end example

@c EN
(If you want to search entries using pattern, see @code{info-serach} below.)
@c JP
(パターンにマッチするエントリを探したい場合は下の@code{info-search}を見てください)
@c COMMON

@c EN
If the current output port is a tty, the info page is displayed by
a paging software.  If an environment variable @code{PAGER} is defined,
it is used as a paging software.  Otherwise, this function looks for
@code{less} and @code{more} in this order from the directories in
@code{PATH}.  If none of them is found, or the output port is not
a tty, this function just displays the page.
@c JP
現在の出力ポートが端末である場合、infoドキュメントの該当ページは
ページングプログラムを用いて表示されます。環境変数@code{PAGER}が指定されていれば
それを用い、そうでなければコマンドサーチパスから@code{less}及び@code{more}を
この順で探します。いずれも見付からなかった場合や、出力ポートが端末では
ない場合には、単にページがそのまま出力されます。
@c COMMON

@c EN
The first invocation of this function in a session takes some time
to parse the info file.
@c JP
この手続きのセッション中での最初の呼び出しは、infoファイルをパーズするために
多少時間がかかります。
@c COMMON

@c EN
NB: When you use @code{less} as a pager, make sure you set
it to handle utf-8 characters (e.g. setting @code{LESSCHARSET}
environment variable to
@code{UTF-8}), or you'll see some escaped sequences on the screen.
@c JP
註: @code{less}をページャに使う場合、@code{less}がutf-8文字を扱えるように
設定してください (例えば@code{LESSCHARSET}環境変数を@code{UTF-8}にする)。
そうでないと画面にエスケープされた文字が表示されて見づらいです。
@c COMMON

@c EN
NB: If you invoke @code{gosh} within the build tree, using @code{-ftest}
option, @code{info} reads the info files in the build tree if they exist.
@c JP
註: @code{gosh}を@code{-ftest}オプションをつけてビルドツリー内で起動した場合、
@code{info}はビルドツリー内のinfoファイルを(もしあれば)読みます。
@c COMMON
@end defun

@defun info-search regexp
@c MOD gauche.interactive
@c EN
Lists info entries matching @var{regexp}.  See @code{info} above
about where the info files are searched.
@c JP
@var{regexp}にマッチするinfoのエントリをリストします。
infoファイルがどこから読まれるかについては上の@code{info}の説明を参照してください。
@c COMMON
@end defun

@defun ed filename-or-procedure :key editor load-after
@c MOD gauche.interactive
@c EN
Invoke an external editor to open the named file, or the file containing
the definition of the given procedure (if it can be known).
For the latter, it uses @code{source-location} procedure to find out
the source code location (@pxref{Debugging aid}).
@c JP
外部エディタを起動し、与えられた名前のファイル、もしくは与えられた手続きの定義がある
ファイルを開きます。後者については、与えられた手続きを
@code{source-location}に渡して定義箇所を調べます(@ref{Debugging aid}参照)。
定義箇所がわからなければファイルは開かれません。
@c COMMON

@c EN
The name of the editor to invoke is determined as follows:
@c JP
起動するエディタの名前は次の順序で決定されます。
@c COMMON

@enumerate
@item
@c EN
The @var{editor} keyword argument.
@c JP
キーワード引数@var{editor}。
@c COMMON
@item
@c EN
The value of the variable @code{*editor*} in the @code{user} module,
if defined.  This is handy that you can set this in your @code{.gaucherc}.
@c JP
@code{user}モジュール中の変数@code{*editor*}の値。
これは、@code{.gaucherc}内で設定しておくのが便利です。
@c COMMON
@item
@c EN
The value of the environment variable @code{GAUCHE_EDITOR}.
@c JP
環境変数@code{GAUCHE_EDITOR}の値
@c COMMON
@item
@c EN
The value of the environment variable @code{EDITOR}.
@c JP
環境変数@code{EDITOR}の値
@c COMMON
@end enumerate

@c EN
If none of the above is defined or @code{#f}, the procedure prompts the user
to type in the name of the editor.
@c JP
上記のどの値も定義されていないか@code{#f}なら、
手続き@code{ed}はユーザにエディタ名を入力するように促します。
@c COMMON

@c EN
Once the editor name is obtained, it is invoked as a subprocess,
with the following format:
@c JP
エディタの名前がわかったら、それが子プロセスとして次の形式で実行されます。
@c COMMON

@example
EDITOR +lineno filename
@end example

@c EN
The @var{lineno} is an integer line number, 1 being the first line.
The editor is expected to locate the cursor on the specified line.
@c JP
@var{lineno}は整数の行番号で、1が先頭行です。エディタは指定された行の頭に
カーソルを移動することが期待されます。
@c COMMON

@c EN
Once the editor process exits, the procedure checks if the named
file is updated.  If so, it may load the file, according to the
value of the @var{load-after} keyword argument.  It may take one
of the following values:
@c JP
エディタプロセスが終了したら、@code{ed}はファイルが更新されたかどうかを調べ、
更新された場合は@var{load-after}引数の値によってそのファイルをロードするかどうかを
決定します。@var{load-after}引数の値は以下のいずれかです。
@c COMMON

@table @code
@item #t
@c EN
Load the file automatically if it's updated.
@c JP
ファイルが更新されていれば自動的にロード
@c COMMON
@item #f
@c EN
Do not load the file.
@c JP
ファイルをロードしない
@c COMMON
@item ask
@c EN
The symbol @code{ask} cause the procedure to prompt the user
whether it should load the file.  This is the default.
@c JP
シンボル@code{ask}の場合は、ロードすべきかどうかユーザに尋ねる。
これがデフォルトの動作です。
@c COMMON
@end table
@end defun


@c ----------------------------------------------------------------------
@node Lazy sequence utilities, Listener, Interactive session, Library modules - Gauche extensions
@section @code{gauche.lazy} - Lazy sequence utilities
@c NODE 遅延シーケンスユーティリティ, @code{gauche.lazy} - 遅延シーケンスユーティリティ

@deftp {Module} gauche.lazy
@mdindex gauche.lazy
@c EN
This module provides utility procedures that yields lazy sequences.
For the details of lazy sequences, @pxref{Lazy sequences}.
@c JP
このモジュールは、遅延シーケンスを生成するようなユーティリティ手続きの数々を提供します。
遅延シーケンス自体については@ref{Lazy sequences}を参照してください。
@c COMMON
@end deftp

@c EN
Since lazy sequences are forced implicitly and indistinguishable
from ordinary lists, we don't need a separate set of procedures
for @emph{taking} lists and lazy sequences; we can use @code{find}
to search in both ordinary lists and lazy sequences.
@c JP
遅延シーケンスは自動的にforceされ、通常のリストと区別がつかないので、
@emph{引数に}リストを取るか遅延シーケンスを取るかで別々の手続きを用意する必要はありません。
例えば@code{find}は、リストから要素を探すのにも遅延シーケンスから要素を探すのにも使えます。
@c COMMON

@c EN
However, we do need a separate set of procedures
for @emph{returning} either lists or lazy sequences.  For example,
@var{lmap} can take any kind of sequences, and
returns lazy sequence (and calls the procedure on demand).
@c JP
しかし、@emph{返り値として}リストを返すか遅延シーケンスを返すかは、
手続きを別にする必要があります。
例えば@var{lmap}は、引数としてはどちらも受け取ることができますが、
返り値は遅延シーケンスになります。(そして、高階手続きは必要な分だけ呼ばれます。)
@c COMMON

@c EN
This distinction is subtle, so I reiterate it.  You can use
both @code{map} and @code{lmap} on lazy sequences.  If you want
the result list at once, use @code{map}; it doesn't have
overhead of delayed calculation.  If you don't know you'll use
the entire result, or you know the result will get very large
list and don't want to waste space for an intermediate list,
you want to use @code{lmap}.
@c JP
この区別は混乱しやすいので、整理しておきます。
@code{map}と@code{lmap}のどちらも、遅延シーケンスに適用することができます。
結果のリストを一度に計算した状態で手に入れたいなら、@code{map}を使います。
その場合、遅延計算のオーバヘッドはかかりません。
もし結果のリスト全てを使うかどうかわからない、
あるいは結果のリストが巨大になるので中間結果の保持のためにメモリを圧迫したくない、
といった場合には@code{lmap}を使いましょう。
@c COMMON

@menu
* Lazy sequence constructors::
* Lazy sequence operations::
* Lazy sequence with positions::
@end menu

@node Lazy sequence constructors, Lazy sequence operations, Lazy sequence utilities, Lazy sequence utilities
@subsection Lazy sequence constructors
@c NODE 遅延シーケンスのコンストラクタ

@c EN
You can construct lazy sequences with
built-in @code{generator->lseq} and @code{lcons}.
This module provides a few more constructors.
@c JP
遅延シーケンスは組み込みの@code{generator->lseq}や@code{lcons}で作ることができます。
このモジュールでは追加でいくつかのコンストラクタを用意しています。
@c COMMON

@defun x->lseq obj
@c MOD gauche.lazy
@c EN
A convenience function to coerce @var{obj} to (possibly lazy) list.
If @var{obj} is a list, it is returned as it is.  If @var{obj} is
other type of collection, the return value is a lazy sequence
that iterates over the collection.  If @var{obj} is other object,
it is returned as it is (you can think of it as a special case
of dotted list).

If you try @code{x->lseq} in REPL, it looks as if it just
converts the input collection to a list.
@c JP
@var{obj}を(おそらく遅延された)リストに変換する便利な手続きです。
@var{obj}がリストならそのまま返されます。
@var{obj}が他のコレクション型なら、コレクションの各要素を順に返す遅延シーケンスが返されます。
@var{obj}がそれ以外ならやはりそのまま返されます(ドットリストの特別な場合と考えられます)。

REPLで@code{x->lseq}を試すと、単に渡したコレクションをリストに変換しているだけのように見えるでしょう。
@c COMMON

@example
(x->lseq '#(a b c)) @result{} (a b c)
@end example

@c EN
But that's because the lazy sequence is forced by the output
routine of the REPL.
@c JP
実際には、返された遅延シーケンスがREPLの出力ルーチンによってforceされてリストになっています。
@c COMMON
@end defun

@defun lunfold p f g seed :optional tail-gen
@c MOD gauche.lazy
@c EN
A lazy version of @code{unfold} (@pxref{R7RS lists}).
The arguments @var{p}, @var{f} and @var{g} are procedures,
each of which take one argument, the current seed value.
The predicate @var{p} determines when to stop, @var{f} creates
each element, and @var{g} generates the next seed value.
The @var{seed} argument gives the initial seed value.
If @var{tail-gen} is given, it should also be a procedure
that takes one argument, the last seed value (that is, the
seed value @code{(p seed)} returned @code{#f}).  It must return
a (possibly lazy) list, that forms the tail of the resulting sequence.
@c JP
@code{unfold}の遅延バージョンです (@ref{R7RS lists}参照)。
@var{p}、@code{f}、@code{g}引数はそれぞれ1引数を取る手続きで、
現在のシード値を受けとります。
@var{p}は生成を停止するかどうかを決める述語、
@var{f}は要素を生成する手続き、そして
@var{g}は次のシード値を生成する手続きです。
@var{seed}引数には最初のシード値を与えます。
@var{tail-gen}が与えられた場合、それは最後のシード値
(つまり、@code{(p seed)}が@code{#f}を返した時のシード値)を
受け取り、リストあるいは遅延シーケンスを返す手続きです。
それが結果のシーケンスの末尾に付け足されます。
@c COMMON

@example
(lunfold ($ = 10 $) ($ * 2 $) ($ + 1 $) 0 (^_ '(end)))
  @result{} (0 2 4 6 8 10 12 14 16 18 end)
@end example
@end defun

@defun literate proc seed
@c MOD gauche.lazy
@c EN
Creates an infinite sequence of
@code{(@var{seed} (@var{proc} @var{seed}) (@var{proc} (@var{proc} @var{seed})) @dots{})}.

The same sequence can be created with
@code{(lunfold (^_ #f) identity proc seed)},
but this one is a lot more efficient.

See also @code{util.stream}, which as @code{stream-iterate}
(@pxref{Stream constructors}).
@c JP
@code{(@var{seed} (@var{proc} @var{seed}) (@var{proc} (@var{proc} @var{seed})) @dots{})} という無限シーケンスを作ります。

同じシーケンスは@code{(lunfold (^_ #f) identity proc seed)}でも作れますが、
こちらの方がずっと効率的です。

類似の手続きとして、@code{util.stream}に@code{stream-iterate}があります
(@ref{Stream constructors}参照)。
@c COMMON

@example
(take (literate (pa$ + 1) 0) 10)
 @result{} (0 1 2 3 4 5 6 7 8 9)
@end example
@end defun

@defun coroutine->lseq proc
@c MOD gauche.lazy
@c EN
The @var{proc} procedure is called with one argument,
@var{yield}, which is also a procedure that takes one argument.
Whenever @var{yeild} is called, the value passed to it
becomes the next element of resulting lseq.
When @var{proc} returns, lseq ends.
@c JP
@var{proc}引数がひとつの引数@var{yield}を伴って呼び出されます。
@var{yeidl}はそれ自体がひとつの引数を取る手続きで、呼ばれるとそこに渡された
値が、結果のlseqの要素となります。@var{proc}からリターンしたらlseqも終了となります。
@c COMMON

@example
(coroutine->lseq (^[yield] (dotimes [i 10] (yield (square i)))))
  @result {} (0 1 4 9 16 25 36 49 64 81)
@end example

@c EN
See also @code{generate} (@ref{Generator constructors}), and
@code{coroutine->cseq} (@ref{Concurrent sequences}).
@c JP
@ref{Generator constructors}の@code{generate}、および
@ref{Concurrent sequences}の@code{coroutine->cseq}も参照。
@c COMMON
@end defun


@node Lazy sequence operations, Lazy sequence with positions, Lazy sequence constructors, Lazy sequence utilities
@subsection Lazy sequence operations
@c NODE 遅延シーケンスの操作

@defun lseq->list obj
@c MOD gauche.lazy
@c EN
Returns @var{obj}, but if it is an lseq, fully computes all values.
It is useful when you need to ensure necessary compuatation is done
by certain moment, e.g. you want to ensure all data is read from a port before
closing it.
@c JP
@var{obj}を返しますが、それがlseqであった場合、その要素を全て計算します。
ある時点までに必要な計算が全て行われることを保証したい場合に便利です。
例えばポートから遅延計算でデータを読み出している場合に、
ポートを閉じる時点で全てのデータが読まれたことを保証したい、といった場合です。
@c COMMON
@end defun

@defun lmap proc seq seq2 @dots{}
@c MOD gauche.lazy
@c EN
Returns a lazy sequence consists of values calculated
by applying @var{proc} to every first element of @var{seq} @var{seq2}
@dots{}, every second element of them, etc., until any of
the input is exhausted.
Application of @var{proc} will be delayed as needed.
@c JP
@var{proc}を@var{seq} @var{seq2} @dots{}の各1番目の要素、各2番目の要素、@dots{}
に適用したものからなる遅延シーケンスを返します。
どれかの入力が尽きた時が結果のシーケンスの終わりとなります。
@var{proc}の適用は必要になるまで遅延されます。
@c COMMON

@example
@c EN
;; If you use map instead of lmap, this won't return
@c JP
;; lmapのかわりにmapを使うとこの式の評価は終わらない
@c COMMON
(use math.prime)
(take (lmap (pa$ * 2) *primes*) 10)
  @result{} (4 6 10 14 22 26 34 38 46 58)
@end example
@end defun

@defun lmap-accum proc seed seq seq2 @dots{}
@c MOD gauche.lazy
@c EN
The procedure @var{proc} takes one element each from
@var{seq} @var{seq2} @dots{}, plus the current seed value.
It must return two values, a result value and the next seed value.
The result of @code{lmap-accum} is a lazy sequence consists
of the first values returned by each invocation of @var{proc}.
@c JP
@var{proc}は各シーケンス@var{seq} @var{seq2} @dots{}からの要素一つづつと、
現在のシード値を取り、結果の要素値と次のシード値を返す手続きです。
@var{lmap-accum}の結果は、@var{proc}が生成する要素値からなる遅延シーケンスとなります。
@c COMMON

@example
(use math.prime)
(take (lmap-accum (^[p sum] (values sum (+ p sum))) 0 *primes*) 10)
  @result{} (0 2 5 10 17 28 41 58 77 100)
@end example

@c EN
This is a lazy version of @code{map-accum} (@pxref{Mapping over collection}),
but @code{lmap-accum} does not return the final seed value.  We only
know the final seed value when we have the result sequence to the
end, so it can't be calculated lazily.
@c JP
これは@code{map-accum}の遅延バージョンです(@ref{Mapping over collection}参照)。
ただ、@code{lmap-accum}は最後のシード値を返しません。
最後のシード値を返すためには結果の遅延シーケンスを最後まで計算する必要があるので、
遅延計算にならないからです。
@c COMMON
@end defun

@defun lappend seq @dots{}
@c MOD gauche.lazy
@c EN
Returns a lazy sequence which is concatenation of @var{seq} @dots{}.
Unlike @code{append}, this procedure returns immediately, taking O(1) time.
It is useful when you want to append large sequences but may use
only a part of the result.
@c JP
シーケンス@var{seq} @dots{}をつなぎ合わせた遅延シーケンスを返します。
@code{append}と違い、この手続きはO(1)時間で、すぐに返ります。
従って、大きなシーケンスをつなぎ合わせたいけれど全部使うとは限らない、といった場合に便利です。
@c COMMON
@end defun

@defun lconcatenate seqs
@c MOD gauche.lazy
@c EN
The @var{seqs} argument is a sequence of sequences.  Returns
a lazy sequence that is a concatenation of all the sequences in @var{seqs}.

This differs from @code{(apply lappend seqs)}, for @code{lconcatenate}
can handle infinite number of lazy @var{seqs}.
@c JP
@var{seqs}引数はシーケンスのシーケンスです。
それら各シーケンスを全てつなぎ合わせた遅延シーケンスを返します。

これと@code{(apply lappend seqs)}との違いは、@code{lconcatenate}は
無限個の@var{seq}をつなぎ合わせられるということです。
@c COMMON
@end defun

@defun lappend-map proc seq1 seq @dots{}
@c MOD gauche.lazy
@c EN
Lazy version of @code{append-map}.   This differs from a simple
composition of @var{lappend} and @var{lmap}, since
@code{(apply lappend (lmap proc seq1 seq @dots{}))} would
evaluate the result of @code{lmap} to the end before passing it to
@code{lappend} (it's because @code{apply} need to determine
the list of arguments before calling @code{lappend}).
@c JP
@code{append-map}の遅延バージョンです。
これは単に@code{lappend}と@code{lmap}を合成したものとは異なります。
というのも、@code{(apply lappend (lmap proc seq1 seq @dots{}))}では、
@code{apply}が引数リストを確定するために@code{lmap}を最後まで評価しなければ
ならないからです。
@c COMMON

@c EN
It also differs from
@code{(lconcatenate (lmap proc seq1 seq @dots{}))} in the subtle way.
@c JP
また、これは@code{(lconcatenate (lmap proc seq1 seq @dots{}))}とも
微妙に異なります。
@c COMMON

@c EN
Remember that Gauche's lazy sequence evaluates one element ahead?
@code{lconcatenate} does that to the result of @code{lmap}.
To see the effect, let's define a procedure with a debug print:
@c JP
Gaucheの遅延シーケンスは1つ要素を余分に評価することを覚えていますか。
@code{lconcatenate}は@code{lmap}の結果に対して「一つ余分に評価」を行います。
この効果を調べるために、デバッグプリントをつけた手続きを使ってみましょう。
@c COMMON

@example
(define (p x) #?=(list x x))
@end example

@c EN
You can see in the following example
that @code{(apply lappend (lmap ...))} wouldn't delay
any of application of @code{p}:
@c JP
次の例で、@code{(apply lappend (lmap ...))}が@code{p}
の適用を遅延しないことがわかります。
@c COMMON

@example
gosh> (car (apply lappend (lmap p '(1 2 3))))
(car (apply lappend (lmap p '(1 2 3))))
#?="(standard input)":4:(list x x)
#?-    (1 1)
#?="(standard input)":4:(list x x)
#?-    (2 2)
#?="(standard input)":4:(list x x)
#?-    (3 3)
1
@end example

@c EN
How about @code{lconcatenate}?
@c JP
@code{lconcatenate}はどうでしょう。
@c COMMON

@example
gosh> (car (lconcatenate (lmap p '(1 2 3))))
(car (lconcatenate (lmap p '(1 2 3))))
#?="(standard input)":4:(list x x)
#?-    (1 1)
#?="(standard input)":4:(list x x)
#?-    (2 2)
1
@end example

@c EN
Oops, even though we need only the first element, and the first
result of @code{lmap}, @code{(1 1)}, provides the second element, too,
@code{p} is already applied to the second input.
@c JP
おっと、最初の要素だけを取り出しているので、
@code{lmap}の最初の結果である@code{(1 1)}だけが必要なはずなのに、
@code{p}は2番目の入力に対しても適用されてしまいました。
@c COMMON

@c EN
This is because the intermediate lazy list of the result of @code{lmap} is
evaluated ``one element ahead''.   On the other hand, @code{lappend-map}
doesn't have this problem.
@c JP
これは、@code{lmap}の結果である中間の遅延リストが「1要素余分に」評価されるためです。
@code{lappend-map}にはこの問題がありません。
@c COMMON

@example
gosh> (car (lappend-map p '(1 2 3)))
(car (lappend-map p '(1 2 3)))
#?="(standard input)":4:(list x x)
#?-    (1 1)
1
@end example
@end defun

@defun linterweave seq @dots{}
@c MOD gauche.lazy
@c EN
Returns a lazy seq of the first items from @var{seq} @dots{}, then
their second items, and so on.   If the length of shortest sequence
of @var{seqs} is N, the length of the resulting sequence is
@code{(* N number-of-sequences)}.  If all of @var{seq}s are infinite,
the resulting sequence is also infinite.
@c JP
@var{seq} @dots{}の最初の要素を順番に取り、次に2番目の要素を順番に取り…として
得られる遅延シーケンスを返します。
入力のシーケンスのうち最も短いシーケンスの長さを@code{N}とすれば、
結果の遅延シーケンスの長さは@code{(* N シーケンスの数)}となります。
もし全ての入力シーケンスが無限長ならば、結果も無限長となります。
@c COMMON

@example
(linterweave (lrange 0) '(a b c d e) (circular-list '*))
 @result{} (0 a * 1 b * 2 c * 3 d * 4 e *)
@end example
@end defun

@defun lfilter proc seq
@c MOD gauche.lazy
@c EN
Returns a lazy sequence that consists of non-false values calculated
by applying @var{proc} on every elements in @var{seq}.
@c JP
@var{proc}を@var{seq}の各要素に適用し、@code{#f}でない値だけを集めた遅延シーケンスを
返します。
@c COMMON
@end defun

@defun lfilter-map proc seq seq2 @dots{}
@c MOD gauche.lazy
@c EN
Lazy version of @code{filter-map}.
@c JP
@code{filter-map}の遅延バージョンです。
@c COMMON
@end defun

@defun lstate-filter proc seed seq
@c MOD gauche.lazy
@c EN
Lazy sequence version of @code{gstate-filter} (@pxref{Generator operations}).
@c JP
@code{gstate-filter}の遅延シーケンス版です (@ref{Generator operations}参照)。
@c COMMON
@end defun

@defun ltake seq n :optional fill? padding
@defunx ltake-while pred seq
@c MOD gauche.lazy
@c EN
Lazy versions of @code{take*} and @code{take-while}
(@pxref{List accessors and modifiers}).   Note that
@code{ltake} works rather like @code{take*} than @code{take},
that is, it won't complain if the input sequence has less than @var{n}
elements.  Because of the lazy nature of @code{ltake}, it can't know
whether input is too short or not before returning the sequence.
@c JP
@code{take*}と@code{take-while}の遅延バージョンです
(@ref{List accessors and modifiers}参照)。
@code{ltake}は@code{take}ではなく@code{take*}のように動作します。
つまり、入力シーケンスの長さが@code{n}以下でもエラーになりません。
というもの、@code{ltake}は怠惰に動作するため、
値を返す時点では入力が足りないかどうかわからないからです。
@c COMMON

@c EN
There are no @code{ldrop} and @code{ldrop-while}; you don't need them.
if you apply
@code{drop} and @code{drop-while} on lazy sequence, they return
lazy sequence.
@c JP
@code{ldrop}と@code{ldrop-white}はありません。必要ないからです。
@code{drop}と@code{drop-white}を遅延シーケンスに適用すれば、
遅延シーケンスが返されます。
@c COMMON
@end defun

@defun lrxmatch rx seq
@c MOD gauche.lazy
@c EN
This is a lazy sequence version of @code{grxmatch}
(@pxref{Generator operations}).

The @var{seq} argument must be a sequence of characters (including
ordinary strings).
The return value is a lazy sequence of @var{<rxmatch>} objects,
each representing strings matching to the regular expression @var{rx}.
@c JP
@code{grxmatch}の遅延シーケンス版です(@ref{Generator operations}参照)。

@var{seq}は文字のシーケンス (文字列を含む) でなければなりません。
返り値は@var{<rxmatch>}オブジェクトからなる遅延シーケンスです。
各要素の@var{<rxmatch>}オブジェクトが、
入力中の@var{rx}にマッチした部分を表現しています。
@c COMMON

@c EN
This procedure is convenient to scan character sequences from
lazy character sequences, but it may be slow if you're looking for
rarely matching string from very large non-string input.
Unless @var{seq} is a string,
@code{lrxmatch} buffers certain length of input,
and if matching phrase isn't found, it extend the buffer and scan
again from the beginning, since the match may span from the end of
previous chunk to the newly added portion.
@c JP
この手続きは遅延文字シーケンス中からマッチするパターンを探すのに便利ですが、
入力が文字列ではなく、パターンが滅多にマッチしない場合に非常に遅くなる危険があることに
注意してください。@code{lrxmatch}は入力をある程度バッファしてスキャンし、
マッチがみつからなければ、バッファを拡張してまた最初からスキャンします。
というのも、新たなマッチが以前のバッファの末尾から新たに追加された部分へと
またがっている可能性があるからです。
@c COMMON
@end defun

@defun lslices seq k :optional fill? padding
@c MOD gauche.lazy
@c EN
Lazy version of @code{slices} (@pxref{List accessors and modifiers}).
@c JP
@code{slices}の遅延バージョンです(@ref{List accessors and modifiers}参照)。
@c COMMON

@example
(lslices '(a b c d e f) 2)
  @result{} ((a b) (c d) (e f))
@end example
@end defun

@node Lazy sequence with positions,  , Lazy sequence operations, Lazy sequence utilities
@subsection Lazy sequence with positions
@c NODE 位置情報つき遅延シーケンス

@c EN
Treating input data stream as a lazy sequence is a powerful abstraction;
especially, it allows unlimited lookahead with simple list manipulation.
@c JP
入力データストリームを遅延シーケンスとして取り扱うのは強力な抽象化です。
とりわけ、単純なリスト操作を使って制限の無い先読みを実現できます。
@c COMMON

@c EN
However, you'll have a difficulty when you want to know the position
of the input data within the input stream, e.g. for an error message.
Unlike reading from a port, which gives you the current input position,
a lazy sequence just looks like a list and unknown amout of data
may be prefetched from the real source.
@c JP
しかし、データの入力ストリーム内での位置情報を、例えばエラーメッセージのために取りたいといった
ことは難しくなります。ポートから読んでいる場合は、ポートに問い合わせれば現在の位置を
教えてくれます。しかし遅延シーケンスは普通のリストと同じように見え、
入力ソースに問い合わせようにも既にデータは先読みされてしまっているかもしれません。
@c COMMON

@c EN
Gauche has special pair objects, called extended pairs, that can
carry auxiliary information (@pxref{Extended pairs and pair attributes}).
You can create a lazy sequence that carries positional information
using the feature.
@c JP
Gaucheは拡張ペアと呼ばれる、補助的な情報を保持できる特別なペアを持っています
(@ref{Extended pairs and pair attributes}参照)。それを利用して、
遅延シーケンスに入力位置情報を持たせることができます。
@c COMMON

@deftp {Class} <sequence-position>
@c MOD gauche.lazy
@c EN
An immutable structure holding positional information.  It is returned
by @code{lseq-position}.  The information is queried by
the following procedure.
@c JP
位置情報を保持する変更不可な構造で、@code{lseq-position}から返されます。
情報は以下の手続きでアクセスできます。
@c COMMON
@end deftp

@defun sequence-position-source seqpos
@defunx sequence-position-line seqpos
@defunx sequence-position-column seqpos
@defunx sequence-position-item-count seqpos
@c MOD gauche.lazy
@c EN
Query positional information to a @code{<sequence-position>} instance
@var{seqpos}.
@c JP
@code{<sequence-position>}のインスタンス@var{seqpos}から情報を取り出します。
@c COMMON

@c EN
Returns the source name (usually the source file name),
the line count (starting from 1), the column count (starting from 1),
and the item count (number of characters, starting from 0).
@c JP
それぞれ、ソースの名前(通常はソースファイル名)、
行番号(1から)、カラム番号(1から)、アイテムカウント(読まれた文字数、0から)です。
@c COMMON

@c EN
The source name may be @code{#f} if it is not available.
@c JP
ソース名が不明な場合は@code{#f}になっています。
@c COMMON
@end defun

@defun port->char-lseq/position :optional port :key source-name start-line start-column start-item-count
@c MOD gauche.lazy
@c EN
Like @code{port->char-lseq}, returns a lazy sequence of characters read
from an input port @var{port}.  However, the sequence returned by this
procedure has positional info attached, and can be retrieved
by @code{lseq-position}.
@c JP
@code{port->char-lseq}と同じように、@var{port}から読まれる文字の遅延シーケンスを
返します。ただし、そのシーケンスには位置情報が付加されており、
@code{lseq-position}で取り出すことができます。
@c COMMON

@c EN
The @var{source-name}, @var{start-line}, @var{start-column} and
@var{start-item-count} initializes the positional info before
start reading characters.  The default values are
@code{(port-name port)}, 1, 1 and 0, respectively.
If you're reading from a freshly opened port, the default values suffice.
Specify these if you've already read some data from the port, for example.
@c JP
@var{source-name}、@var{start-line}、@var{start-column}、
@var{start-item-count}は最初の文字を読み出す前の位置情報の初期化に使われます。
デフォルトはそれぞれ、@code{(port-name port)}、1、1、0で、
オープンしたばかりのポートから読み出す場合はデフォルトが適切な値となっています。
既にポートからいくらか読み出してしまった場合などにこれらの値を指定してください。
@c COMMON
@end defun


@defun generator->lseq/position char-gen :key source-name start-line start-column start-item-count
@c MOD gauche.lazy
@c EN
Like @code{generator->lseq}, returns a lazy sequence of characters
generated by @var{char-gen}.  However, the sequence returned by this
procedure has positional info attached, and can be retrieved
by @code{lseq-position}.
@c JP
@code{generator->lseq}と同じように、ジェネレータ@var{char-gen}から生成される
文字からなる遅延シーケンスを返します。ただし、そのシーケンスには位置情報が付加されており、
@code{lseq-position}で取り出すことができます。
@c COMMON

@c EN
The @var{source-name}, @var{start-line}, @var{start-column} and
@var{start-item-count} initializes the positional info before
start reading characters.  The default values are
@code{#f}, 1, 1 and 0, respectively.
@c JP
@var{source-name}、@var{start-line}、@var{start-column}、
@var{start-item-count}は最初の文字を読み出す前の位置情報の初期化に使われます。
デフォルトはそれぞれ、@code{(port-name port)}、1、1、0です。
@c COMMON
@end defun

@defun lseq-position seq
@c MOD gauche.lazy
@c EN
If @var{seq} is a lazy sequence with positional info attached,
retrieve it and returns a @code{<sequence-position>} instance.
@c JP
@var{seq}が遅延シーケンスで位置情報が付加されている場合は、
その情報を@code{<sequence-position>}のインスタンスにして返します。
@c COMMON

@c EN
If @var{seq} doesn't have positional info, or not even a sequence,
@code{#f} is returned.
@c JP
@var{seq}に位置情報が付加されていない、あるいは遅延シーケンス以外のオブジェクトであった
場合は@code{#f}が返されます。
@c COMMON
@end defun


@c ----------------------------------------------------------------------
@node Listener, User-level logging, Lazy sequence utilities, Library modules - Gauche extensions
@section @code{gauche.listener} - Listener
@c NODE リスナー, @code{gauche.listener} - リスナー

@deftp {Module} gauche.listener
@mdindex gauche.listener
@c EN
This module provides a convenient way to enable multiple
read-eval-print loop (repl) concurrently.
@c JP
このモジュールは、
複数のread-eval-printループ(repl)を並行して動作させるのに便利な機能を提供します。
@c COMMON

@c EN
An obvious way to run multiple repls is to use threads;
creating as many threads as sessions and calling
@code{read-eval-print-loop} (@pxref{Eval and repl}) from each thread.
Nevertheless, sometimes single threaded implementation is preferred.
For instance, you're using a library which is not MT-safe,
or your application already uses select/poll-based dispatching mechanism.
@c JP
複数のreplを実現する自明な方法は、セッション毎にスレッドを生成して
各スレッド上で@code{read-eval-print-loop} (@ref{Eval and repl}参照)を
呼ぶことですが、シングルスレッドでの実装が好ましい場合もあります。
例えばアプリケーションがMT-safeでないライブラリに大きく依存していたり、
既にアプリケーションがselectやpollをベースにしたディスパッチメカニズムを
持っているような場合です。
@c COMMON

@c EN
To implement repl in the single-threaded selection-base application,
usually you register a handler that is called when data is available
in the listening port.  The handler reads the data and add them into
a buffer.  Then it examines if the data in the buffer consists a
complete expression, and if so, it reads the expression from the
buffer, evaluates it, then prints the result to the reporting port.
The @code{<listener>} class in this module provides this handler mechanism,
so all you need to do is to register the handler to your dispatching
mechanism.
@c JP
シングルスレッドのselectionベースのアプリケーションでreplを実装するには、
通常、listenしているポートにデータが到着した時に呼ばれるハンドラを登録します。
ハンドラはポートからデータを読み、内部バッファに追加します。
そして内部バッファをスキャンし、データが完全な式を構成した場合は
それをS式として読みだし、評価して結果をポートに流します。
このモジュールの@code{<listener>}クラスはこのハンドラのメカニズムを提供するので、
アプリケーション側はそれを自分のディスパッチメカニズムに登録するだけで済みます。
@c COMMON

@c EN
Note: it may also be desirable to buffer the output sometimes,
but the current version doesn't implement it.
@c JP
註：場合によっては、出力もバッファリングする必要があるかもしれませんが、
現在はそれは実装されていません。
@c COMMON
@end deftp

@subheading Listener API

@deftp {Class} <listener>
@clindex listener
@c MOD gauche.listener
@c EN
An object that maintains the state of a repl session.
It has many external slots to customize its behavior.
Those slot values can be set at construction time
by using the keyword of the same name as the slot,
or can be set by @code{slot-set!} afterwards.  However,
most of them should be set before calling
@code{listener-read-handler}.
@c JP
Replセッションの状態を維持するオブジェクトです。
オブジェクトのふるまいをカスタマイズするためにいくつもの外部スロットがあります。
これらのスロットの値は、スロットの名前と同名のキーワード引数を用いて
オブジェクトの構築時に指定することもできますし、オブジェクト構築後に
@code{slot-set!}で設定することもできますが、@code{listener-read-handler}
を呼ぶ前に確定していなければなりません。
@c COMMON

@defivar <listener> input-port
@c EN
Specifies the input port from which the listener get the input.
The default value is the current input port when the object is
constructed.
@c JP
リスナーが入力を受けとる入力ポートを指定します。デフォルト値は、
オブジェクトが構築された時のカレント入力ポートです。
@c COMMON
@end defivar

@defivar <listener> output-port
@c EN
Specifies the output port to which the listener output will go.
The default value is the current output port when the object is
constructed.
@c JP
リスナーが出力をおこなう出力ポートを指定します。デフォルト値は、
オブジェクトが構築された時のカレント出力ポートです。
@c COMMON
@end defivar

@defivar <listener> error-port
@c EN
Specifies the output port to which the listener's error messages will go.
The default value is the current error port when the object is
constructed.
@c JP
リスナーのエラーメッセージを出力するポートを指定します。デフォルト値は、
オブジェクトが構築された時のカレントエラー出力ポートです。
@c COMMON
@end defivar

@defivar <listener> reader
@c EN
A procedure with no arguments.  It should read a Scheme expression
from the current input port when called.
The default value is system's @code{read} procedure.
@c JP
引数を取らない手続きです。呼び出し時のカレント入力ポートからScheme式を
読み込まなければなりません。デフォルト値はシステムの@code{read}手続きです。
@c COMMON
@end defivar

@defivar <listener> evaluator
@c EN
A procedure that takes two arguments, a Scheme expression and
an environment specifier.  It should evaluate the expression in
the given environment and returns zero or more value(s).
The default value is system's @code{eval} procedure.
@c JP
Scheme式と環境指定子のふたつの引数をとる手続きです。
式を与えられた環境で評価し、0個以上の値を返さなければなりません。
デフォルト値はシステムの@code{eval}手続きです。
@c COMMON
@end defivar

@defivar <listener> printer
@c EN
A procedure that takes zero or more argument(s) and prints them
out to the current output port.  The default value is a procedure
that prints each value by @code{write}, followed by a newline.
@c JP
0以上の引数をとり、カレント出力ポートに印字する手続きです。
デフォルト値は、各値を@code{write}で印字したのち、改行する手続きです。
@c COMMON
@end defivar

@defivar <listener> prompter
@c EN
A procedure with no arguments.  It should prints a prompt
to the current output port.  The output is flushed by the listener
object so this procedure doesn't need to care about it.
The default procedure prints @code{"listener> "}.
@c JP
引数をとらない手続きです。カレント出力ポートにプロンプトを
印字しなければなりません。リスナーは、この手続きが面倒を見なくてよいように、
出力をフラッシュします。
デフォルトの手続きは @code{"listener> "} を印字します。
@c COMMON
@end defivar

@defivar <listener> environment
@c EN
An environment specifier where the expressions will be
evaluated.  The default value is the value returned by
@code{(interaction-environment)}.
@c JP
式を評価する環境指定子です。デフォルト値は@code{(interaction-environment)}が
返す値です。
@c COMMON
@end defivar

@defivar <listener> finalizer
@c EN
A thunk that will be called when EOF is read from @code{input-port}.
During the execution of @var{finalizer}, the current input, output
and error ports are restored to the ones when
@code{listener-read-handler} is called.

It can be @code{#f} if no such procedure is needed.
The default value is @code{#f}.
@c JP
@code{input-port}からEOFが読み込まれたときに呼び出されるサンクです。
@var{finalizer}実行中は、現在の入力、出力、エラー出力ポートは、
@code{listener-read-handler}が呼ばれたときのものに戻っています。

このような手続きが必要ない場合は@code{#f}にしておいて構いません。
デフォルトの値は@code{#f}です。
@c COMMON
@end defivar

@defivar <listener> error-handler
@c EN
A procedure that takes one argument, an error exception.  It is
called when an error occurs during read-eval-print stage,
with the same dynamic environment as the error is signaled.
The default value is a procedure that simply prints the
error exception by @code{report-error}.
@c JP
エラー例外をひとつ引数としてとる手続きです。read-eval-printの最中に
エラーが発生すると、エラーシグナルが発生すのと同じ動的環境で、
呼び出されます。
デフォルト値はエラー例外を@code{report-error}を使って印字する手続きです。
@c COMMON
@end defivar

@defivar <listener> fatal-handler
@c EN
A procedure that takes one argument, an error exception.
It is called when a @emph{fatal} error occurred (see below
for the precise definition).  If this handler is
called, you should assume you can no longer continue the listener
session safely, even write messages to the client.  This handler
is to log such condition or to clean up the listener.
During the execution of @var{fatal-handler}, the current input, output
and error ports are restored to the ones when
@code{listener-read-handler} is called.
@c JP
エラー例外をひとつの引数としてとる手続です。
@emph{fatal}エラー(詳しい定義については後述)が発生したときに呼び出され
ます。このハンドラが呼び出された場合、リスナーセッションは安全に続ける
ことはできないと思ってください。クライアントへのメッセージを書くこと
もできません。このハンドラはこういう状況でログを残したりリスナーの
クリーンアップするためのものです。@var{fatal-handler}を実行中は現在の
入力、出力、エラー出力は@code{listener-read-handler}が呼ばれたときのも
のに戻ります。
@c COMMON

@c EN
If @var{fatal-handler} returns @code{#f}, @var{finalizer} is
called afterwards.  With this, you can implement a common
cleanup work in @var{finalizer}.  If @var{fatal-handler} returns
a true value, @var{finalizer} will not be called.
@c JP
@var{fatal-handler}が@code{#f}を返す場合、@var{finalizer}は後で呼ばれ
ます。これを利用して@var{finalizer}で共通のクリーンアップを実行するよ
うな実装ができます。@var{fatal-handler}が真の値を返した場合には、
@var{finalizer}は呼ばれません。
@c COMMON

@end defivar

@end deftp


@deffn {Method} listener-read-handler (listener <listener>)
@c MOD gauche.listener
@c EN
Returns a thunk that is to be called when a data is available
from @code{input-port} of the listener.

The returned thunk (read handler) does the following steps.
Note that the first prompt is @emph{not} printed by this
procedure.  See @code{listener-show-prompt} below.
@enumerate
@item
Reads available data from @code{input-port} and appends it to the
listener's internal buffer.
@item
Scans the buffer to see if it has a complete S-expression.
If not, returns.
@item
Reads the S-expression from the buffer.
The read data is removed from the buffer.
@item
Evaluates the S-expression, then prints the result to
@code{output-port}.
@item
Prints the prompt by prompter procedure to @code{output-port},
then flush @code{output-port}.
@item
Repeats from 2.
@end enumerate
@c JP
リスナーの@code{input-port}から読み込んだデータが正しい時に
呼ばれるサンクを返します。

返されたサンク(readハンドラ)は、以下のように実行されます。
この手続きは最初のプロンプトを印字@emph{しない}ことに
注意してください。これについては後述の@code{listener-show-prompt}を
参照してください。
@enumerate
@item
@code{input-port}にあるデータを読み、これをリスナーの内部バッファに
連結する。
@item
バッファをスキャンして、それが完結したS式であるかを確かめ、
完結していなければ、リターンする。
@item
バッファからそのS式を読み込み、そのバッファからは
そのデータを除去する。
@item
そのS式を評価して、結果を@code{output-port}へ印字する。
@code{output-port}.
@item
プロンプタ手続きを使って、プロンプトを@code{output-port}に印字したのち、
@code{output-port}をフラッシュする。
@item
2から繰り返す。
@end enumerate
@c COMMON
@end deffn

@deffn {Method} listener-show-prompt (listener <listener>)
@c MOD gauche.listener
@c EN
Shows a prompt to the listener's output port, by using
listener's prompter procedure.  Usually you want to use
this procedure to print the first prompt, for instance,
when the client is connected to the listener socket.
@c JP
リスナーの出力ポートにプロンプトを表示します。表示にはリスナーの
プロンプタ手続きを使います。通常この手続きは最初のプロンプトを
印字するために使います。たとえば、クライアントがリスナーソケットに
接続してきたときです。
@c COMMON
@end deffn

@defun complete-sexp? str
@c MOD gauche.listener
@c EN
Returns @code{#t} if @var{str} contains a complete S-expression.
This utility procedure is exported as well, since it might be useful
for other purposes.

Note that this procedure only checks syntax of the expressions,
and doesn't rule out erroneous expressions (such as containing
invalid character name, unregistered SRFI-10 tag, etc.).
This procedure may raise an error if the input contains
'@code{#<}' character sequence.
@c JP
もし、@var{str}が完結したＳ式を含んでいれば@code{#t}を返します。
このユーティリティ手続きは、他の目的にも有用なので、
他の手続きといっしょにエクスポートしてあります。

この手続きは構文のチェックをするだけで、(不正な文字名を含んだり、
登録されていないSRFI-10のタグを含むなど)誤りのある式を判別するわけでは
ないことに注意してください。この手続きは入力が'@code{#<}'文字の
シーケンスを含むと、エラーを発生させます。
@c COMMON
@end defun

@c EN
@subheading Error handling
@c JP
@subheading エラー処理
@c COMMON

@c EN
There are a few error situations the listener handles differently.
@c JP
エラー状況によりリスナーのエラー処理法が異ります。
@c COMMON

@itemize @bullet
@item
@c EN
@emph{Fatal error} - An error situation that the listener session
can no longer go on safely.  You cannot even tell so to the
listener client, since the connection to the client may be broken.
All you can do is to clean up the listener session (e.g. removes
the handler).   This case happens in (1) a low-level system error
occurs during reading from @var{input-port}. (A syntax error
of the input isn't count as fatal, and handled as REPL error described
below.), (2) a @code{SIGPIPE} signal is raised during writing to
@var{output-port}, or (3) an unhandled error occurred during executing
@var{error-handler}.
@c JP
@emph{致命的エラー} - もはやリスナーセッションを安全に続けることが不可
能なエラー状況です。リスナーのクライアントとの接続が切れてしまうこと
になるので、状況を知らせることもできません。できることはリスナーセッショ
ンをクリーンアップする(たとえばハンドラを削除する)ことだけです。このエ
ラーは以下の場合に発生します。(1) @var{input-port}からの読み込み中に低
レベルのシステムエラーが発生した場合。(入力の構文エラーは致命的エラー
とはみなさず、後述のREPLエラーとして処理されます。) (2)
@var{output-port} へ書き出し中に @code{SIGPIPE} シグナルがあがった場合
(3) @var{error-handler} を実行中に処理未設定エラーが発生した場合。
@c COMMON

@c EN
When this situation happens, the @var{fatal-handler} is called
if it is given.  If @var{fatal-handler} returns @code{#f}, or
@var{fatal-handler} isn't given, @var{finalizer} is also called.
@c JP
このような状況が起こると、@var{fatal-handler}が与えられていればそれが
呼ばれます。@var{fatal-handler}が@code{#f}を返すか、
@var{fatal-handler}が与えられていなければ、@var{finalizer}が呼ばれます。
@c COMMON

@item
@c EN
@emph{Leaked error} - If an error occurs during executing
@var{fatal-handler} or @var{finalizer}, we don't have no more
safety net.  The error is 'leaked' outside the listener handler,
and should be handled by the user of @code{gauche.listener}.
@c JP
@emph{リークエラー} - @var{fatal-handler}あるいは@var{finalizer}を実行
中にエラーが起こるともはやセーフティネットはありません。このエラーはリ
スナーハンドラの外に漏れだしますので、@code{gauche.listener}のユーザが
自ら処理しなければなりません。
@c COMMON

@c EN
Generally this situation should be considered as a bug of
the program; you should make sure to catch foreseeable errors within
@var{fatal-handler} and @var{finalizer}.
@c JP
一般的にはこのような状況はプログラムのバグだと考えるべきです。したがっ
て、想定されたエラーとして@var{fatal-handler}および@var{finalizer}内で
捕捉されるべきです。
@c COMMON

@item
@c EN
@emph{REPL error} - Other errors are handled by @var{error-handler}.
@c JP
@emph{REPLエラー} - @var{error-handler}で処理されるその他のエラー
@c COMMON
@end itemize

@c EN
@subheading Listener example
@c JP
@subheading リスナーの例
@c COMMON

@c EN
The following code snippet opens a server socket, and opens
a Scheme interactive session when a client is connected.
(Note: this code is just for demonstration.  Do not run
this program on the machine accessible from outside network!)
@c JP
以下のコード断片は、サーバソケットをオープンし、クライアントが
接続してきたときにSchemeの対話的セッションをオープンするというものです。
(註: このコードはdemo用のコードです。決して、外のネットワークから
アクセス可能なマシン上で走らせてはいけません！)
@c COMMON

@example
(use gauche.net)
(use gauche.selector)
(use gauche.listener)

(define (scheme-server port)
  (let ((selector (make <selector>))
        (server   (make-server-socket 'inet port :reuse-addr? #t))
        (cid      0))

    (define (accept-handler sock flag)
      (let* ((client (socket-accept server))
             (id     cid)
             (input  (socket-input-port client :buffering :none))
             (output (socket-output-port client))
             (finalize (lambda ()
                         (selector-delete! selector input #f #f)
                         (socket-close client)
                         (format #t "client #~a disconnected\n" id)))
             (listener (make <listener>
                         :input-port input
                         :output-port output
                         :error-port output
                         :prompter (lambda () (format #t "client[~a]> " id))
                         :finalizer finalize))
             (handler (listener-read-handler listener))
             )
        (format #t "client #~a from ~a\n" cid (socket-address client))
        (inc! cid)
        (listener-show-prompt listener)
        (selector-add! selector input (lambda _ (handler)) '(r))))

    (selector-add! selector
                   (socket-fd server)
                   accept-handler
                   '(r))
    (format #t "scheme server started on port ~s\n" port)
    (do () (#f) (selector-select selector))))
@end example

@c ----------------------------------------------------------------------
@node User-level logging, Instance pools, Listener, Library modules - Gauche extensions
@section @code{gauche.logger} - User-level logging
@c NODE ユーザレベルのロギング, @code{gauche.logger} - ユーザレベルのロギング

@deftp {Module} gauche.logger
@mdindex gauche.logger
@c EN
Provides a simple interface to log the program's activity.
The information can be written to the specified file,
or to the system logger using @code{syslog(3)}.
When a file is used, syslog-like prefix string is added
to each message, which is configurable.  It can also takes care of
locking of the file (see the description of @code{lock-policy} below).
@c JP
プログラムからログを書き出す簡単なインタフェースを提供します。
情報は指定されたファイルへ書き出されるか、もしくは@code{syslog(3)}を
使ってシステムログへと送られます。
ファイルに書き出される場合は、
syslogに似たプレフィクスが各メッセージの前に追加されます。
プレフィクスはカスタマイズすることもできます。
また、ログファイルの排他制御も行われます (下の@code{lock-policy}の説明を
参照して下さい)。
@c COMMON
@end deftp

@deftp {Class} <log-drain>
@clindex log-drain
@c MOD gauche.logger
@c EN
Represents the destination of log messages.
There's one implicit global @code{<log-drain>} instance, which is
used by default.  However, you can create as many instances
by @code{make} method as you want, in case if you want to log
to more than one destination.
@c JP
ログメッセージの行き先を表現するオブジェクトです。
デフォルトのログの行き先として、グローバルな@code{<log-drain>}のインスタンスが
ひとつ作られます。
ログをいくつかにわけて出力する場合などは@code{make}メソッドを使って
いくつでも@code{<log-drain>}のインスタンスを作ることができます。
@c COMMON

@defivar {<log-drain>} path
@c EN
Designates destination of log output.  It can be one of the following
values.

@table @asis
@item @r{string}
Pathname of the log file.  The output is written to it.
@item @code{current-error}
@itemx @code{#t}
The output goes to the current error port.
@item @code{current-output}
The output goes to the current output port.
@item @code{syslog}
The output is sent to the system logger.
@item @code{ignore}
Make @code{log-format} does nothing.
@item @code{#f}
The output is turned to a string and returned from
@code{log-format}.
@end table

By default, this slot is @code{#f}.
@c JP
ログの出力先を指定します。以下の値をとることができます。

@table @asis
@item @r{文字列}
ログファイルのパスを指定します。出力はそのファイルへと書き出されます。
@item @code{current-error}
@itemx @code{#t}
出力は現在のエラーポートに向かいます。
@item @code{current-output}
出力は現在の出力ポートに向かいます。
@item @code{syslog}
出力はシステムログへと送られます。
@item @code{ignore}
@code{log-format}が何もしないようにします。
@item @code{#f}
出力は文字列になって@code{log-format}からの戻り値となります。
@end table

このスロットの初期値は@code{#f}です。
@c COMMON
@end defivar

@defivar {<log-drain>} prefix
@c EN
Specifies the prefix string that is attached to the beginning of every
message.  If the message spans to several lines, the prefix is
attached to each line.   The value of this slot can also be a procedure
that takes @code{<log-drain>} object and returns a string to be used as
the prefix.  The procedure is called every time prefix is needed.
@c JP
各メッセージの前に追加されるプレフィクス文字列を指定します。
メッセージが複数行に渡る場合、プレフィクスは各行の頭に追加されます。
またこのスロットには手続きをセットすることもできます。
その場合、プレフィクス文字列が必要とされる度にその手続きが@code{<log-drain>}
を引数として呼び出され、戻り値の文字列がプレフィクスとして使われます。
@c COMMON

@c EN
When the @code{path} slot is a symbol @code{syslog}, the value of this slot
is ignored.  System logger will attach an appropriate prefix.
@c JP
@code{path}スロットの値がシンボル@code{syslog}の場合は、
このスロットの値は無視されます。システムのログ機構が適切なプレフィクスを付けるからです。
@c COMMON

@c EN
When the value of the prefix slot is a string, the following character sequences
have special meanings and replaced by @code{log-format} for appropriate
information when written out.
@c JP
prefixスロットの値が文字列の場合、以下に挙げる文字シーケンスは特別な意味を持ち、
@code{log-format}によって置換されます。
@c COMMON

@table @code
@item ~T
@c EN
Current time, in the format of "Mmm DD hh:mm:ss" where "Mmm" is
an abbreviated month, "DD" is the day of month, "hh", "mm" and
"ss" are hours (in 24 hour basis), minutes and seconds, respectively.
This format is compatible with system logs.
@c JP
現在の時刻を"Mmm DD hh:mm:ss"という形式で表したもの。
ここで"Mmm" は英語の月名の省略形、"DD" は日、"hh"、"mm"、
"ss" は時間(24時間制)、分、秒です。
このフォーマットはシステムログと同じです。
@c COMMON

@item ~Y
@c EN
Current 4-digit year.
@c JP
4桁で表した現在の西暦。
@c COMMON

@item ~P
@c EN
The program name.  The default value is the basename of
@code{(car (command-line))} (@pxref{Command-line arguments}),
but you can change it by the @code{program-name}
slot described below.
@c JP
プログラム名。初期値は@code{(car (command-line))}の値のbasenameが使われます
(@ref{Command-line arguments}参照)。
下に述べる@code{program-name}スロットの値を変えれば
ここに現れる文字列を変えることができます。
@c COMMON

@item ~$
@c EN
The process id of this program.
@c JP
このプログラムのプロセスID。
@c COMMON

@item ~U
@c EN
The name of the effective user of the process.
@c JP
このプロセスの実行ユーザ名。
@c COMMON

@item ~H
@c EN
The hostname the process is running.
@c JP
このプロセスが走っているホスト名。
@c COMMON
@end table

@c EN
The default value of this slot is "@code{~T ~P[~$]: }".  For example,
if a string "this is a log message.\nline 2\nline 3" is given as the
message, it produces something like the following log entry.
@c JP
このスロットの初期値は"@code{~T ~P[~$]: }"です。例えば
"this is a log message.\nline 2\nline 3"というメッセージが
与えられると、次のようなログが書き出されます。
@c COMMON

@example
Sep  1 17:30:23 myprogram[441]: this is a log message
Sep  1 17:30:23 myprogram[441]: line 2
Sep  1 17:30:23 myprogram[441]: line 3
@end example

@end defivar

@defivar {<log-drain>} program-name
@c EN
Specifies the program name written by @code{~P} directive of
the prefix slot.
@c JP
プレフィクス文字列の@code{~P}が置換されるプログラム名を指定します。
@c COMMON
@end defivar

@defivar {<log-drain>} lock-policy
@c EN
Specifies the way the log file should be locked.
If the value of this slot is a symbol @code{fcntl},
the log file is locked using
fcntl() (@pxref{Low-level file operations}).
If the value is a symbol @code{file}, the log file is locked by
creating auxiliary lock file, whose name is generated by appending ".lock"
after the log file path.  The logging
process needs a write permission to the log file directory.
Note that if the process is killed forcibly during writing the
log file, a stale lock file may remain.  @code{Log-format}
silently removes the lock file if it is unusually old (currently 10 minutes).
If the value is @code{#f}, no locking is performed.

The default value is @code{fcntl}, except MacOSX which doesn't
support fcntl()-style locking and thus @code{file} is default.

The locking isn't performed if the destination is not a file.
@c JP
ログファイルのロックの方法を指定します。
このスロットの値がシンボル@code{fcntl}だった場合は、
fcntl()によるファイルロックが使われます
(@ref{Low-level file operations}参照)。
このスロットの値がシンボル@code{file}だった場合は、
ログファイルのパス名に ".lock" を追加したロックファイルを作成することによる
排他制御が行われます。この場合、ログを行うプロセスはログファイルの
置かれるディレクトリに書き込み権限が必要です。
また、プロセスがログファイル書き込み中に強制的に終了させられた場合、
ロックファイルが残ってしまう恐れがあります。
@code{Log-format}はロックファイルが十分に古い場合(現在は10分をリミットとしています)
ロックファイルを自動的に削除します。
このスロットの値が@code{#f}だった場合は、排他制御は行われません。

デフォルトの値は@code{fcntl}です。但しMacOSXではfcntlスタイルのロックが
サポートされていないため、@code{file}がデフォルト値となります。

ログの行き先がファイルでない場合は排他制御は行われません。
@c COMMON
@end defivar

@defivar {<log-drain>} syslog-option
@defivarx {<log-drain>} syslog-facility
@defivarx {<log-drain>} syslog-priority
@c EN
The value of these slots are used when the destination of the drain
is the system logger.   @xref{Syslog}, for the detailed information
about these values.  The default values of these slots
are @code{LOG_PID}, @code{LOG_USER} and @code{LOG_INFO}, respectively.
@c JP
これらのスロットの値は、ログの行き先がシステムログの場合にのみ使われます。
これらの値に関する説明は@ref{Syslog}を参照して下さい。
デフォルトの値はそれぞれ@code{LOG_PID}、@code{LOG_USER}、@code{LOG_INFO}です。
@c COMMON
@end defivar
@end deftp


@defun log-open path :key prefix program-name
@c MOD gauche.logger
@c EN
Sets the destination of the default log message to the path @var{path}.
It can be a string or a boolean, as described above.
You can also set prefix and program name by corresponding keyword
arguments.  See the @code{<log-drain>} above for those parameters.
@c JP
デフォルトのログの行き先を@var{path}に指定します。
@var{path}は文字列かboolean値あるいはシンボル@code{syslog}で、
上の@code{path}スロットで述べたものと
おなじ意味を持ちます。またプレフィクスとプログラム名をキーワード引数で
指定することもできます。
これらのパラメータの意味については上の@code{<log-drain>}の項を参照して下さい。
@c COMMON

@c EN
Despite its name, this function doesn't open the specified file
immediately.  The file is opened and closed every time @code{log-format}
is called.
@c JP
名前に"open"とありますが、この手続きは指定されたファイルをオープンしません。
ファイルは@code{log-format}が呼ばれるたびにオープンされクローズされます。
@c COMMON
@end defun

@deffn {Parameter} log-default-drain
@c MOD gauche.logger
@c EN
When called with no argument, returns the current default log-drain
@code{log-format} uses when the explicit drain is omitted.
It may return @code{#f} if the default log drain hasn't been
opened by @code{log-open}.

Calling with new @code{<log-drain>} object or
@code{#f} alters the default log-drain.
You can also use @code{parameterize} (@ref{Parameters}) to change
the log drain temporary.
@c JP
引数無しで呼ばれると、@code{log-format}が使う、
現在のデフォルトのログの行き先が返されます。
まだデフォルトのログの行き先が@code{log-open}で指定されていない場合は
@code{#f}が返ります。

新たな@code{<log-drain>}オブジェクトか@code{#f}を引数にして呼び出すと、
デフォルトのログの行き先がそれに変更されます。
@code{parameterize} (@ref{Parameters}) を使えば、一時的にデフォルトの
ログの行き先を変更できます。
@c COMMON
@end deffn


@deffn {Method} log-format (format <string>) arg @dots{}
@deffnx {Method} log-format (drain <log-drain>) (format <string>) arg @dots{}
@c MOD gauche.logger
@c EN
Formats a log message by @var{format} and @var{arg @dots{}}, by using
@code{format} (@pxref{Output}).    In the first form, the output goes
to the default destination.  In the second form, the output goes to
the specified drain.
@c JP
ログメッセージを@code{format}手続きでフォーマットし(@ref{Output}参照)、
指定された行き先に書き出します。最初の形式ではデフォルトの行き先が使われます。
@c COMMON

@c EN
The file is opened and closed every time.  You can safely move
the log file while your program that touches the log file is running.
Also @code{log-format} acquires a write lock of the log file by
@code{sys-fcntl} (@pxref{Low-level file operations}).
@c JP
ファイルはこの手続きが呼ばれるたびにオープンされクローズされます。
したがって、ログファイルに書き出すプログラムが走っている最中でも
ログファイルをmoveすることができます。
また、@code{log-format}は@code{sys-fcntl} (@ref{Low-level file operations}参照)
を使ってファイルロックを獲得します。
@c COMMON

@c EN
If the first form of @code{log-format} is called before @code{log-open}
is called, @code{log-format} does nothing.
It is useful to embed debug stubs in your code; once your code is
past the debugging stage, you just comment out @code{log-open} and
the code runs without logging.
@c JP
@code{log-open}が呼ばれる前に@code{log-format}が最初の形式で呼ばれた場合、
@code{log-format}は何もしません。したがって、@code{log-format}をデバッグに
活用し、必要なくなったら@code{log-open}だけをコメントアウトする、というような
使用法も可能です。
@c COMMON
@end deffn

@defun log-display obj :optional drain
@defunx log-write obj :optional drain
@c MOD gauche.logger
@c EN
Convenience procedures.
Work as @code{(log-format drain "~a" obj)} and
@code{log-format drain "~s" obj)}, respectively.
Note the order of the arguments; these are alined with @code{display} and
@code{write}.
@c JP
便利関数です。それぞれ@code{(log-format drain "~a" obj)}、
@code{log-format drain "~s" obj)}のように動作します。
引数順に注意。これらの手続きは@code{display}と@code{write}に合わせてあります。
@c COMMON
@end defun

@deffn {Method} log-from-input-port (port <port>) :key formatter
@deffnx {Method} log-from-input-port (drain <log-drain>) (port <port>) :key formatter
@c MOD gauche.logger
@c EN
Starts a thread that keeps reading from the input port @var{port},
line by line, and logs each line using @var{formatter}.
It is handy to log data fed asynchronously via a pipe.

The @var{formatter} procedure is called as @code{(formatter line drain)},
where @var{line} is a string (without a newline), and @var{drain} is
@code{<log-drain>}.  The default formatter is @code{log-display}.

The created thread is returned.  It terminates when @var{port} reaches EOF.

In the first form, the value of @code{(log-default-drain)}
@emph{when this procedure is called} is used as the log drain.  Changing
the value of @code{(log-default-drain)} afterwards won't affect
the destination of the log.

If an error occurs in the thread, it is captured and a warning is issued
to the current error port at the time of calling @code{log-from-input-port},
using @code{warn} (@pxref{Warnings}).
If the error is low-level I/O error from the @var{port}, the port
is closed and the thread terminates.  Otherwise, the thread resumes
monitoring the input and logging.

Note: To wait all the data from the port to be logged, you have to
call @code{thread-join!} on the returned thread.
@c JP
入力ポート@var{port}から1行づつ読み込み、
それを@var{formatter}を使ってログ出力するスレッドを開始します。
パイプから非同期に送られてくるデータをログするのに便利です。

@var{formatter}は入力行(改行文字は含まない)@var{line}とログドレイン@var{drain}
を引数として@code{(formatter line drain)}のように呼ばれます。
@var{formatter}のデフォルトは@code{log-display}です。

戻り値は作られたスレッドです。スレッドは@var{port}がEOFに達したら終了します。

最初の形式では、ログの行き先として@emph{この手続きが呼ばれた時点}での
@code{(log-default-drain)}の値が使われます。
この手続きを呼んだ後で@code{(log-default-drain)}を変えてもログの行き先に影響はありません。

スレッド内でエラーが起きた場合、それは捕捉され、警告が@code{warn}を使って
@code{log-from-input-port}が呼ばれた時点での@code{current-error-port}に
出力されます (@pxref{Warnings})。その後、もしエラーが@var{port}の
低レベルI/Oに起因するものなら、@var{port}がクローズされスレッドは終了します。
そうでなければ、また@var{port}を読んでログするループに戻ります。

註: ポートからの全てのデータがログされるまで待つには、返されたスレッド
を@code{thread-join!}で待つ必要があります。
@c COMMON
@end deffn

@c ----------------------------------------------------------------------
@node Instance pools, Propagating slot access, User-level logging, Library modules - Gauche extensions
@section @code{gauche.mop.instance-pool} - Instance pools
@c NODE インスタンスプール, @code{gauche.mop.instance-pool} - インスタンスプール

@deftp {Module} gauche.mop.instance-pool
@mdindex gauche.mop.instance-pool
@c EN
Sometimes, you want to track all instances created from a class.
This module provies tools to do that.
@c JP
しばしば、あるクラスから作られた全てのインスタンスを
追跡したいことがあります。このモジュールはそのための道具を提供します。
@c COMMON

@c EN
An @emph{instance pool} class is a class that keeps the list of instances
of itself and its subclasses.
@c JP
@emph{インスタンスプール}クラスは、
それ自身、及びそのサブクラスのインスタンスのリストを保持するクラスです。
@c COMMON

@c EN
A class that inherits @code{<instance-pool-mixin>} directly becomes a 'root'
class of the pool.  Instances of the subclass of the root class will
be added to the pool.
@c JP
@code{<instance-pool-mixin>}を直接継承したクラスが
インスタンスプールの「根」になります。
そのクラス及び全てのサブクラスのインスタンスがそのプールに加えられます。
@c COMMON

@c EN
An application can have multiple root classes.  If a class inherits
from two or more pooled classes, its instances will be added to
all the pools.
@c JP
アプリケーションは複数の根となるクラスを持てます。
複数のインスタンスプールクラスを継承した場合、そのインスタンスは
両方のインスタンスプールに加えられます。
@c COMMON

@c EN
The actual implementation of how to manage pools can be customizable
by subclassing @code{<instance-pool-meta>} and overloading methods.
@c JP
実際にどのようにプールが管理されるかは、
@code{<instance-pool-meta>}メタクラスを継承して
メソッドをオーバーロードすることでカスタマイズできます。
@c COMMON

@c EN
Note that instance pools are global---it keeps all the instances
ever created, unless explicitly cleared.
@c JP
インスタンスプールはグローバルであることに注意してください。
明示的にクリアされない限り、作られた全てのインスタンスが保持されます。
@c COMMON
@end deftp

@deftp {Class} <instance-pool-meta>
@clindex instance-pool-meta
@c MOD gauche.mop.instance-pool
@c EN
A metaclass that adds a class the capability of tracking its instances.
By default, instance of itself and its subclasses are tracked.
@c JP
クラスにインスタンスを追跡する機能を付け加えるメタクラスです。
デフォルトでは、このメタクラスから作られるクラス、及びその全ての
サブクラスのインスタンスが追跡されます。
@c COMMON
@end deftp

@deftp {Class} <instance-pool-mixin>
@clindex instance-pool-mixin
@c MOD gauche.mop.instance-pool
@c EN
A mixin class that makes the class that directly inherits this mixin
an instance of @code{<instnace-pool-meta>}.  You can use this mixin
class, instead of using metaclass explicitly, to make a class
a root of the pool.
@c JP
このミックスインクラスを直接継承するクラスは@code{<instnace-pool-meta>}の
インスタンスになります。メタクラスを直接指定するかわりに、
このミックスインクラスを継承することで、
プールの「根」にすることができます。
@c COMMON
@end deftp

@deffn {Generic Function} instance-pool->list class
@c MOD gauche.mop.instance-pool
@c EN
Returns a list of instances in the pool of @var{class},
which should be an instance
of @code{<instance-pool-meta>}.
The list is fresly constructuted every time it is called.
The order of instances are not specified.
@c JP
@var{class}は@code{<instance-pool-meta>}メタクラスのインスタンスで
なければなりません。このジェネリックファンクションは
@var{class}の持つインスタンスプール中のインスタンスのリストを
返します。
返されるリストは毎回新たに作られます。
インスタンスの順序は不定です。
@c COMMON
@end deffn

@deffn {Generic Function} instance-pool-find class pred
@c MOD gauche.mop.instance-pool
@c EN
Returns an instance in the pool of @var{class} which
satisfies the predicate @var{pred}.
If no instance satisfies it, @code{#f} is returned.
@c JP
@var{class}のプール中のインスタンスのうち、
述語@var{pred}を満たすものをひとつ探して返します。
見つからなければ@code{#f}が返ります。
@c COMMON
@end deffn

@deffn {Generic Function} instance-pool-remove! class pred
@c MOD gauche.mop.instance-pool
@c EN
Remove all instances that satisfies the predicate @var{pred}
from the pool of @var{class}.
@c JP
@var{class}のプールから、述語@var{pred}を満たすインスタンスを
全て取り除きます。
@c COMMON
@end deffn

@deffn {Generic Function} instance-pool-fold class kons knil
@c MOD gauche.mop.instance-pool
@c EN
Calls @var{kons} over every instance in the pool of @var{class},
with the current accumulated value.  The initial value is @var{knil},
and each return value of @var{kons} is used as the next value.
The last return value of @var{kons} is returned from the function.

It is functionally equivalent with the following, except that it may
be more efficient (without creating intermediate list).  Also, the
order of instances are not guaranteed to be the same as
@code{instance-pool->list} returns.
@c JP
@var{class}のプール中の全てのインスタンスに対して、
@var{kons}を、そのインスタンスと蓄積された値を引数として呼びます。
最初の蓄積された値は@var{knil}で、各@var{kons}の戻り値が
新たな蓄積された値として次の@var{kons}の呼び出しに渡されます。

これは次のコードと機能的に同じですが、
中間のリストを作らない分効率が良いかもしれません。
また、@code{instance-pool->list}と同じように、インスタンスの順序は不定です。
@c COMMON
@example
(fold kons knil (instance-pool->list class))
@end example
@end deffn

@deffn {Generic Function} instance-pool-map class proc
@deffnx {Generic Function} instance-pool-for-each class proc
@c MOD gauche.mop.instance-pool
@c EN
Apply @var{proc} on each instances in the pool of @var{class};
@code{instance-pool-map} gathers the results into a list and returns it,
while @code{instance-pool-for-each} discards the result of @var{proc}.

The order in which instances are visited is not specified.
@c JP
@var{proc}を@var{class}のプールの各インスタンスに対して呼びます。
@code{instance-pool-map}は呼び出しの結果をリストにして返します。
@code{instance-pool-for-each}は@var{proc}の結果は捨てられます。

インスタンスがどういう順番で処理されるかは不定です。
@c COMMON
@end deffn

@c ----------------------------------------------------------------------
@node Propagating slot access, Singleton, Instance pools, Library modules - Gauche extensions
@section @code{gauche.mop.propagate} - Propagating slot access
@c NODE スロットアクセスの伝播, @code{gauche.mop.propagate} - スロットアクセスの伝播

@deftp {Module} gauche.mop.propagate
@mdindex gauche.mop.propagate
@c EN
Provides a metaclass to add @code{:propagated} slot allocation option.

When a slot allocation has @code{:propagated}, access
to the slot is redirected to other object's slot.
It is handy for composite objects to keep external
interface simple, for access to the slot of inner objects
can be disguised as if it is a slot of the parent object.
@c JP
スロットの@code{:allocation}オプションに@code{:propagated}を追加するメタクラスを提供します。

アロケーションが@code{:propagated}であるスロットへのアクセスは、
指定された他のオブジェクトのスロットへのアクセスにリダイレクトされます。
コンポジットしたオブジェクトの外部インタフェースを簡便に保ちたい時に便利です。
内部オブジェクトの持つスロットへのアクセスを、
親オブジェクトのスロットであるかのように見せられるからです。
@c COMMON
@end deftp

@c EN
An example would work better than explanation.
Suppose you have a @code{<rect>} class to represent
generic rectangular area, and you want to use it when you create
a @code{<viewport>} class by composition, instead of
inheritance.  A simple way would be as follows:
@c JP
説明よりまず例を示したほうがわかりやすいでしょう。
長方形の領域を表す@code{<rect>}という抽象クラスがある時、
それを継承ではなくコンポジションによって@code{<viewport>}クラスを作ることを
考えます。簡単な方法は次のようになるでしょう:
@c COMMON

@example
(define-class <rect> ()
  ((width  :init-keyword :width)
   (height :init-keyword :height)))

(define-class <viewport> ()
  ((dimension :init-form (make <rect>))
   ;;   ... other slots ...
   ))
@end example

@c EN
With this definition, whenever you want to access the viewport's
width or height, you have to go through @code{<rect>} object, e.g.
@code{(~ viewport'dimension'width)}.  This is not only cumbersome,
but the users of viewport class have to know that how the
viewport is composed (it's not necessarily a bad thing,
but sometimes you may want to hide it).
@c JP
この定義だと、viewportの高さや幅にアクセスした場合、
@code{(~ viewport'dimension'width)}のように
常に@code{<rect>}オブジェクトを経由しなければならなくなります。
これは煩わしいだけでなく、viewportクラスのユーザが、
viewportがどう構成されているかを知っていなければならないということでもあります
(必ずしも悪いことではないですが、時にはそれを隠したいこともあります)。
@c COMMON

@c EN
Using @code{gauche.mop.propagate}, you can define slots
@code{width} and @code{height} in @code{<viewport>} class
that are proxies of @code{<rect>}'s slots.
@c JP
@code{gauche.mop.propagate}を使うと、
@code{<viewport>}クラスに@code{width}と@code{height}スロットを定義して、
それ経由で内部の@code{<rect>}クラスへアクセスさせることができます。
@c COMMON

@example
(use gauche.mop.propagate)

(define-class <rect> ()
  ((width  :init-keyword :width)
   (height :init-keyword :height)))

(define-class <viewport> (<propagate-mixin>)
  ((dimension :init-form (make <rect>))
   (width     :allocation :propagated :propagate 'dimension
              :init-keyword :width)
   (height    :allocation :propagated :propagate 'dimension
              :init-keyword :height)))
@end example

@c EN
With @code{:propagated} allocation, the slots are not actually
allocated in @code{<viewport>} instance, and accesses to the
slots are redirected to the object in the slot specified by
@code{:propagate} slot option---in this case, the @code{dimension} slot.
It is somewhat similar to the virtual slots, but it's more convenient
for you don't explicitly write procedures to redirect the access.
@c JP
@code{:allocation}に@code{:propagated}が指定されると、
そのスロットは@code{<viewport>}インスタンス内にはアロケートされません。
そのスロットへのアクセスは、@code{:propagate}スロットオプションで指定される
スロット(上の例では@code{dimension}スロット)に格納されたオブジェクトへと
リダイレクトされます。
仮想スロットの一種とも言えますが、アクセス手続きを書く必要がありません。
@c COMMON

@c EN
Now you can treat @code{width} and @code{height} as if they
are slots of @code{<viewport>}.   You can even make them
initialize via @code{init-keyword} (but you can't use
@code{:init-form} or @code{:init-value}; if you want to specify
default values, give the default values to the actual object).
@c JP
こうすると、@code{width}と@code{height}スロットが@code{<viewport>}クラスの
スロットであるかのように扱えます。@code{init-keyword}による初期化も行えます。
(ただ、@code{:init-form}や@code{:init-value}は使えません。
初期値は実体を持つオブジェクトで指定してください)。
@c COMMON

@example
gosh> (define vp (make <viewport> :width 640 :height 480))
vp
gosh> (d vp)
#<<viewport> 0xc5a1e0> is an instance of class <viewport>
slots:
  dimension : #<<rect> 0xc5a130>
  width     : 640
  height    : 480
gosh> (set! (~ vp'width) 800)
#<undef>
gosh> (~ vp'width)
800
@end example

@c EN
Here's two classes that enables this feature.
Usually all you have to do is to inherit @code{<propagate-mixin>} class.
@c JP
以下の2つのクラスがこれを可能にしています。
通常、ユーザは@code{<propagate-mixin>}クラスを継承するだけで充分です。
@c COMMON

@deftp {Class} <propagate-meta>
@clindex propagate-meta
@c MOD gauche.mop.propagate
@c EN
Adds @code{:propagated} slot allocation.
The propagated slot has to have @code{:propagate} slot option
which specifies the name of the slot that points to an object
that actually holds the value of the slot.
If a slot has @code{:propagated} slot allocation but
does not have @code{:propagate} slot option, an error is signaled.
@c JP
スロットアロケーションに@code{:propagated}を追加します。
propagatedが指定されたスロットは、実体を持つオブジェクトを指定する
@code{:propagate}スロットオプションを持たねばなりません。
アロケーションが@code{:propagated}スロットであるにもかかわらず
@code{:propagate}スロットオプションが指定されていない場合は、エラーが投げられます。
@c COMMON

@c EN
The @code{:propagate} slot option should have a value
of either a symbol, or a list of two symbols.
@c JP
@code{:propagate}スロットオプションは、シンボルもしくは2つのシンボルからなる
リストを取ります。
@c COMMON

@c EN
If it is a symbol, it names the slot that contains an
object, whose slot with the same name of the propagate slot
holds the value.
@c JP
単なるシンボルであった場合、それは内部オブジェクトを格納しているスロットの名前です。
このスロットへのアクセスは、指定されたスロットが保持する内部オブジェクトの同名の
スロットへのアクセスにリダイレクトされます。
@c COMMON

@c EN
If it is a list of two symbols as @code{(X Y)}, then
the access to this propagated slot actually works as
@code{(slot-ref (slot-ref obj X) Y)}.
@c JP
二つのシンボルからなるリストであった場合、例えばそれを@code{(X Y)}とすると、
このスロットへのアクセスは@code{(slot-ref (slot-ref obj X) Y)}になります。
@c COMMON

@c EN
If you want to make a propagated slot initializable by
init-keywords, make sure the slot holding the actual object
comes before the propagated slots.  Slot initialization proceeds
in the order of appearance by default, and you want the
actual object is created before setting values.
@c JP
propagatedスロットを@code{init-keyword}で初期化可能にしたい場合、
propagateするオブジェクトをpropagatedスロットより前に置くようにしてください。
スロットの初期化はデフォルトでスロットの出現順に行われます。
内部オブジェクトの実体が先に作られていないと、そのスロットに初期値を設定できません。
@c COMMON
@end deftp

@deftp {Class} <propagate-mixin>
@clindex propagate-mixin
@c MOD gauche.mop.propagate
@c EN
This is a convenience mixin class.   Instead of giving
@code{:metaclass <propagate-meta>}, you can just inherit
this calss to make propagated slots available.
@c JP
これは簡便のためのmixinクラスです。
クラス定義で@code{:metaclass <propagate-meta>}を指定するかわりに、
このmixinクラスを継承すれば、propagatedスロットが使えるようになります。
@c COMMON
@end deftp

@c ----------------------------------------------------------------------
@node Singleton, Slot with validator, Propagating slot access, Library modules - Gauche extensions
@section @code{gauche.mop.singleton} - Singleton
@c NODE シングルトン, @code{gauche.mop.singleton} - シングルトン

@deftp {Module} gauche.mop.singleton
@mdindex gauche.mop.singleton
@c EN
Provides a metaclass to define a singleton class.
@c JP
シングルトンクラスを定義するためのメタクラスを提供します。
@c COMMON
@end deftp

@deftp {Class} <singleton-meta>
@clindex singleton-meta
@c MOD gauche.mop.singleton
@c EN
Creates a singleton class.  A singleton class is a class that is
guaranteed to create only one instance.
The first invocation of @code{make} creates the single instance,
and further attempt of creation returns the same instance.
@c JP
シングルトンクラスを生成します。シングルトンクラスはそのインスタンスが
ただ一つしかないことを保証するクラスです。 @code{make} の
最初の呼び出しで、唯一のインスタンスを生成し、その後の呼出しでは
最初に生成したものと同一のインスタンスを返します。
@c COMMON
@example
(define-class single () () :metaclass <singleton-meta>)

(define a (make single))
(define b (make single))

(eq? a b) @result{} #t
@end example

@c EN
The slots of the instance are initialized at the first invocation
of @code{make}.  Initargs of @code{make} are effective only in the
fist invocation, and ignored in the subsequent invocation.

The call of initialization in @code{make} is thread-safe.
Even if more than one thread calls @code{make} simultaneously,
instance allocation and initialization is done exactly once,
in one thread, while other threads wait for its completion
and returns the singleton instance.
@c JP
インスタンスのスロットは最初の @code{make} の呼び出し時に
初期化されます。@code{make}への初期引数は最初の呼び出しのときに
だけ効果があり、それ以降の呼び出しでは無視されます。

初期化ルーチンの呼び出しはスレッドセーフです。
複数のスレッドが同時に@code{make}を呼び出しても、
インスタンスのアロケーションと初期化は一度だけ、ひとつのスレッドで行われ、
残りのスレッドはその完了を待って作られたシングルトンインスタンスを返します。
@c COMMON
@end deftp

@deffn {Method} instance-of (class <singleton-meta>) :rest initargs
@c MOD gauche.mop.singleton
@c EN
This method just calls @code{make} with the passed arguments.
It is more obvious in the program that you're dealing with singleton.
@c JP
このメソッドは渡された引数とともに @code{make} を呼んでいるだけです。
シングルトンを扱うプログラム中ではこちらの方が分りやすいでしょう。
@c COMMON
@end deffn

@deftp {Class} <singleton-mixin>
@clindex singleton-mixin
@c MOD gauche.mop.singleton
@c EN
An instance of @code{<singleton-meta>}.  Instead of specifying
@code{<singleton-meta>} as the @code{:metaclass} argument of
@code{define-class}, you can inherit this class to give your
class the property of singleton.
@c JP
@code{<singleton-meta>}のインスタンスです。@code{<singleton-meta>}
を @code{define-class} の @code{:metaclass} 引数として指定せずに、
このクラスを継承することで、定義しようとするクラスにシングルトンの
性質を与えることができます。
@c COMMON
@end deftp

@c ----------------------------------------------------------------------
@node Slot with validator, Native type utilities, Singleton, Library modules - Gauche extensions
@section @code{gauche.mop.validator} - Slot with validator
@c NODE Validator付きスロット, @code{gauche.mop.validator} - Validator付きスロット

@deftp {Module} gauche.mop.validator
@mdindex gauche.mop.validator
@c EN
Provides a metaclass that adds @code{:validator} and @code{:observer}
slot options.
@c JP
@code{:validator}および@code{:observer}
スロットオプションを追加するメタクラスを提供するモジュールです。
@c COMMON
@end deftp

@deftp {Class} <validator-meta>
@clindex validator-meta
@c MOD gauche.mop.validator
@c EN
This metaclass adds a feature that you can specify callbacks that are
called before and after the slot value is set.
For example, if you want to guarantee
that a certain slot always holds a string value, you can make a procedure
be called before the slot is modified, either by @code{slot-ref} or
by a setter method.  In the procedure you can either rejects a
value except string, or coerce the value to a string.

A @emph{validator} procedure is a callback procedure that is called
before the slot value is set.   It can be specified by @code{:validator}
slot option.  The procedure takes two values, the instance and
the value to be set.  Whatever the procedure returns is set to
the actual slot value.

A @emph{observer} procedure is a callback procedure that is called
after the slot value is set.  It can be specified by @code{:observer}
slot option.  The procedure also takes two values, the instance
and the new value.  Result of the observer procedure is discarded.

See the following example:
@c JP
このメタクラスは、スロットの値がセットされる前後に呼ばれるコールバックを
指定する機能を提供します。例えば、あるスロットに常に文字列のみが
セットされているようにしたい場合、そのスロットに、@code{slot-ref}経由であれ
アクセサメソッド経由であれ値がセットされようとした時に指定の手続きが呼ばれるように
し、その手続きの中で、値が文字列でなかったらエラーとするか、強制的に値を
文字列に変換してしまうことができます。その手続きが返した値が実際にスロットに
セットされます。

スロットに値がセットされる前に呼ばれる@emph{validator}手続きは、
@code{:validator}スロットオプションによって指定できます。
手続きは、インスタンスとセットされようとしている値の二つを引数に取ります。
その手続きが返した値が実際にスロットにセットされる値となります。

スロットに値がセットされた後に呼ばれる@emph{observer}手続きは
@code{:observer}スロットオプションによって指定できます。
手続きは、インスタンスとセットされた値の二つを引数に取ります。
戻り値は捨てられます。

下の例を参照して下さい。
@c COMMON

@example
(define-class <v> ()
  ((a :accessor a-of
      :validator (lambda (obj value) (x->string value)))
   (b :accessor b-of
      :validator (lambda (obj value)
                   (if (integer? value)
                       value
                       (error "integer required for slot b")))))
  :metaclass <validator-meta>)

(define v (make <v>))
(slot-set! v 'a 'foo)
(slot-ref v 'a) @result{} "foo"

(set! (a-of v) 1234)
(a-of v) @result{} "1234"

(slot-set! v 'b 55)
(slot-ref v 'b) @result{} 55

(slot-set! v 'b 3.4) @result{} @r{error}
(set! (b-of v) 3.4)  @result{} @r{error}
@end example

@c EN
You can specify default slot value (@code{:init-value} etc.) with
@code{:validator}.  In that case, the initialization method of the
instance calls the validator with the specified default value,
if :init-keyword is not given.
@c JP
@code{:validator} が指定されたスロットにも、@code{:init-value}等を
使って既定の初期値を指定しておくことができます。
その場合、インスタンスの初期化ルーチンは、
init-keywordによる初期値指定が無ければ既定の初期値を引数としてvalidator手続きを
呼び出します。
@c COMMON

@example
(define-class <v> ()
  ((a :initform 'foo :init-keyword :a
      :validator (lambda (obj value) (x->string value)))))

(slot-ref (make <v>) 'a)        @result{} "foo"
(slot-ref (make <v> :a 555) 'a) @result{} "555"
@end example

@c EN
It looks similar to the virtual slot, but note that a slot with
validator has an actual storage in the instance, while a virtual
slot doesn't.

It is also a good example of customizing how the slots are accessed
using the metaobject protocol.  This feature is implemented by
only a couple of dozen lines of code.
@c JP
仮想スロットに似ていますが、validatorを持つスロットはインスタンス内に実際に
値を格納している点が異なります。

このモジュールはまた、スロットのアクセスをメタオブジェクトプロトコルを使って
カスタマイズする例でもあります。この機能は20行ほどのコードで実現されています。
@c COMMON
@end deftp

@c ----------------------------------------------------------------------
@node Native type utilities, Networking, Slot with validator, Library modules - Gauche extensions
@section @code{gauche.native-type} - Native type utilities
@c NODE ネイティブタイプユーティリティ, @code{gauche.native-type} - ネイティブタイプユーティリティ

@deftp {Module} gauche.native-type
@mdindex gauche.native-type
This module provides a type infrastructure to communicate with the
``native'', or ``close to the metal'' layer.  Examples include
foreign function interface (FFI) and structured binary data access.

Basic native types are built-in (@pxref{Native types}).  This module
adds constructors for derived or aggregate types (such as arrays
and structs), endian-specified types, conversions between
native type objects and compact signatures, and so on.

This module also provides @emph{native handles}, via which
you access native data from Scheme world (@pxref{Native handles}).
@end deftp

@menu
* Derived and aggregate native types::
* Representation-specific types::
* Native type signature::
* Native handles::
@end menu

@node Derived and aggregate native types, Representation-specific types, Native type utilities, Native type utilities
@subsection Derived and aggregate native types

We have subclasses of @code{<native-type>}, which are classes
of individual derived or aggregate native types.
For example, ``pointer to int'' native type is an instance of
@code{<c-pointer>} class.  Note that @code{<c-pointer>} itself
is not an instance of @code{<native-type>}.

@subsubheading C pointers

@deftp {Class} <c-pointer>
@clindex c-pointer
A class of native types representing pointers.  Can be created
with @code{make-c-pointer-type}, or from a signature
with @code{native-type} (e.g. @code{(native-type 'int*)},
@pxref{Native type signature}).

Note: At the moment, we don't keep track of quoalifiers
such as @code{const} or @code{volatile}, but their support may
be added in future.

A native handle with a C pointer type can be ``dereferenced''
with @code{native*} (@pxref{Native handles}).
@end deftp

@defun make-c-pointer-type pointee-type
@c MOD gauche.native-type
The argument must be an native type instance.
Returns an native type represents a pointer to the @var{pointee-type}.

@example
(make-c-pointer-type <int>)
  @result{} #<c-pointer <int*>>

(make-c-pointer-type (make-c-pointer-type <int>))
  @result{} #<c-pointer <int**>>
@end example
@end defun

@defun c-pointer-type-pointee c-pointer-type
@c MOD gauche.native-type
Returns the pointee type of the given c-pointer type.

@example
(c-pointer-type-pointee (make-c-pointer-type <int>))
  @result{} #<native-type <int>>
@end example
@end defun

@subsubheading C arrays

@deftp {Class} <c-array>
@clindex c-array
@c MOD gauche.native-type
A class of native types representing C-style arrays.  Can be created
with @code{make-c-array-type}, or from a signature
with @code{native-type} (e.g. @code{(native-type '(.array int (10)))},
@pxref{Native type signature}).

Arrays can have more than one dimensions.  Elements
with consectuve last indexes are laid adjacent on memory.
The length of the first dimension can be left unspecified
(we use @code{*} as a placeholder), just like C array
such as @code{int a[][10][3]}.

An element, or a subarray, of an array represented by a
native handle with a C array type
can be accessed with @code{native-aref} (@pxref{Native handles}).
@end deftp

@defun make-c-array-type element-type element-type dimensions
@c MOD gauche.native-type
Creates a C array type, whose elements are of type @var{element-type},
which must be a native type.

The @var{dimensions} argument must be a list of non-negative
exact integers, except that the first element may be a symbol @code{*}.
They specify the lengths of each dimension of the array.  Each index
of dimensions starts with 0.  @code{*} in the first dimension indicates
the length is unspecified.
@end defun

@defun c-array-type-dimensions c-array-type
@c MOD gauche.native-type
Returns a list of lengths of dimensions of @var{c-array-type}.
@end defun

@subsubheading C functions

@deftp {Class} <c-function>
@clindex c-function
@c MOD gauche.native-type
A class of native types representing C function types.  Can be created
with @code{make-c-function-type}, or from a signature
with @code{native-type} (e.g.
@code{(native-type '(.function (int int) ::int))},
@pxref{Native type signature}).

Instances of @code{<c-function>} describe the signature of a C function:
its return type, argument types, and whether it accepts variable arguments.

A native handle with a @code{<c-function>} type can be cast to and from
a pointer-to-function type with @code{cast-handle}
(@pxref{Native handles}).
@end deftp

@defun make-c-function-type return-type argument-type-list
@c MOD gauche.native-type
Returns a native type representing a C function that returns
@var{return-type} and takes arguments of the types listed in
@var{argument-type-list}.  Both @var{return-type} and each element
of @var{argument-type-list} must be native type instances, with
an exception below.

The last element of @var{argument-type-list} can be the symbol @code{...},
and then the resulting type represents a variadic function (like C's @code{...}
in @code{int printf(const char*, @dots{})}).  The @code{...} marker is
not a native type and is not included in the result of
@code{c-function-type-argument-types}.

@example
(make-c-function-type <int> `(,<int> ,<double>))
  @result{} #<c-function  int double -> int>

(make-c-function-type <int> `(,<int> ...))
  @result{} #<c-function  int ... -> int>

(c-function-type-argument-types (make-c-function-type <int> `(,<int> ...)))
  @result{} (#<native-type <int>>)

(c-function-type-variadic? (make-c-function-type <int> `(,<int> ...)))
  @result{} #t
@end example
@end defun

@defun c-function-type-return-type c-function-type
@c MOD gauche.native-type
Returns the return type of @var{c-function-type} as a native type instance.
@end defun

@defun c-function-type-argument-types c-function-type
@c MOD gauche.native-type
Returns the list of argument types of @var{c-function-type}.  Each element
is a native type instance.  The variadic marker @code{...} is not included;
use @code{c-function-type-variadic?} to check for variadic functions.
@end defun

@defun c-function-type-variadic? c-function-type
@c MOD gauche.native-type
Returns @code{#t} if @var{c-function-type} represents a variadic function
(i.e., it was created with @code{...} as the last element of the
argument-type list), @code{#f} otherwise.
@end defun

@subsubheading C structs and unions

@deftp {Class} <c-struct>
@deftpx {Class} <c-union>
@clindex c-struct
@clindex c-union
@c MOD gauche.native-type
A class of native types representing C struct and union types, respectively.
Can be created with @code{make-c-struct-type} and
@code{make-c-union-type}, or from a signature with
@code{native-type} (e.g.
@code{(native-type '(.struct t (a::int b::char)))},
@pxref{Native type signature}).
@end deftp

@defun make-c-struct-type tag fields
@defunx make-c-union-type tag fields
@c MOD gauche.native-type
Returns a native type representing a C struct type or a C union type.
@var{tag} can be a symbol representing the struct/union tag, or @code{#f}
for untagged struct/union.

@var{fields} is a list of @code{(@var{symbol} @var{type})}, where
@var{symbol} names the field's name, and @var{type} for its type.
@var{type} must be an instance of a native type.

When a struct/union type is constructed, its total size and each field's
offset are computed (in unions, all the offsets are 0).
@end defun

@defun c-struct/union-type-tag c-struct/union-type
@c MOD gauche.native-type
Returns the tag (symbol) of @var{c-struct/union-type}.
If the type is untagged, @code{#f} is returned.
@end defun

@defun c-struct/union-type-field-names c-struct/union-type
@c MOD gauche.native-type
Returns a list of field names (symbols) of @var{c-struct/union-type}.
@end defun

@defun c-struct/union-type-field-type c-struct/union-type field-name
@defunx c-struct/union-type-field-offset c-struct/union-type field-name
@c MOD gauche.native-type
Returns the type and the byte offset of @var{field-name} (symbol)
of @var{c-struct/union-type}.
@end defun

@subsubsection Predicates

@defun c-pointer-type? obj
@defunx c-array-type? obj
@defunx c-function-type? obj
@defunx c-struct-type? obj
@defunx c-union-type? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is an instance of @code{<c-pointer>},
@code{<c-array>}, @code{c-function>}, @code{c-struct}, or @code{<c-union>},
and @code{#f} otherwise, respectively.
@end defun

@defun c-pointer-like-type? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is either a C pointer type,
a C array type, or a C function type.  Handles of those types
can be ``casted'' to a pointer type, following the C semantics.
See @code{cast-handle} for the details (@pxref{Native handles}).
@end defun

@defun c-aggregate-type? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is either a C array type,
a C struct type, or a C union type.
@end defun

@defun c-struct/union-type? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is either
a C struct type, or a C union type.
@end defun

@node Representation-specific types, Native type signature, Derived and aggregate native types, Native type utilities
@subsection Representation-specific types

Primitive native types such as @code{<int16>} read/write memory
with the system's native endianness.  For FFI it is fine.  However,
if you read/write binary data for exchanging between systems,
you need to explicitly specify the endianness.

We have native types for that purpose.

@deftp {Native type} <int16-be>
@deftpx {Native type} <int16-le>
@deftpx {Native type} <int32-be>
@deftpx {Native type} <int32-le>
@deftpx {Native type} <int64-be>
@deftpx {Native type} <int64-le>
@deftpx {Native type} <uint16-be>
@deftpx {Native type} <uint16-le>
@deftpx {Native type} <uint32-be>
@deftpx {Native type} <uint32-le>
@deftpx {Native type} <uint64-be>
@deftpx {Native type} <uint64-le>
@deftpx {Native type} <float-be>
@deftpx {Native type} <float-le>
@deftpx {Native type} <double-be>
@deftpx {Native type} <double-le>
@clindex int16-be
@clindex int16-le
@clindex int32-be
@clindex int32-le
@clindex int64-be
@clindex int64-le
@clindex uint16-be
@clindex uint16-le
@clindex uint32-be
@clindex uint32-le
@clindex uint64-be
@clindex uint64-le
@clindex float-be
@clindex float-le
@clindex double-be
@clindex double-le
@c MOD gauche.native-type
These native types accesses binary data as the specified numeric type,
@emph{and} the specified endianncess (@code{-be} for big-endian,
@code{-le} for little endian).

The endianness is only considered when reading from or writing to memory
through native handles (with @code{native*} etc, @pxref{Native handles}).
In other words, these types only makes sense when they are used
within derived or aggregate types.
@end deftp


@node Native type signature, Native handles, Representation-specific types, Native type utilities
@subsection Native type signature

A @dfn{native type signature} is a compact S-expression description of
a native type.  It lets you specify pointer, array, struct, union, and
function types without explicitly calling the corresponding constructors
such as @code{make-c-pointer-type}.

The procedure @code{native-type} can parse a signature
and returns the native type instance it denotes; @code{native-type->signature}
performs the inverse conversion.  Signatures are also recognized in
some other places where a native type is expected---for example, in
struct/union field type declarations within @code{.struct} and
@code{.union} signature forms (so compound types can be written
without first naming each piece).

The signature format has been used in Gauche-C interface for long time
(stubs and CiSE), though hasn't been documented well.  Because of its
origin to transfer C type declarations to S-expression, it may feel
C-centric.

@subsubheading Primitive types

A bare symbol whose name matches a built-in C type name denotes the
corresponding primitive native type.  Recognized names follow the
C spelling, e.g.@: @code{int}, @code{u_int}, @code{short}, @code{u_short},
@code{long}, @code{u_long}, @code{char}, @code{int8_t}, @code{uint8_t},
@code{int16_t}, @code{uint16_t}, @code{int32_t}, @code{uint32_t},
@code{int64_t}, @code{uint64_t}, @code{size_t}, @code{ssize_t},
@code{ptrdiff_t}, @code{off_t}, @code{intptr_t}, @code{uintptr_t},
@code{float}, @code{double}, and @code{void}.  See @ref{Native types}
for the corresponding type instances and what Scheme values they accept.

C's @code{char} denotes the native type @code{<c-char>}, for
@code{<char>} is used for Gauche's character type.  @code{<c-char>}
is mapped to a Scheme character with unicode range U+0000 to U+00FF.
If the C routine uses @code{char} as a byte-sized numeric value,
use @code{int8_t} or @code{uint8_t} (depending on signedness) instead.

The pseudo-name @code{c-string} denotes the @code{<c-string>} type
(NUL-terminated C string).  This special name is provided because
C type @code{const char *} may simply mean a pointer to byte-sized
numeric data, thus ambiguous.

pThe endian-specified types listed in @ref{Representation-specific types}
are also accepted, by their underscore-separated names: @code{int16_le},
@code{int16_be}, @code{uint16_le}, @code{uint16_be}, and likewise for
the 32-bit and 64-bit integer types and for @code{float} and @code{double}.

@subsubheading Pointer types

A symbol whose name ends with one or more asterisks denotes a pointer
type; each trailing asterisk wraps the rest of the type in one
additional layer of @code{<c-pointer>}.  Thus @code{int*} is equivalent
to @code{(make-c-pointer-type <int>)}, @code{char**} is a pointer to a
pointer to @code{<c-char>}, and so on.

C-style multi-token forms are also accepted as a list of symbols.
The list is normalized by stripping any @code{const} tokens and
concatenating the rest into a single symbol.  Therefore
@code{(char *)}, @code{(char const*)}, @code{(const char*)},
@code{(int * *)}, and @code{(int** *)} are all valid.  The form
@code{(const @var{type})} is also accepted, with @code{const}
currently ignored.

(We do not yet track @code{const} or @code{volatile} qualifiers on the
resulting native type; they are silently dropped.  Support may be added
in the future.)

@subsubheading Array types

@example
(.array @var{element-type} (@var{dim} @dots{}))
@end example

Denotes a C-style array.  @var{element-type} is itself a native type
signature.  Each @var{dim} is a non-negative exact integer, except
that the leftmost @var{dim} may be the symbol @code{*} to indicate an
unspecified leading dimension (as in C's @code{int a[][3][4]}).
Multiple dimensions describe a multi-dimensional array, with elements
that share leading indices laid out adjacently in memory (the last
index varies fastest).

@subsubheading Struct and union types

@example
(.struct @var{tag} (@var{field-spec} @dots{}))
(.struct (@var{field-spec} @dots{}))
(.union  @var{tag} (@var{field-spec} @dots{}))
(.union  (@var{field-spec} @dots{}))
@end example

Denote a C struct or union type.  @var{tag}, when given, is a symbol
that names the struct/union tag; the second form of each pair (with no
tag) denotes an anonymous struct/union.

Each @var{field-spec} has the form
@code{@var{name}::@var{type}}, using the typed-variable notation
common across Gauche.  @var{name} is a symbol naming the field, and
@var{type} is itself a native type signature, so fields may be of
compound type as well.  For the convenience, the delimiter @code{::}
may be concatenated to @code{name} and/or @code{type}--
for example, @code{a::int} and @code{a :: int} are equivalent.

@subsubheading Function types

@example
(.function (@var{arg-type} @dots{}) @var{return-type})
@end example

Denotes a C function type.  Each @var{arg-type} and @var{return-type}
is itself a native type signature.  If the last @var{arg-type} is the
literal symbol @code{...}, the resulting type is variadic
(corresponding to C's trailing @code{...}); the @code{...} marker is
not itself a type, and is not included in the argument-type list
returned by @code{c-function-type-argument-types}.  Use
@code{c-function-type-variadic?} to test for variadicity.

@subsubheading Pass-through

If the argument is already an instance of @code{<native-type>},
@code{native-type} returns it unchanged.  This makes it convenient for
higher-level routines to accept either a signature or a previously
constructed type instance.

Notably, you can emulate C's @code{typedef} by assigning native type
to a variable, and inserting it in another type signature:

@example
(define foo (.struct foo (a::int b::int)))

(native-type `(.array ,foo (10))) @result{} #<c-array struct foo(10)>
@end example

@subsubheading Examples

@example
(native-type 'int)
  @result{} #<native-type <int>>

(native-type 'int*)
  @result{} #<c-pointer <int*>>

(native-type 'char**)
  @result{} #<c-pointer <c-char**>>

(native-type '(char const *))
  @result{} #<c-pointer <c-char*>>

(native-type 'c-string)
  @result{} #<native-type <c-string>>

(native-type '(.array int (3 4)))
  @result{} #<c-array <int>(3 4)>

(native-type '(.array int (* 3)))
  @result{} #<c-array <int>(* 3)>

(native-type '(.struct point (x::double y::double)))
  @result{} #<c-struct struct point>

(native-type '(.union v (i::int f::float)))
  @result{} #<c-union union v>

(native-type '(.function (int int) double))
  @result{} #<c-function <int> <int> -> <double>>

(native-type '(.function (char* ...) int))
  @result{} #<c-function <c-char*> ... -> <int>>
@end example

@defun native-type signature-or-type
@c MOD gauche.native-type
The argument must be an S-expression type signature or
a native type instance.  If it is a type signature, a native
type instance denoted by the type signature is returned.
If the argument is already a native type instance, it is returned
as is.

See above for the specification of a native type signature.
@end defun

@defun native-type->signature native-type
@c MOD gauche.native-type
Returns a native type signature that denotes the given native type.
@end defun

@node Native handles,  , Native type signature, Native type utilities
@subsection Native handles

A native handle is a handle through which you can access native data.
Native handles may be returned from a foreign function call, or you can
create one from a binary buffer.  C pointers, arrays, structs, and unions
to be passed to and from foreign functions are reprensed by native handles.

@subsubheading Native handle class and predicates

@deftp {Class} <native-handle>
@clindex native-handle
@c MOD gauche.native-type
The class of native handle.  A native handle is either a typed
reference of, or a typed pointer to a native object.
Its type can be retrieved with @code{native-handle-type}.
The pointed or referenced object is retrieved with
type-specific accessors below.

A native handle can be of c-pointer, c-array, c-function,
c-struct or c-union types.  If it's other than c-pointer type,
native handle holds a reference.  The distinction of pointers and
references is vague in the Scheme world, since all heap-allocated Scheme
objects are treated indirectly.  But there's a distinction in the C/C++ world;
the following example session shows it.

@example
(define inner (native-type '(.struct (a::int b::int))))
(define outer (native-type `(.struct (ref::,inner ptr::(,inner *)))))

(define handle (uvector->native-handle (make-u8vector (~ outer'size)) outer))

(set! (native. (native. handle 'ref) 'a) 1)  ; handle.ref.a = 1
(set! (native. (native. handle 'ref) 'b) 2)  ; handle.ref.b = 2

(set! (native. handle 'ptr) (native& handle 'ref)) ; handle.ptr = &handle.ref

(define inner-ref (native. handle 'ref)) ; inner& inner_ref = handle.ref
inner-ref @result{} #<native-handle struct anonymous@@0x77a1b10f51f0>

(define inner-ptr (native. handle 'ptr)) ; inner* inner_ptr = handle.ptr
inner-ptr @result{} #<native-handle <struct anonymous*>@@0x77a1b10f51f0>

(native. inner-ref 'a)  @result{} 1           ; inner_ref.a
(native-> inner-ptr 'a)  @result{} 1          ; inner_ptr->a

(native. (native* inner-ptr) 'b) @result{} 2 ; (*inner_ptr).b
@end example
@end deftp

@defun native-handle-type handle
@c MOD gauche.native-type
Returns the native type of the handle.
@end defun

@defun c-pointer-handle? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is a native handle of c-pointer type,
@code{#f} otherwise.
@end defun

@defun c-function-handle? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is a native handle of c-function type,
@code{#f} otherwise.
@end defun

@defun c-array-handle? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is a native handle of c-array type,
@code{#f} otherwise.
@end defun

@defun c-struct-handle? obj
@defunx c-union-handle? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is a native handle of c-struct
and c-union type, respectively,
@code{#f} otherwise.
@end defun

@defun c-aggregate-handle? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is a native handle of c-array,
c-struct, or c-union type,
@code{#f} otherwise.
@end defun

@defun c-pointer-like-handle? obj
@c MOD gauche.native-type
Returns @code{#t} if @var{obj} is a native handle of c-array,
c-pointer, or c-function type.
@end defun

@subsubheading Accessing through native handles

@defun native* handle
@c MOD gauche.native-type
Pointer dereference.  @var{handle} must be a c-pointer handle.
Returns the pointed value @emph{boxed} as a Scheme object.
if the pointed value is an object of c-pointer or c-aggregate types,
a native handle representing that object is returned.
@end defun

@defun (setter native*) handle val
@c MOD gauche.native-type
You can use a generic setter to modify the value in the pointed location.
@var{val} must be a value acceptable as the pointee type of
the pointer.
@end defun

@defun native-aref handle index
@c MOD gauche.native-type
Array reference.  @var{handle} must be a c-array handle or c-pointer
handle (Allowing c-pointer here reflects the C semantics).

@var{index} must be a nonnegative integer or a list of nonnagative
integers.  If the element type is a primitive type,
the value is returned as a Scheme value.  If the element type is
a pointer type or an aggregate type, the value is wrapped as a
native handle.

C's multidimensional array is effectively nested one-dimensional
arrays. If you give indexes less than the rank of the array,
a handle to the subarray is returned.

If the handle points to an unbounded c-array or a c-pointer,
no boundary check is done with @var{index}.  It is caller's
responsibility to ensure @var{index} falls in a valid range.
@end defun

@defun (setter native-aref) handle index val
@c MOD gauche.native-type
@var{handle} must be a c-array or c-pointer handle, and
@var{index} must be a nonnegative integer or a list of nonnagative
integers.

Sets @var{val} to the array at the position specified by @var{index}.

If the handle points to an unbounded c-array or a c-pointer,
no boundary check is done with @var{index}.  It is caller's
responsibility to ensure @var{index} falls in a valid range.
@end defun

@defun native. handle slot
@c MOD gauche.native-type
Struct/union field reference.  @var{handle} must be a native handle
of c-struct or c-union type, and @var{slot} must be a symbol
naming its slot.  An error is thrown if the struct/union doesn't
have the named slot.
@end defun

@defun (setter native.) handle slot val
@c MOD gauche.native-type
Sets @var{val} to the field @var{slot} of c-struct or c-union @var{handle}.
@end defun

@defun native-> handle slot
@c MOD gauche.native-type
Indirect struct/union field reference.  @var{handle} must be
a native handle of c-pointer to a c-struct or c-union.
@code{(native-> handle slot)} is the same as
@code{(native. (native* handle) slot)}, just like
@code{s->a} and @code{(*s).a} are the same in C.
@end defun

@defun (setter native->) handle slot :optional type
@c MOD gauche.native-type
Sets @var{val} to the field @var{slot} of c-struct or c-union
pointed by a c-pointer handle @code{handle}.
@end defun

@defun native& handle selector
@c MOD gauche.native-type
This takes the pointer to an element inside an aggregate data
referenced by @var{handle}.  The @var{handle} must be a
native handle fo type c-array, c-struct, or c-union.  An error
is signaled if other type of native handle is given.

If @var{handle} is a c-struct or c-union, @var{selector} must
be a symbol naming its field.  A c-poitner handle points to
the field is returned.

If @var{handle} is a c-array, @var{selector} must be a fixnum,
or a list of fixnums, as the index to the array.  If the array
is 1-dimensional, a fixnum or a list of signle fixnum is
accepted.  A c-pointer handle points to the element is
returned.

@example
(define ts (native-type '(.struct (a::int))))
(define hs (uvector->native-handle (make-u8vector (~ ts'size)) ts))

(native& hs 'a) @result{} #<native-handle <int*>@@0x726ffcc1a060>

(define ta (native-type '(.array int (10))))
(define ha (uvector->native-handle (make-u8vector (~ ta'size)) ta))

(native& ha 3) @result{} #<native-handle <int*>@@0x726ffcccd42c>
@end example
@end defun

@subsubheading Pointer handle operations

@defun cast-handle type handle :optional offset
@c MOD gauche.native-type
@end defun

@defun c-pointer-compare handle-a handle-b
@c MOD gauche.native-type
@end defun

@defun c-pointer=? handle-a handle-b
@defunx c-pointer<? handle-a handle-b
@defunx c-pointer<=? handle-a handle-b
@defunx c-pointer>? handle-a handle-b
@defunx c-pointer>=? handle-a handle-b
@c MOD gauche.native-type
@end defun

@subsubheading Aggregate handle operations

@defun c-memwise-compare handle-a handle-b
@c MOD gauche.native-type
@end defun

@subsubheading Creating a native handle

@defun uvector->native-handle uv type :optional offset
@c MOD gauche.native-type
This creates a native handle of native type @var{type}, using a uniform
vector @var{uv} as the backing storage.  This is useful to prepare
binary data in Scheme world.  @var{type} must be a pointer or
an aggregate native type.

@var{uv} can also be @code{#f}, in which case a u8vector of size
to contain object of @var{type} is allocated and used.

If @var{offset} is given, it specifies a byte offset from
the beginning of @var{uv} for the resulting handle to point to.
Using @var{offset}, you can extract a native handle
in the middle of larger binary data.  If it is omitted, 0 is assumed.

The size of @var{uv} in bytes minus @var{offset} must be greater than
or equal to the size of @var{type}, or an error is thrown.

The returned native handle can be passed to a foreign function.
Note that, however, if the foreign function retains the pointer,
it may not be visible from Gauche's GC.  You have to make sure to
retain reference to @var{uv} or the resulting native handle
in the Scheme world as far as the pointer is retained in the
foreign world.

You can use any type of uniform vector as @var{uv}, but other than
@code{u8vector} and @code{s8vector}, the machine's native endianness
is exposed as the binary data.

@example
(define ip (uvector->native-handle '#u8(#xff #xff #xff #xff)
                                   (native-type 'int32_t*)))

ip @result{} #<native-handle <int32*>@@0x7d6fbf442ff0>

(native* ip) @result{} -1
@end example
@end defun

@defun null-pointer-handle :optional type
@c MOD gauche.native-type
Returns a c-pointer handle representing NULL pointer.
The optional argument @var{type} must be a c-pointer type and
specifies the type of the resulting handle.  When omitted,
@code{<void*>} native type is assumed.
(For FFI calls, you can pass @code{<void*>} pointer to wherever
a pointer is expected.)
@end defun

@defun null-pointer-handle? obj
@c MOD gauche.native-type
Returns @code{#t} if @code{obj} is a native handle representing
NULL pointer (of any c-pointer type), @code{#f} otherwise.
@end defun

@c ----------------------------------------------------------------------
@node Networking, Package metainformation, Native type utilities, Library modules - Gauche extensions
@section @code{gauche.net} - Networking
@c NODE ネットワーキング, @code{gauche.net} - ネットワーキング

@deftp {Module} gauche.net
@mdindex gauche.net
@c EN
Provides a set of functions necessary for network communications
based on BSD socket interface.

The API is provided in two different levels.  Lower level routines
reflect traditional BSD socket interface, such as @code{bind(2)}.
Higher level routines provides more convenient way to create
typical connection-oriented server/client sockets.

This module also provides APIs to obtain various information
about hostnames, service ports, and protocols.
@c JP
BSDソケットに基づいたネットワーキングに必要な手続きを提供するモジュールです。

2つのレベルのAPIが定義されています。低レベルの手続きは@code{bind(2)}のような
BSDソケットインタフェースに近いインタフェースを提供し、高レベルの手続きは
典型的なコネクション指向のクライアントサーバアプリケーションに便利な
インタフェースを提供します。

また、ホストネームやプロトコルに関する情報にアクセスするAPIも定義されます。
@c COMMON

@c EN
Gauche can handle IPv6 if it is compiled
with the @code{--enable-ipv6} configuration option.
To check whether IPv6 is enabled or not,
you can use @code{cond-expand} with
@code{gauche.net.ipv6} feature identifier
after loading @code{gauche.net}, as shown below.

@example
(use gauche.net)
(cond-expand
  (gauche.net.ipv6
    ... code to use ipv6 ...)
  (else
    ... ipv4 only code ...))
@end example

See @ref{Feature conditional} for the details of @code{cond-expand}.
@c JP
Gaucheは、@code{--enable-ipv6}コンフィギュアオプションつきで
コンパイルされていれば、IPv6を扱うことができます。
IPv6が使えるかどうかを調べるには、
@code{cond-expand}中で@code{gauche.net.ipv6} feature identifierを
使うことができます。次の例を見てください。

@example
(use gauche.net)
(cond-expand
  (gauche.net.ipv6
    ... ipv6を使うコード ...)
  (else
    ... ipv4のみのコード ...))
@end example

@code{cond-expand}の詳細については@ref{Feature conditional}を
参照してください。
@c COMMON

@end deftp

@c EN
Note: If you want to write a portable program using network,
take a look at @code{srfi.106} (@pxref{Basic socket interface}).
@c JP
ネットワークを使うポータブルなコードを書きたい場合は、
@code{srfi.106}を見てください (@ref{Basic socket interface}参照)。
@c COMMON

@menu
* Socket address::
* High-level network functions::
* Low-level socket interface::
* Netdb interface::
@end menu

@node Socket address, High-level network functions, Networking, Networking
@subsection Socket address
@c NODE ソケットアドレス

@c EN
@subsubheading Socket address objects
@c JP
@subsubheading ソケットアドレスオブジェクト
@c COMMON

@deftp {Builtin Class} <sockaddr>
@clindex sockaddr
@c MOD gauche.net
@c EN
An abstract base class of socket addresses.  Each socket address family
is implemented as a subclass of this class.

Although socket addresses are built-in classes, you can use
@code{make} method to create an instance of a
specific socket address family.
@c JP
ソケットアドレスの抽象ベースクラスです。
ソケットアドレスファミリはこのクラスのサブクラスとして実装されます。

ソケットアドレスはビルトインクラスですが、@code{make}メソッドで
特定のソケットアドレスファミリのインスタンスを作成することができます。
@c COMMON
@end deftp

@deffn {Generic Function} sockaddr-family addr
@c MOD gauche.net
@c EN
Returns a symbol that indicates the family of the socket address
@var{addr}.
@c JP
ソケットアドレス@var{addr}のファミリを表すシンボルを返します。
@c COMMON
@end deffn

@deffn {Generic Function} sockaddr-name addr
@c MOD gauche.net
@c EN
Returns a string which represents the content of the socket address
@var{addr}.
@c JP
ソケットアドレス@var{addr}の名前を表す文字列を返します。
@c COMMON
@end deffn

@deftp {Builtin Class} <sockaddr-in>
@clindex sockaddr-in
@c MOD gauche.net
@c EN
AF_INET family socket address.  To create an instance of this class,
use @code{make} method as follows:
@c JP
AF_INETファミリのソケットアドレスです。このクラスのインスタンスを
作成するには、次のようにして@code{make}メソッドを呼びます。
@c COMMON
@example
(make <sockaddr-in> :host @var{host} :port @var{port})
@end example
@c EN
@var{host} can be a string, an integer IP address, a
@code{u8vector} IP address, or one of the keywords
@code{:any}, @code{:broadcast}, @code{:none} or @code{:loopback}.
If it is a string, it is either a host name or a dotted IP notation.
Gauche uses @code{gethostbyname(3)} to obtain the actual IP address from
@var{host} parameter.  If it is a keyword @code{:any},
or @code{:broadcast}, the address
uses @code{INADDR_ANY}, or @code{INADDR_BROADCAST}
respectively.  The keyword @code{:loopback} is a synonym to the
IPv4 loopback address "127.0.0.1".
@c JP
@var{host}は文字列、整数のIPアドレス、@code{u8vector}のIPアドレス、
もしくは@code{:any}、@code{:broadcast}、@code{:none}、@code{:loopback}の
いずれかのキーワードでなければなりません。
文字列の場合、それはホスト名かIPアドレスのドット表記です。
Gaucheは@code{gethostbyname(3)}を使って実際のIPアドレスを得ます。
この値がキーワード@code{:any}か@code{:broadcast}なら、それぞれ
@code{INADDR_ANY}か@code{INADDR_BROADCAST}がアドレスとして使われます。
キーワード@code{:loopback}はIPv4のループバックアドレス"127.0.0.1"を表します。
@c COMMON

@c EN
@var{port} must be a positive integer indicating the port number.
@c JP
@var{port}はポート番号を示す正の整数です。
@c EN
See also @code{make-sockaddrs} below, to create multiple
socket addresses on the machine which may have more than one
protocol stack.
@c JP
2つ以上のプロトコルスタックを持つようなマシン上で複数のソケットアドレスを
生成するには、後述の @code{make-sockaddrs} も参照してください。
@c COMMON
@end deftp

@deffn {Method} sockaddr-family (addr <sockaddr-in>)
@c MOD gauche.net
@c EN
Returns a symbol @code{inet}.
@c JP
シンボル@code{inet}を返します。
@c COMMON
@end deffn

@deffn {Method} sockaddr-name (addr <sockaddr-in>)
@c MOD gauche.net
@c EN
Returns a string in the form "@var{a}.@var{b}.@var{c}.@var{d}:@var{port}",
 where "@var{a}.@var{b}.@var{c}.@var{d}" is dotted decimal notion of
the IP address and @var{port} is the port number.
@c JP
文字列"@var{a}.@var{b}.@var{c}.@var{d}:@var{port}"を返します。
コロンの前はIPアドレスのドット表記で、@var{port}はポート番号です。
@c COMMON
@end deffn

@deffn {Method} sockaddr-addr (addr <sockaddr-in>)
@deffnx {Method} sockaddr-port (addr <sockaddr-in>)
@c MOD gauche.net
@c EN
Returns the IP address and the port number as an integer, respectively.
@c JP
それぞれ、IPアドレスとポート番号を整数で返します。
@c COMMON
@end deffn

@deftp {Builtin Class} <sockaddr-un>
@clindex sockaddr-un
@c MOD gauche.net
@c EN
AF_UNIX family socket address.  To create an instance of this class,
use @code{make} method as follows:
@c JP
AF_UNIXファミリのソケットアドレスです。このクラスのインスタンスを作成するには、
@code{make}メソッドを次のように呼んで下さい。
@c COMMON
@example
(make <sockaddr-un> :path @var{path})
@end example
@c EN
@var{path} must be a string specifying pathname of the socket.
@c JP
@var{path}はソケットのパス名を表す文字列です。
@c COMMON
@end deftp

@deffn {Method} sockaddr-family (addr <sockaddr-un>)
@c MOD gauche.net
@c EN
Returns a symbol @code{unix}.
@c JP
シンボル@code{unix}を返します。
@c COMMON
@end deffn

@deffn {Method} sockaddr-name (addr <sockaddr-un>)
@c MOD gauche.net
@c EN
Returns a pathname of the socket address.
@c JP
ソケットアドレスのパス名を返します。
@c COMMON
@end deffn

@deftp {Builtin Class} <sockaddr-in6>
@clindex sockaddr-in6
@c MOD gauche.net
@c EN
AF_INET6 family socket address.  This is only available if
gauche is configured with --enable-ipv6 configure option.
The constructor and the slots are the same as @code{<sockaddr-in>}.
@c JP
AF_INET6ファミリのソケットアドレスです。
このクラスはgaucheが--enable-ipv6つきでconfigureされている場合に使えます。
コンストラクタとスロットは@code{<sockaddr-in>}と同じです。
@c EN
See also @code{make-sockaddrs} below, to create multiple
socket addresses on the machine which may have more than one
protocol stack.
@c JP
2つ以上のプロトコルスタックを持つようなマシン上で複数のソケットアドレスを
生成するには、後述の @code{make-sockaddrs} も参照してください。
@c COMMON
@end deftp

@defun make-sockaddrs host port :optional proto
@c MOD gauche.net
@c EN
This is a higher-level utility procedure to create all possible
inet domain socket addresses that point to @code{@var{host}:@var{port}}
of protocol @var{proto}.  Particularly, if the specified host has
both IPv4 and IPv6 addresses, and the running system supports both,
then both IPv4 and IPv6 socket addresses are returned.   If @var{host} has
multiple IP addresses, socket addresses are created for each of these
IP address.   You can make your network application much more portable
among different network stack configurations.

Passing @code{#f} to @var{host} creates the local
(server) address.  You can also pass a service name (e.g. @code{"http"})
instead of an integer, to the @var{port} argument.
The value of @var{proto} can be either a symbol @code{tcp} or @code{udp},
and the default is @code{tcp}.

It always returns a list of socket addresses.  If the lookup of @var{host}
is failed, null list is returned.
@c JP
これは上位レベルのユーティリティ手続きで、プロトコル @var{proto} の
@code{@var{host}:@var{port}} を指す、可能なすべてのドメインソケット
アドレスを生成します。特に、指定したホストが IPv4 および IPv6 の両方の
アドレスを持ち、稼働中のシステムがその両方をサポートしている場合、IPv4 と
IPv6 の両方のソケットアドレスが返ります。もし、@var{host} が複数の
IP アドレスをもつ場合、ソケットアドレスはそれぞれのIPアドレス毎に生成
されます。自分のネットワークアプリケーションを異るネットワークスタックの
設定の間でこれまでよりはるかにポータブルなものにすることができます。

@var{host} に @code{#f} を渡すと、ローカルな(サーバ)アドレスが生成されます。
@var{port} 引数に整数のかわりに、サービス名(たとえば、@code{"http"})を
わたすこともできます。@var{proto} の値は、@code{tcp} あるいは @code{udp}
のどちらかのシンボルになります。デフォルトでは、@code{tcp} です。

この手続きは常にソケットアドレスのリストを返します。もし、@var{host} の
検索に失敗した場合には、空リストが返ります。
@c COMMON
@end defun

@c EN
@subsubheading Address and string conversion
@c JP
@subsubheading アドレスと文字列との変換
@c COMMON

@defun inet-string->address address
@c MOD gauche.net
@c EN
Converts string representing of the internet address @var{address}
to an integer address.  If @var{address} is parsed successfully,
returns two values: the integer address value and the recognized
protocol (the constant value @code{2} (= @code{AF_INET})
for IPv4 addresses, and @code{10} (= @code{AF_INET6})
for IPv6 addresses).  If @var{address} can't be
parsed, @code{#f} and @code{#f} are returned.
@c JP
文字列で表現されたインターネットアドレス@var{address}を整数のアドレス
に変換します。@var{address}のパーズが成功した場合には値を2つ返します。
ひとつは整数で表現されたアドレスの値、もうひとつは認識されたプロトコル
(定数値で、@code{2} (= @code{AF_INET})ならIPv4アドレス、@code{10} (=
@code{AF_INET6})ならIPv6アドレス)です。@var{address}のパーズに失敗した
ら、@code{#f}と@code{#f}との2つが返ります。
@c COMMON

@example
(inet-string->address "192.168.1.1")
 @result{} 3232235777 and 2
(inet-string->address "::1")
 @result{} 1 and 10
(inet-string->address "::192.168.1.1")
 @result{} 3232235777 and 10
(inet-string->address "ffe0::1")
 @result{} 340116213421465348979261631549233168385 and 10
(inet-string->address "::192.168.1.1")
 @result{} 3232235777 and 10
@end example
@end defun

@defun inet-string->address! address buf
@c MOD gauche.net
@c EN
Like @code{inet-string->address}, but fills the given u8vector
@var{buf} by the parsed address instead of returning it as
an integer value.  The integer representation of inet addresses
is likely to be a bignum, and you can avoid creating bignums
with this function.  The given u8vector @var{buf} must be mutable.
Returns the protocol on success, or @code{#f} on failure.
@c JP
@code{inet-string->address}と同じですが、整数値を返すかわりに、与えら
れたu8vectorである@var{buf}をパーズしたアドレスで埋めるところが違いま
す。inetアドレスの整数表現はbignumと同じやりかたです。この関数を使えば
bignumを生成しなくてすみます。与えられたu8vector@var{buf}は変更可能で
なければなりません。変換に成功した場合はプロトコルが、失敗した場合は
@code{#f}が返ります。
@c COMMON

@c EN
The caller must provide big enough buffer.  If @var{buf}
is larger than required, the result is filled from the top
of the u8vector and the rest of the vector remains intact.
@c JP
呼び出し側は格納に十分なバッファを用意しなければなりません。@var{buf}
が必要な分より大きい場合には結果は先頭から詰められ、ベクタの他の部分は
そのままになります。
@c COMMON

@example
(let* ((buf (make-u8vector 16 0))
       (proto (inet-string->address! "192.168.1.1" buf)))
  (list proto buf))
 @result{} (2 #u8(192 168 1 1 0 0 0 0 0 0 0 0 0 0 0 0))
@end example
@end defun


@defun inet-address->string address protocol
@c MOD gauche.net
@c EN
Converts the given @var{address} to its string representation
of the protocol @var{protocol}, which can be either
@code{2} (the constant @code{AF_INET}) or @code{10}
(the constant @code{AF_INET6}).
An integer or a u8vector can be used as @var{address}.  If it is
a u8vector, only the necessary portion of the vector is read; i.e.
the vector can be longer than the required length.
@c JP
与えれれた@var{address}をプロトコル@var{protocol}の文字列表現に変換し
ます。プロトコルとしては@code{2} (定数@code{AF_INET})または@code{10}
(定数@code{AF_INET6})が指定可能です。@var{address}としては整数または
u8vectorが使えます。u8vectorをつかった場合には必要な部分だけが読み込ま
れます。したがって、必要な長さ以上あるベクタでもかまいません。
@c COMMON

@example
(inet-address->string 3232235777 AF_INET)
  @result{} "192.168.1.1"

(inet-address->string '#u8(192 168 1 1) AF_INET)
  @result{} "192.168.1.1"

(inet-address->string 3232235777 AF_INET6)
  @result{} "::c0a8:101"
@end example
@end defun


@node High-level network functions, Low-level socket interface, Socket address, Networking
@subsection High-level network functions
@c NODE 高レベルネットワーク手続き

@deftp {Builtin Class} <socket>
@clindex socket
@c MOD gauche.net
@c EN
Abstracts a socket, a communication endpoint.

For a connection-oriented socket, you can access the communication
channel by two ports associated to the socket, one for input and
another for output.  @code{socket-input-port} and @code{socket-output-port}
returns those ports, respectively.
@c JP
通信の終端であるところのソケットを表すクラスです。

コネクション型のソケットには、入力用と出力用の2つのポートが結び付いており、
それらを使って通信路にアクセスできます。
@code{socket-input-port}と@code{socket-output-port}はそれぞれ
入力用、出力用のポートを返します。
@c COMMON

@c EN
The @code{<socket>} class implements @code{<connection>} interface.
@xref{Connection framework}, for the details.
The @code{connection-self-address}
and @code{connection-peer-address} methods return
a socket address object.
@c JP
@code{<socket>}クラスはまた、@code{<connection>}インタフェースを実装しています
(詳しくは@ref{Connection framework}参照)。
@code{connection-self-address}と@code{connection-peer-address}は
ソケットアドレスオブジェクトを返します。
@c COMMON
@end deftp

@c EN
The following three functions are convenient ways to create
a connection-oriented socket.  Those functions
are to provide an easy methods for typical cases,
but have less control.  If you need more than these functions
provide, use low-level interface.
@c JP
以下の3つは手軽にコネクション型のソケットを作成する
ための手続きです。 大抵の場合はこれらの手続きで間に合いますが、
より細かい制御が必要な場合は低レベルAPIを使用して下さい。
@c COMMON

@defun make-client-socket :optional address-spec @dots{}
@c MOD gauche.net
@c EN
Creates and returns a client socket, connected to the address
specified by @var{address-spec} @dots{}.
@c JP
引数@var{address-spec} @dots{}によって指定されるアドレスと接続する
クライアントソケットを作成して返します。
@c COMMON

@table @code
@item (make-client-socket 'unix @var{path})
@c EN
The client socket is connected to the unix domain server socket
of address @var{path}.
@c JP
@var{path}で待っているUnixドメインのサーバーソケットに接続します。
@c COMMON
@item (make-client-socket 'inet @var{host} @var{port})
@c EN
The client socket is connected to the inet domain server socket
with hostname @var{host} and port @var{port}.   TCP protocol is
assumed.   @var{host} can be either a hostname, or
a dotted decimal notation of IPv4 address.
If gauche is compiled with --enable-ipv6, IPv6 address notation
can also be used.  @var{Port} must be an exact integer specifying
a port number, or a string service name (e.g. @code{"http"}).

If gauche is compiled with --enable-ipv6, and the hostname is given,
and the hostname has both IPv6 and IPv4 addresses, then
IPv6 connection is tried first, and IPv4 is used when IPv6 fails.
@c JP
ホスト@var{host}のポート@var{port}にTCPで接続します。
@var{host}はIPv4アドレスのドット表記でもホスト名でも
構いません。Gaucheが--enable-ipv6でコンパイルされていれば、
IPv6形式のアドレス表記も受け付けます。
@var{port}はポート番号を指定する正確な整数か、文字列のサービス名
(@code{"http"}等)でなければなりません。

Gaucheが--enable-ipv6でコンパイルされており、ホスト名が渡されて、
そのホスト名がIPv6とIPv4の両方のアドレスを持っていた場合は、
最初にIPv6での接続が試みられ、それが失敗した場合にIPv4での接続が試みられます。
@c COMMON
@item (make-client-socket @var{host} @var{port})
@c EN
This works the same as above.  This form is for compatibility with STk.
@c JP
上と同じです。この形式はSTkとの互換性のために提供されています。
@c COMMON
@item (make-client-socket @var{sockaddr})
@c EN
If an instance of @code{<sockaddr>} is passed,
a socket suitable for @var{sockaddr} is opened and then connected
to the given address.
@c JP
@code{<sockaddr>}クラスのインスタンスが渡された場合には、それに対応する
ソケットをオープンし、そのアドレスへ接続します。
@c COMMON
@end table

@c EN
This function raises an error if it cannot create a socket,
or cannot connect to the specified address.
@c JP
ソケットを作成できなかったり、指定されたアドレスに接続できなかった場合は
エラーが報告されます。
@c COMMON

@example
(make-client-socket 'inet "www.w3.com" 80)
  @result{} ;@r{a socket connected to www.w3.com, port 80}
(make-client-socket "127.0.0.1" 23)
  @result{} ;@r{a socket connected to localhost, port 23}
(make-client-socket 'unix "/tmp/.sock"
  @result{} ;@r{a socket connected to a unix domain socket "/tmp/.sock"}
@end example
@end defun

@defun make-server-socket :optional address-spec @dots{}
@c MOD gauche.net
@c EN
Creates and returns a server socket, listening the address
specified by @var{address-spec}.
@c JP
@var{address-spec}にて接続を待つサーバソケットを作成して返します。
@c COMMON

@table @code
@item (make-server-socket 'unix @var{path} [:backlog @var{num}])
@c EN
The socket is bound to a unix domain socket with a name @var{path}.
The keyword argument @var{backlog} is passed to @code{socket-listen}
to specify the maximum number of connection request the server can keep
before accepting them.  The default is 5.  If your server is very busy
and you see "connection refused" often, you might want to increase it.
@c JP
パス名@var{path}を持つUnixドメインソケットが作成されます。
キーワード引数@var{backlog}に渡された数値は@code{socket-listen}に渡され、
サーバが接続要求を貯めておくキューの最大長を指定します。
デフォルトは5です。多忙なサーバーで、"connection refused"が頻発する場合は
この数値を増やしてみて下さい。
@c COMMON
@item (make-server-socket 'inet @var{port} [:reuse-addr? @var{flag}] [:sock-init @var{proc}] [:backlog @var{num}])
@c EN
The socket is bound to an inet domain TCP socket, listening
port @var{port}, which must be a non-negative exact integer
or a string service name (e.g. @code{"http"}).
If @var{port} is zero, the system assigns one of available port numbers.
If a keyword argument @var{reuse-addr?} is given and true,
@code{SO_REUSEADDR} option is set to the socket before bound to
the port.  This allows the process to bind the server socket
immediately after other process releases the port.
@c JP
ポート@var{port}にて接続を待つInetドメインのTCPソケットが作成されます。
@var{port}は非負の正確な整数か、文字列のサービス名(@code{"http"}等)でなければなりません。
@var{port}が零の場合はシステムが適当なポート番号を割り当てます。
キーワード引数@var{reuse-addr?}に真の値が与えられた場合は、
ソケットに@code{SO_REUSEADDR}オプションがセットされます。
その場合、他のプロセスが解放したばかりの(TCP)ポートでも
エラーとならずに使うことができます。
@c COMMON

@c EN
Alternatively, you can pass a list of positive exact integers to @var{port}.
In that case, Gauche tries to bind each port in the list until it succeeds.
@c JP
あるいは、正の正確な整数のリストを@var{port}に渡すことも出来ます。
その場合、Gaucheは与えられたポート番号で順にbindを試し、成功したらそのソケットを返します。
@c COMMON

@c EN
If keyword argument @code{sock-init} is given, it should be a procedure
that takes two arguments, a created socket and the socket address.
The procedure is called just after the socket is created.  It is
useful to set some special socket options.
@c JP
キーワード引数@code{sock-init}が与えられた場合、@code{proc} が出来たての
ソケットとそのソケットアドレスを引数にして呼び出されます。
つまり、@code{proc} はそのような2つの引数を取る手続きでなければなりません。
ソケットに特殊なオプションを設定したいような場合に便利です。

@c EN
The keyword argument @var{backlog} is the same as in unix sockets;
see the description above.
@c JP
キーワード引数@var{backlog}はunixソケットと同じです。上の記述を参照して下さい。

@c COMMON
@item (make-server-socket @var{port} [:reuse-addr? @var{flag}] [:sock-init @var{proc}][:backlog @var{num}])
@c EN
This is a synonym to the above form (except @var{port} must be
an integer).  This form is backward-compatible
with STk's @code{make-server-socket}.
@c JP
これは、@var{port}が整数でなければならないことを除けば、
上の形式と同じ動作をします。STkの@code{make-server-socket}との
互換性のために提供されています。
@c COMMON
@item (make-server-socket @var{sockaddr} [:reuse-addr? @var{flag}][:sock-init @var{proc}][:backlog @var{num}])
@c EN
This form explicitly specifies the socket address to listen
by an instance of @code{<sockaddr>}.
@c JP
この形式は、listenするソケットアドレスを@code{<sockaddr>}のインスタンスで
明示的に指定します。
@c COMMON
@end table

@example
(make-server-socket 'inet 8080)
  @result{} #<socket (listen "0.0.0.0:8080")>
(make-server-socket 8080)
  @result{} #<socket (listen "0.0.0.0:8080")>
(make-server-socket 'inet 0)
  @result{} #<socket (listen "0.0.0.0:35628")>
(make-server-socket 'unix "/tmp/.sock")
  @result{} #<socket (listen "/tmp/.sock")>
@end example
@end defun

@defun make-server-sockets host port :key reuse-addr? sock-init
@c MOD gauche.net
@c EN
Creates one or more sockets that listen at @var{port}
on all available network interfaces of @var{host}.
You can specify a service name (such as "@code{http}") to
@var{port}, as well as an integer port number.
Returns a list of opened, bound and listened sockets.

This procedure is particularly useful when the host
has multiple protocol stacks, such as IPv4 and IPv6.
In that case, this procedure may return a list of IPv4 socket(s) and
IPv6 socket(s).
(On some OSes, single socket can listen both IPv4 and IPv6.  On
such platform, a list of single socket will be returned.)

The meaning of keyword arguments are the same as of @code{make-server-socket}.
@c JP
@var{host} が持つすべての利用可能なネットワークインタフェース上の
@var{port} で接続を待つソケットを生成し、それらのリストを返します。
@var{port} には数字のポート番号のほか、"@code{http}"などの
サービス名も指定できます。

この手続きは、ホストが複数のプロトコルスタック(IPv4とIPv6など)を
持つ場合に特に便利です。その場合、この手続きはIPv4用のソケットと
IPv6用のソケットのリストを返すかもしれません。
(OSによっては、一つのソケットでIPv4もIPv6も両方listenできるものが
あります。そういったOSでは単一のソケットのリストが返るでしょう。)

キーワード引数の意味は@code{make-server-socket}のと同じです。
@c COMMON

@c EN
You can pass 0 to @var{port}, just like @code{make-server-socket},
to let the system choose an available port number.  If pass 0 as
port and this procedure returns multiple sockets, it is guaranteed
that all the sockets share the same port number.
@c JP
@code{make-server-socket}と同様、@var{port}に0を渡すことで、
システムに空いているポートを自動的にアサインしてもらうことができます。
@var{port}に0を渡して複数のソケットが返される場合、それらのソケットは
同じポート番号を持つことが保証されます。
@c COMMON
@end defun

@c EN
Several accessors are available on the returned socket object.
@c JP
上記の手続きによって返されたソケットオブジェクトに対して、
以下のようなアクセサがあります。
@c COMMON

@defun socket-address socket
@c MOD gauche.net
@c EN
Returns a socket address associated with @var{socket}.
If no address has been associated to the socket, @code{#f} is returned.
@c JP
ソケット@var{socket}のソケットアドレスを返します。
ソケットにアドレスがまだバインドされていない場合は@code{#f}が返ります。
@c COMMON
@end defun

@defun socket-input-port socket :key (buffering :modest)
@defunx socket-output-port socket :key (buffering :line)
@c MOD gauche.net
@c EN
Returns an input and output port associated with @var{socket},
respectively.
@c JP
それぞれ、@var{socket}からデータを読みだす入力ポート、および
@var{socket}にデータを書き出す出力ポートを返します。
@c COMMON

@c EN
The keyword argument @var{buffering} specifies the buffering mode
of the port.  @xref{File ports}, for explanation of the
buffering mode.
@c JP
キーワード引数@var{buffering}はポートのバッファリングモードを
指定します。バッファリングモードの説明は@ref{File ports}にあります。
@c COMMON
@end defun

@defun socket-close socket
@c MOD gauche.net
@c EN
Closes @var{socket}.  All the ports associated to
@var{socket} are closed as well.
@c JP
ソケット@var{socket}をクローズします。@var{socket}の入出力ポートも
クローズされます。

@c EN
Note: as of release 0.7.2, this procedure does not shutdown
the connection.  It is because @var{socket} may be referenced
by forked process(es) and you might want to close it without
interfering the existing connection.   You can call
@code{socket-shutdown} to shutdown the connection explicitly.
@c JP
注意: リリース 0.7.2 より、この手続きは接続をシャットダウンしないように
なりました。その理由は、@var{socket} が fork した別プロセスから参照され
ている可能性があり、既存の接続を妨害することなくクローズしたい場合がある
からです。@code{socket-shutdown} を呼べば接続を明示的にシャットダウンできます。
@c COMMON
@end defun

@defun call-with-client-socket socket proc :key input-buffering output-buffering
@c MOD gauche.net
@c EN
@var{socket} must be a connected client socket.  @var{proc} is called
with two arguments, an input port that reads from the socket
and an output port that writes to the socket.
The socket is closed after @var{proc} returns or @var{proc}
raises an error.
@c JP
@var{socket}は接続されたクライアントソケットでなければなりません。
@var{proc}がソケットから読み出す入力ポートと、
ソケットに書き出す出力ポートを引数として呼ばれます。
@var{proc}が正常終了するか、エラーを投げた場合にソケットはクローズされます。
@c COMMON

@c EN
The keyword arguments @var{input-buffering} and @var{output-buffering}
are, if given, passed as the @var{buffering} keyword arguments
of @code{socket-input-port} and @code{socket-output-port}, respectively.
@c JP
キーワード引数@var{input-buffering}と@var{output-buffering}が与えられた場合、
それらはそれぞれ@code{socket-input-port}と@code{socket-output-port}の
@var{buffering}キーワード引数へと渡されます。
@c COMMON
@end defun

@c EN
This is an example of usage of high-level socket functions,
a very simple http client.
@c JP
これは高レベルソケット手続きを使った、非常に単純なhttpクライアントです。
@c COMMON

@example
#!/usr/bin/env gosh
(use gauche.net)

(define (usage)
  (display "Usage: swget url\n" (current-error-port))
  (exit 1))

;; Returns three values: host, port, and path.
(define (parse-url url)
  (rxmatch-let (rxmatch #/^http:\/\/([-A-Za-z\d.]+)(:(\d+))?(\/.*)?/ url)
      (#f host #f port path)
    (values host port path)))

(define (get url)
  (receive (host port path) (parse-url url)
    (call-with-client-socket
        (make-client-socket 'inet host (string->number (or port "80")))
      (lambda (in out)
        (format out "GET ~a HTTP/1.0\r\n" path)
        (format out "host: ~a\r\n\r\n" host)
        (flush out)
        (copy-port in (current-output-port))))))

(define (main args)
  (if (= (length args) 2)
      (get (cadr args))
      (usage))
  0)
@end example


@node Low-level socket interface, Netdb interface, High-level network functions, Networking
@subsection Low-level socket interface
@c NODE 低レベルソケットインタフェース

@c EN
These functions provide APIs similar to the system calls.
Those who are familiar to programming with socket APIs will
find these functions useful since you can have more detailed control over
the sockets.
@c JP
ここにある関数群はシステムコールと類似した API を提供します。
ソケット API プログラミングに慣れていれば、ソケットをより細かく
制御できるので、役に立つでしょう。
@c COMMON

@defun make-socket domain type :optional protocol
@c MOD gauche.net
@c EN
Returns a socket with specified parameters.
@c JP
パラメータで指定したソケットを返します。
@c COMMON
@end defun

@defvr {Constant} PF_UNIX
@defvrx {Constant} PF_INET
@defvrx {Constant} PF_INET6
@c MOD gauche.net
@c EN
These constants are bound to the system's constants
@code{PF_UNIX}, @code{PF_INET} and @code{PF_INET6}.
You can use those values for @var{domain} argument of @code{make-socket}.

(@code{PF_INET6} is defined only if the underlying operating
system supports IPv6.)
@c JP
これらの定数はそれぞれシステムが提供する@code{PF_UNIX}、@code{PF_INET}、
@code{PF_INET6}に束縛されています。
これらの値を@var{make-socket}の@var{domain}引数に使うことができます。

(@code{PF_INET6}はオペレーティングシステムがIPv6をサポートしている場合にのみ
定義されます。)
@c COMMON
@end defvr

@defvr {Constant} AF_UNIX
@defvrx {Constant} AF_INET
@defvrx {Constant} AF_INET6
@c MOD gauche.net
@c EN
These constants are bound to @code{AF_UNIX},
@code{AF_INET} and @code{AF_INET6}.

(@code{AF_INET6} is defined only if the underlying operating
system supports IPv6.)
@c JP
これらの定数はそれぞれ、@code{AF_UNIX}、@code{AF_INET}、@code{AF_INET6}
に束縛されています。

(@code{AF_INET6}はオペレーティングシステムがIPv6をサポートしている場合にのみ
定義されます。)
@c COMMON
@end defvr

@defvr {Constant} SOCK_STREAM
@defvrx {Constant} SOCK_DGRAM
@defvrx {Constant} SOCK_RAW
@c MOD gauche.net
@c EN
These constants are bound to @code{SOCK_STREAM}, @code{SOCK_DGRAM}
and @code{SOCK_RAW}, and suitable to pass to the @var{type} argument
of @code{make-socket}.
@c JP
これらの定数はそれぞれ、@code{SOCK_STREAM}、@code{SOCK_DGRAM}、
@code{SOCK_RAW} に束縛されており、
@var{make-socket}の@var{type}引数に使うことができます。
@c COMMON
@end defvr

@defun socket-fd socket
@c MOD gauche.net
@c EN
Returns an integer system file descriptor of the underlying socket.
@c JP
ソケットのもつ整数のシステムファイルディスクリプタを返します。
@c COMMON
@end defun


@defun socket-status socket
@c MOD gauche.net
@c EN
Returns a internal status of @var{socket}, by one of the following
symbols.
@multitable {aaaaaaaaaaaaaaaaa} {aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa}
@item none
@tab The socket is just created.
@item bound
@tab The socket is bound to an address by @code{socket-bind}
@item listening
@tab The socket is listening a connection by @code{socket-listen}
@item connected
@tab The socket is connected by @code{socket-connect} or @code{socket-accept}.
@item shutdown
@tab The socket is shutdown by @code{socket-shutdown}
@item closed
@tab The socket is closed by @code{socket-close}.
@end multitable
@c JP
@var{socket} の内部状態を、以下のシンボルのどれかで返します。
@multitable {aaaaaaaaaaaaaaaaa} {aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa}
@item none
@tab 生成直後
@item bound
@tab @code{socket-bind} によって、あるアドレスに束縛されている
@item listening
@tab @code{socket-listen} によって、接続をリッスンしている
@item connected
@tab @code{socket-connect} あるいは @code{socket-accept} によって接続されている
@item shutdown
@tab @code{socket-shutdown} によってシャットダウンされた
@item closed
@tab @code{socket-close} によってクローズされた
@end multitable
@c COMMON
@end defun

@defun socket-bind socket address
@c MOD gauche.net
@c EN
Binds @var{socket} to the local network address @var{address}.
It is usually used to associate specific address to the server port.
If binding failed, an error is signaled (most likely the address is
already in use).

For the inet domain address, you can pass @var{address} with port=0;
the system assigns the port number and sets the actual address to
the @code{address} slot of @var{socket}.
@c JP
@var{socket} をローカルネットワークアドレス @var{address} に束縛します。
通常は、特定のアドレスをこのサーバのポートに結びつけるのに用います。
もし、束縛が失敗したら(多くの場合、そのアドレスが既に使用されている)、
エラーシグナルが発生します。

INET ドメインアドレスの場合には port=0 とした @var{address} を
渡せます。システムがポート番号を割当て、@var{socket} の
@code{address} スロットに実際のアドレスをセットします。
@c COMMON
@end defun

@defun socket-listen socket backlog
@c MOD gauche.net
@c EN
Listens @var{socket}.  The socket must be already bound to some
address.  @var{backlog} specifies maximum number of connection
requests to be queued.
@c JP
@var{socket} をリッスンします。ソケットは既になんらかのアドレスに
束縛されていなければなりません。@var{backlog} はキューに入れる
接続要求の最大数を指定します。
@c COMMON
@end defun

@defun socket-accept socket
@c MOD gauche.net
@c EN
Accepts a connection request coming to @var{socket}.
Returns a new socket that is connected to the remote entity.
The original @var{socket} keeps waiting for further connections.
If there's no connection requests, this call waits for one to come.

You can use @code{sys-select} to check if there's a pending connection
request.
@c JP
@var{socket}に来た接続要求をアクセプトします。リモートエンティティへ
接続している新しいソケットを返します。元の @var{socket} は引き続き
次の接続要求を待ちます。接続要求がないとき、これの呼出しは要求が
一つ来るまで待ちます。

接続要求をペンディングしているかどうかをチェックするのに
@code{sys-select}が使えます。
@c COMMON
@end defun

@defun socket-connect socket address
@c MOD gauche.net
@c EN
Connects @var{socket} to the remote address @var{address}.
This is the way for a client socket to connect to the remote entity.
@c JP
@var{socket} をリモートアドレス @var{address} に接続します。
これは、クライアントソケットをリモートエンティティに接続するための
方法です。
@c COMMON
@end defun

@defun socket-shutdown socket how
@c MOD gauche.net
@c EN
Shuts down connection of @var{socket}.  If @var{how} is @code{SHUT_RD} (or 0),
the receive channel of @var{socket} is disallowed.
If @var{how} is @code{SHUT_WR} (or 1), the send channel of
@var{socket} is disallowed.
If @var{how} is @code{SHUT_RDWR} (or 2), both receive and send channels are
disallowed.  It is an error to call this function on a non-connected socket.

If you shut down the send channel of the socket, the remote peer
sees EOF from its receive channel.  This is useful if the remote peer
expects EOF before sending something back to you.
@c JP
@var{socket} の接続をシャットダウンします。@var{how} が@code{SHUT_RD} (0) なら、
@var{socket} の受信チャネルが不許可となります。@var{how} が@code{SHUT_WR} (1)なら、
@var{socket} の送信チャネルが不許可となります。@var{how} が@code{SHUT_RDWR} (2)なら、
@var{socket} の送受信チャネルの両方が不許可となります。
接続していないソケットに対して、この手続きを呼ぶとエラーになります。

ソケットの送信チャネルをシャットダウンすると、リモート側の受信チャネル
に EOF があらわれます。これは、リモート側が何かを送り返す前に EOF
を受けとることを期待している場合、便利です。
@c COMMON
@end defun

@defun socket-getsockname socket
@c MOD gauche.net
@c EN
Returns a @code{<sockaddr>} instance that is the local address of
@var{socket}.
@c JP
@var{socket}のローカル側アドレスを表す@code{<sockaddr>}インスタンスを返します。
@c COMMON
@end defun

@defun socket-getpeername socket
@c MOD gauche.net
@c EN
Returns a @code{<sockaddr>} instance that is the peer address of
@var{socket}.
@c JP
@var{socket}の通信相手のアドレスを表す@code{<sockaddr>}インスタンスを返します。
@c COMMON
@end defun

@defun socket-send socket msg :optional flags
@defunx socket-sendto socket msg to-address :optional flags.
@c MOD gauche.net
@c EN
Interfaces to @code{send(2)} and @code{sendto(2)}, respectively.
Transmits the content of @var{msg} through @var{socket}.
@var{msg} can be either a string or a uniform vector; if you send
binary packets, uniform vectors are recommended.

Returns the number of octets that are actually sent.

When @code{socket-send} is used, @var{socket} must already be connected.
On the other hand, @code{socket-sendto} can be used for non-connected
socket, and the destination address is specified by
a @code{<sockaddr>} instance @var{to-address}.
@c JP
それぞれ、@code{send(2)} および @code{sendto(2)} へのインタフェース。
@var{msg} の内容を @var{socket} を通じて送出します。
@var{msg}は文字列もしくはユニフォームベクタでなければなりません。
バイナリパケットを送る場合はユニフォームベクタの使用を推奨します。

実際に送出されたオクテット数を返します。

@code{socket-send} を使うときには、@var{socket} は既に接続されて
いなければなりません。他方、@code{socket-sendto} は未接続の
ソケットに対して使用でき、送出先アドレスは @code{<sockaddr>} のインスタンス
@var{to-address} で指定します。
@c COMMON

@c EN
The optional @var{flags} can be a bitwise OR of the integer
constants @code{MSG_*}.  See the system's manpage of @code{send(2)}
and @code{sendto(2)} for the details.
@c JP
オプション引数 @var{flags} は整数定数 @code{MSG_*} のビット毎のORで
指定できます。詳しくはシステムの man ページ @code{send(2)} および
@code{sendto(2)} を見て下さい。
@c COMMON
@end defun

@defun socket-sendmsg socket msghdr :optional flags
@c MOD gauche.net
@c EN
Sends a packet described by @var{msghdr} through @var{socket}
using @code{sendmsg(3)}.  The @var{msghdr} argument must be a
string or u8vector, and it must be prepared as a binary representation
of @code{struct msghdr}.  A reliable way to build a @var{msghdr} is
to use @code{socket-buildmsg} described below.

The @var{flags} argument is the same as @code{socket-send} and
@code{socket-sendto}.

Returns number of octets sent.
@c JP
@code{sendmsg(3)}を使って、@var{msghdr}で記述されるパケットを@var{socket}
を通じて送ります。@var{msghdr}引数は文字列かu8vectorで、
@code{struct msghdr}構造体のバイナリ表現でなければなりません。
@var{msghdr}引数に適したデータを構築する確かな方法は、下に述べる
@code{socket-buildmsg}を使うことです。

@var{flags}引数は@code{socket-send}および@code{socket-sendto}と同じです。

送り出されたオクテット数を返します。
@c COMMON

@c EN
This procedure is not yet supported under the Windows native platform.
You can use the feature identifier @code{gauche.os.windows} to check
availability of this procedure (@pxref{Platform-dependent features}).
@c JP
この手続きはWindowsネイティブ環境では(まだ)サポートされません。
これが使えるかどうかは、機能識別子@code{gauche.os.windows}を使って判定
できます (@ref{Platform-dependent features}参照)。
@c COMMON
@end defun

@defun socket-buildmsg addr iov control flags :optional buf
@c MOD gauche.net
@c EN
Builds a binary representation of @code{struct msghdr} which is
suitable to be given to @code{socket-sendmsg}.
You have to be familiar with @code{sendmsg(3)} system call
to understand this procedure.

The @var{addr} argument must be an instance of @code{<sockaddr>}
or @code{#f}.  If it is a sockaddr, the @code{msg_name} field
of the msghdr is filled with the address.

The @var{iov} argument must be a vector or @code{#f}.  If it is
a vector, each element must be either a string or a u8vector.
They are used to fill @code{msg_iov} field of the msghdr.
Their contents will be concatenated in the kernel to make a payload.

The @var{control} argument represents ancillary data, a.k.a. cmsg.
It can be @code{#f} if you don't need ancillary data.  Otherwise,
it must be a list in the following form:
@example
((@var{level} @var{type} @var{data}) @dots{})
@end example
Where @var{level} and @var{type} are exact integers,
and @var{data} is either a string or a u8vector.
The former two are used to fill cmsg's @code{cmsg_level}
and @code{cmsg_type} fields.  The @var{data} is for
cmsg's data (@code{cmsg_len} is calculated from @var{data}).

The @var{flags} argument is used to fill @code{msg_flags}.

If the @var{buf} argument is @code{#f} or omitted, new memories
are allocated to construct the msghdr.  If a mutable
u8vector is given to @var{buf}, @code{socket-buildmsg} tries
to use it to construct the msghdr as much as possible; it allocates
memory only if @var{buf} is used up.

Returns the constructed msghdr as a u8vector.
@c JP
@code{struct msghdr}構造体のバイナリ表現を構築します。
作られたmsghdrは@code{socket-sendmsg}に渡すことができます。
この手続きを理解するには、@code{sendmsg(3)}の動作をよく知っていることが必要です。

@var{addr}引数は@code{<sockaddr>}のインスタンスか@code{#f}でなければ
なりません。@code{<sockaddr>}のインスタンスである場合、そのアドレスが
msghdrの@code{msg_name}フィールドに使われます。

@var{iov}引数はベクタか@code{#f}でなければなりません。ベクタの場合、
各要素は文字列かu8vectorでなければなりません。これはmsghdrの
@code{msg_iov}フィールドに使われます。各要素の内容はカーネル内で
結合されてペイロードとなります。

@var{control}引数は補助データ(cmsg)を指定します。補助データが必要ない
場合は@code{#f}を渡せます。そうでなければ、@var{control}引数は
次の形式を持つリストでなければなりません。
@example
((@var{level} @var{type} @var{data}) @dots{})
@end example
@var{level}と@var{type}は正確な整数で、@var{data}は文字列かu8vectorの
いずれかです。
最初の2つはそれぞれcmsgの@code{cmsg_level}と
@code{cmsg_type}フィールドを指定します。@var{data}はcmsgのデータとなります。
(@code{cmsg_len}は@var{data}から計算されます)。

@var{flags}引数は@code{msg_flags}フィールドに使われます。

@var{buf}引数が省略されるか@code{#f}の場合、msghdrを構築するのに
必要なメモリがアロケートされます。書き換え可能なu8vectorが@var{buf}
に渡されれば、@code{socket-buildmsg}はできるだけそれをバッファに使って
msghdrを構築しようとします。@var{buf}で領域が不足する場合のみ
新たなメモリをアロケートします。

この手続きは構築されたmsghdrをu8vectorとして返します。
@c COMMON

@c EN
This procedure is not yet supported under the Windows native platform.
You can use the feature identifier @code{gauche.os.windows} to check
availability of this procedure (@pxref{Platform-dependent features}).
@c JP
この手続きはWindowsネイティブ環境では(まだ)サポートされません。
これが使えるかどうかは、機能識別子@code{gauche.os.windows}を使って判定
できます (@ref{Platform-dependent features}参照)。
@c COMMON
@end defun

@defun socket-recv! socket buf :optional flags
@c MOD gauche.net
@c EN
Interface to @code{recv(2)}.  Receives a message from @var{socket},
and stores it into @var{buf}, which must be a mutable uniform vector.
Returns the number of bytes actually written.   @var{socket} must
be already connected.  If the size of @var{buf} isn't enough to
store the entire message, the rest may be discarded depending on
the type of @var{socket}.
@c JP
@code{recv(2)}へのインタフェースです。@var{socket}からメッセージを
受信し、それを変更可能なユニフォームベクタ@var{buf}へと書き込みます。
そして実際に書き込まれたバイト数を返します。
@var{socket}は既にコネクトされていなければなりません。
@var{buf}の大きさが受信したメッセージより小さい場合、@var{socket}の
タイプによっては残りのメッセージは捨てられる可能性があります。
@c COMMON

@c EN
The optional @var{flags} can be a bitwise OR of the integer
constants @code{MSG_*}.  See the system's manpage of @code{recv(2)}
for the details.
@c JP
オプション引数 @var{flags} は整数定数 @code{MSG_*} のビット毎のORで
指定できます。詳しくはシステムの man ページ @code{recv(2)}を見て下さい。
@c COMMON
@end defun

@defun socket-recvfrom! socket buf addrs :optional flags
@c MOD gauche.net
@c EN
Interface to @code{recvfrom(2)}.  Receives a message from
@var{socket}, which may be unconnected, and stores it to
a mutable uniform vector @var{buf}.  Like @var{socket-recv},
if the size of @var{buf} isn't enough to store the entire message,
the rest may be discarded depending on the type of @var{socket}.

Returns two values; the number of bytes actually written into
@var{buf}, and an instance of a subclass of @code{<sys-sockaddr>}
which shows the sender's address.

The @var{addrs} argument must be a list of instances of socket
addresses, optionally its last cdr being @code{#t} (as a special
case, if there's zero addresses to pass, just @code{#t} may be given).
The content of each address doesn't matter; if the protocol family
of one of them matches the sender's address, the sender's address
is written into the passed sockaddr object.  By listing sockaddrs
of possible families, you can count on @code{socket-recvfrom!}
to allocate no memory on successful operation.  It is useful if
you call @code{socket-recvfrom!} in a speed-sensitive inner loop.

If the sender's address family doesn't match any of the addresses
given to @var{addrs}, the behavior depends on whether the list is
terminated by @code{()} or @code{#t}.  If it is terminated by @code{()},
(i.e. @var{addrs} is a proper list), the sender's address is simply
discarded and @code{socket-recvfrom!} returns @code{#f} as the
second value.  If the list is terminated by @code{#t},
@code{socket-recvfrom!} allocates a fresh sockaddr object and
returns it as the second value.

Two simple cases: If you pass @code{()} to @var{addrs}, the sender's
address is always discarded, which is useful if @var{socket} is
connected (that is, you already know your sender's address).
If you pass @code{#t} to @var{addrs}, a new socket address
object is always allocated for the sender's address,
which is convenient if you don't mind memory allocation.
@c JP
@code{recvfrom(2)}へのインタフェースです。@var{socket}からメッセージを
受け取り、変更可能なユニフォームベクタへ書き込みます。@var{socket}は
コネクトされていなくても構いません。@code{socket-recv}と同様に、
@var{buf}の大きさがメッセージ全てを保持するのに十分でない場合、
@var{socket}のタイプによっては残りのメッセージは捨てられます。

ふたつの値を返します。実際に@var{buf}に書かれたバイト数と、
送信者のアドレスを示す@code{<sys-sockaddr>}のサブクラスのインスタンスです。

@var{addrs}引数はソケットアドレスインスタンスのリストでなければなりません。
ただし、リストの終端 (最後の@code{cdr}) は@code{#t}であっても許されます。
(この特殊な場合として、@var{addrs}引数にただ@code{#t}を渡すことも許されます)。
@var{addrs}引数に渡されたソケットアドレスの中身は何でも構いません。
送信者のアドレスファミリーに一致するソケットアドレスインスタンスが@var{addrs}
中にあった場合、@code{socket-recvfrom!}はそのインスタンスに直接
送信者のアドレスを書き込みます。受信し得る全てのアドレスファミリのソケットアドレスを
リストで渡しておけば、@code{socket-recvfrom!}が(成功時には)
メモリアロケーションを行わないことが保証されます。これは
速度が重要となるタイトなループ内で@code{socket-recvfrom!}を呼ぶ場合に
重要です。

送信者のアドレスファミリに一致するソケットアドレスがあたえられなかった場合、
@code{socket-recvfrom!}の振舞いは@var{addrs}のリスト終端の値によります。
@var{addrs}が@code{()}で終端されていた場合 (@var{addrs}が真性リストで
あった場合)、送信者のアドレスは捨てられ、@code{socket-recvfrom!}は
二番めの値として@code{#f}を返します。@var{addrs}が@code{#t}で終端
されていた場合、@code{socket-recvfrom!}は新たなソケットアドレス
インスタンスを作成して返します。

簡単な場合として次の二つがあります：@var{addrs}に@code{()}が渡された場合、
送信者のアドレスは常に捨てられます。@var{socket}がコネクトされていれば
送信者のアドレスは既にわかっているので、そういう場合に便利でしょう。
一方@var{addrs}に@code{#t}を渡せば、常に新しいソケットアドレスが
アロケートされて返されます。メモリアロケーションについて気にしなくても
良い場合は便利でしょう。
@c COMMON

@c EN
The optional @var{flags} can be a bitwise OR of the integer
constants @code{MSG_*}.  See the system's manpage of @code{recvfrom(2)}
for the details.
@c JP
オプション引数 @var{flags} は整数定数 @code{MSG_*} のビット毎のORで
指定できます。詳しくはシステムの man ページ @code{recvfrom(2)}を見て下さい。
@c COMMON
@end defun


@defun socket-recv socket bytes :optional flags
@defunx socket-recvfrom socket bytes :optional flags
@c MOD gauche.net
@c EN
Like @code{socket-recv!} and @code{socket-recvfrom!}, but
these returns the received message as a (possibly incomplete)
string, up to @var{bytes} size.  Additionally,
@code{socket-recvfrom} always allocates a socket address
object for the sender's address.
@c JP
@code{socket-recv!}や@code{socket-recvfrom!}と似ていますが、
受け取ったメッセージを(不完全かもしれない)文字列として返します。
@var{bytes}は受信する上限のバイト数を指定します。
@code{socket-recvfrom}はそれに加えて、送信者のアドレスのために
常に新たなソケットアドレスオブジェクトを生成します。
@c COMMON

@c EN
The use of these procedures are discouraged, since they
often returns incomplete strings for binary messages.
Using strings for binary data creates many pitfalls.
Uniform vectors (especially @code{u8vector}s) are for binary data.
(The reason these procedures return strings is merely historical.)
@c JP
これらの手続きの使用はお薦めしません。というのは、バイナリメッセージを
不完全な文字列の形で扱うことになりがちだからです。文字列で
バイナリメッセージを取り扱うことは多くの落とし穴を作ります。
バイナリデータを扱う場合はユニフォームベクタ (特に@code{u8vector})
を使うべきでしょう。
(これらの手続きが文字列を返すのは単に歴史的な理由によります)。
@c COMMON
@end defun

@defvar MSG_CTRUNC
@defvarx MSG_DONTROUTE
@defvarx MSG_EOR
@defvarx MSG_OOB
@defvarx MSG_PEEK
@defvarx MSG_TRUNC
@defvarx MSG_WAITALL
@c MOD gauche.net
@c EN
Pre-defined integer constants to be used as @var{flags} values
for @code{socket-send}, @code{socket-sendto}, @code{socket-recv}
and @code{socket-recvfrom}.   Some of these constants may not be
defined if the underlying operating system doesn't provide them.
@c JP
@code{socket-send}、@code{socket-sendto}、@code{socket-recv} および
@code{socket-recvfrom} の @var{flag} として使う定義済み整数定数。
これらの定数のいくつかは、基盤のＯＳが提供していなければ未定義に
なっています。
@c COMMON
@end defvar

@c EN
Further control over sockets and protocol layers is possible
by getsockopt/setsockopt interface, as described below.
@c JP
以下に解説する getsockopt/setsockopt インタフェースを使えば、
ソケットやプロトコルをさらに制御することができます。
@c COMMON

@defun socket-setsockopt socket level option value
@defunx socket-getsockopt socket level option rsize
@c MOD gauche.net
@c EN
These are the interface to setsockopt() and getsockopt() calls.
The interface is a bit clumsy, in order to allow full access to
those low-level calls.

@var{socket} must be a non-closed socket object.
@var{level} and @var{option} is an exact integer to specify
the level of protocol stack and the option you want to deal with.
There are several variables pre-bound to system constants listed below.

To set the socket option, you can pass either an exact integer or
a string to @var{value}.  If it is an integer, the value is passed
to setsockopt(2) as C @code{int} value.  If it is a string, the
byte sequence is passed as is.  The required type of value depends on
the option, and Gauche can't know if the value you passed is expected
by setsockopt(2); it is your responsibility to pass the correct values.

To get the socket option, you need to tell the maximum length of expected
result by @var{rsize} parameter, for Gauche doesn't know the amount
of data each option returns.
@code{socket-getsockopt} returns the option value as a byte string.
If you know the option value is an integer, you can pass 0 to @var{rsize};
in that case @code{socket-getsockopt} returns the value as an exact integer.

Note about the name: I tempted to name these function socket-@{set|get@}opt
or socket-@{set|get@}-option,
but I rather took the naming consistency.  Hence duplicated "sock"s.

@c JP
これらは、setsockopt() および getsockopt() を呼ぶための
インタフェースです。このインタフェースが少々ぎこちないのは、
低レベルの呼び出しすべてにアクセスできるようにしているためです。

@var{socket} および @var{option} は、処理する対象の
プロトコルスタックのレベルおよびオプションを指定する
正確な整数です。以下にリストアップしたシステム定数に束縛された
変数があります。

ソケットオプションを設定するには、@var{value} に正確な整数を渡す方法と
文字列を渡す方法があります。それが、整数なら、その値は、C の
@code{int} として setsockopt (2) に渡されます。文字列なら、バイト列が
そのまま渡されます。どの型の値が要求されるかは、オプションに依存します。
Gauche 側では渡された値が setsockopt (2) で期待された型であるかどうかは
知ることができません。正しい値が渡されるかどうかはプログラマの責任です。

ソケットオプションを知るには、結果として期待する最大の長さを @var{rsize}
を使って教える必要があります。Gauche 側は返されるそれぞれのオプションの
合計を知らないからです。
@code{socket-getsockopt} はオプションの値をバイト列として返します。
オプションの値が整数だと、わかっているなら @var{rsize} に0を渡すこと
ができます。その場合 @code{socket-getsockopt} は正確な整数として値を返します。

関数名に関する註: これらの関数の名前を socket-@{set|get@}opt あるいは
socket-@{set|get@}-option にしようかとも思いましたが、結局、命名の
一貫性をとることにしました。それで、"sock" が重複しています。
@c COMMON

@end defun

@c EN
The following predefined variables are provided.
Note that some of them are not available on all platforms.
See manpages @code{socket(7)}, @code{tcp(7)} or @code{ip(7)} of
your system to find out exact specification of those values.

For ``level'' argument:
@c JP
以下のような定義済みの変数が用意されています。
すべてのプラットフォームで利用できるわけではないものも含まれている
ことに注意してください。
これらの値の正確な使用は、お使いのシステムの man ページ @code{socket(7)}、
@code{tcp(7)} あるいは @code{ip(7)} を参照してください。

``level'' 引数
@c COMMON
@defvar SOL_SOCKET
@defvarx SOL_TCP
@defvarx SOL_IP
@c MOD gauche.net
@c EN
These variables are bound to @code{SOL_SOCKET}, @code{SOL_TCP} and
@code{SOL_IP}, respectively.
@c JP
これらの変数は、それぞれ、@code{SOL_SOCKET}、@code{SOL_TCP} および
@code{SOL_IP} に束縛されています。
@c COMMON
@end defvar

@c EN
For ``option'' argument:
@c JP
``option'' 引数
@c COMMON
@defvar SO_KEEPALIVE
@c MOD gauche.net
@c EN
Expects integer value.  If it is not zero, enables sending  of
keep-alive messages on connection-oriented sockets.
@c JP
整数が期待されています。0でなければ、コネクション指向ソケットに
キープアライブ(keep-alive)メッセージを送ることができます。
@c COMMON
@end defvar

@defvar SO_OOBINLINE
@c MOD gauche.net
@c EN
Expects integer value.  If it is not zero, out-of-band data is
directly placed into the receive data stream.  Otherwise
out-of-band  data  is  only passed when the
MSG_OOB flag is set during receiving.
@c JP
整数が期待されています。0でなければ、帯域外データは直接
受信データストリームに乗ります。さもなければ、帯域外データは、受信中に
MSG_OOBフラグが設定されてたときにのみ渡されます。
@c COMMON
@end defvar

@defvar SO_REUSEADDR
@c MOD gauche.net
@c EN
Expects integer value.  If it is not zero, @code{socket-bind}
allows to reuse local addresses, unless an active listening
socket bound to the address.
@c JP
整数が期待されています。0ではない場合、@code{socket-bind}は、
ローカル・アドレスが、アクティブソケットにリッスンされていない
場合にかぎり、そのアドレスを再利用することを許可されます。

@c COMMON
@end defvar

@defvar SO_TYPE
@c MOD gauche.net
@c EN
Gets the socket type as an integer (like @code{sock_stream}).
Can be only used with @code{socket-getsockopt}.
@c JP
ソケットの型(@code{sock_stream}など)を整数として取得します。
@code{socket-getsockopt}でのみ使用可能です。
@c COMMON
@end defvar

@defvar SO_BROADCAST
@c MOD gauche.net
@c EN
Expects integer value.  If it is not zero, datagram sockets
are allowed to send/receive broadcast packets.
@c JP
整数が期待されています。0でなければ、データグラムソケットは
ブロードキャストパケットを送受信することを許されます。
@c COMMON
@end defvar

@defvar SO_PRIORITY
@c MOD gauche.net
@c EN
Expects integer value, specifying the protocol-defined priority
for all packets to be sent on this socket.
@c JP
整数が期待されています。このソケットで送信されるすべてのパケットに
ついてプロトコル定義の優先順位を指定します。
@c COMMON
@end defvar

@defvar SO_ERROR
@c MOD gauche.net
@c EN
Gets and clears the pending socket error as an integer.
Can be only used with @code{socket-getsockopt}.
@c JP
保留状態のソケットエラー(整数値)を取得し、それをクリアします。
@code{socket-getsockopt}でのみ使用可能です。
@c COMMON
@end defvar


@defun inet-checksum packet size
@c MOD gauche.net
@c EN
Calculates one's complement of Internet Checksum (RFC1071) of the
@var{packet}, which must be given as a uniform vector.  First
@var{size} bytes of @var{packet} are used for calculation.
Returned value is in network byte order (big-endian).
It is an error if @var{size} is greater than the size of @var{packet}.

Note: The used algorithm assumes @var{packet} is not too big (< 64K).
@c JP
ユニフォームベクタで与えられる@var{packet}のインターネットチェックサム(RFC1071)
の1の補数を計算して返します。@var{packet}の最初の@var{size}バイトのみが
計算の対象となります。返される値はネットワークバイトオーダ (ビッグエンディアン)
です。@var{packet}より大きな値を@var{size}に指定するとエラーとなります。

註: 使われているアルゴリズムは、@var{packet}がそれほど大きくないこと (< 64K) を
仮定しています。
@c COMMON
@end defun


@node Netdb interface,  , Low-level socket interface, Networking
@subsection  Netdb interface
@c NODE Netdbインタフェース




@deftp {Builtin Class} <sys-hostent>
@clindex sys-hostent
@c MOD gauche.net
@c EN
A class of objects for network hosts.  Corresponding to
@code{struct hostent} in C.  The following slots are available read-only.
@c JP
このクラスはネットワークホストのオブジェクト用で、
C の @code{struct hostent}
に対応しています。以下のスロットは読み込み専用です。
@c COMMON

@defivar {<sys-hostent>} name
@c EN
The formal name of the host (string).
@c JP
ホストの正式名(文字列)
@c COMMON
@end defivar
@defivar {<sys-hostent>} aliases
@c EN
A list of alias names of the host (list of strings).
@c JP
ホストの別名リスト(文字列のリスト)
@c COMMON
@end defivar
@defivar {<sys-hostent>} addresses
@c EN
A list of addresses (list of strings).  Only ipv4 address is
supported currently.  Each address is represented by dotted decimal
notation.
@c JP
アドレスのリスト(文字列のリスト)。現時点では IPv4 のアドレスのみサポート
しています。それぞれのアドレスは、ドットつき十進記法で表記されています。
@c COMMON
@end defivar
@end deftp

@defun sys-gethostbyname name
@c MOD gauche.net
@c EN
Looks up a host named @var{name}.
If found, returns a @code{<sys-hostent>} object.
Otherwise, returns @code{#f}.
@c JP
@var{name}という名前のホストを探し、見つかれば、@code{<sys-hostent>}
オブジェクトを返します。見つからなければ、@code{#f} を返します。
@c COMMON
@example
(let ((host (sys-gethostbyname "www.w3c.org")))
  (list (slot-ref host 'name)
        (slot-ref host 'aliases)
        (slot-ref host 'addresses)))
  @result{} ("www.w3.org" ("www.w3c.org") ("18.29.1.34" "18.29.1.35"))
@end example
@end defun

@defun sys-gethostbyaddr addr proto
@c MOD gauche.net
@c EN
Looks up a host that has an address @var{addr} of protocol @var{proto}.
@var{addr} is a natural string representation of the address;
for ipv4, it is a dotted decimal notation.  @var{proto} is a
protocol number; only @code{AF_INET} is supported currently.
If the host is found, returns a @code{<sys-hostent>} object.
Otherwise, returns @code{#f}.
@c JP
@var{proto}というプロトコルの、@var{addr}というアドレスを持つホストを
探します。@var{addr}はアドレスの自然な文字列表現で、IPv4 については、
ドットつき十進記法です。@var{proto}はプロトコル番号で、現時点では
@code{AF_INET}のみサポートされています。ホストが見つかれば、
@code{<sys-hostent>}オブジェクトを返します。
見つからなければ、@code{#f} を返します。
@c COMMON
@example
(let ((host (sys-gethostbyaddr "127.0.0.1" AF_INET)))
  (list (slot-ref host 'name)
        (slot-ref host 'aliases)
        (slot-ref host 'addresses))
  @result{} ("localhost" ("localhost.localdomain") ("127.0.0.1"))
@end example
@end defun

@deftp {Builtin Class} <sys-servent>
@clindex sys-servent
@c MOD gauche.net
@c EN
An entry of the network service database.  Corresponding to
@code{struct servent} in C.  The following slots are available read-only.
@c JP
ネットワークサービスデータベースのエントリです。
C の @code{struct servent}に対応しています。
以下のスロットは読み込み専用です。
@c COMMON

@defivar {<sys-servent>} name
@c EN
The formal name of the service (string).
@c JP
サービスの正式名(文字列)
@c COMMON
@end defivar
@defivar {<sys-servent>} aliases
@c EN
A list of alias names of the service (list of strings).
@c JP
サービスの別名リスト(文字列のリスト)
@c COMMON
@end defivar
@defivar {<sys-servent>} port
@c EN
A port number registered for this service (exact integer).
@c JP
サービスに割り当てられたポート番号(正確な整数)
@c COMMON
@end defivar
@defivar {<sys-servent>} proto
@c EN
A protocol name for this service (string).
@c JP
このサービス用のプロトコル名(文字列)
@c COMMON
@end defivar
@end deftp

@defun sys-getservbyname name proto
@c MOD gauche.net
@c EN
Looks up the network service database with a service name @var{name} and
a protocol @var{proto}.  Both @var{name} and @var{proto} must be a string.
If a service is found, an instance of @code{<sys-servent>} is returned.
Otherwise, @code{#f} is returned.
@c JP
ネットワークサービスデータベースをサービス名 @var{name} および
プロトコル @var{proto} で検索します。@var{name} および @var{proto}
は文字列でなければなりません。サービスが見つかれば、@code{<sys-servent>}
のインスタンスを返します。見つからなければ、@code{#f} を返します。
@c COMMON
@example
(let ((serv (sys-getservbyname "http" "tcp")))
  (list (slot-ref serv 'name)
        (slot-ref serv 'aliases)
        (slot-ref serv 'port)
        (slot-ref serv 'proto)))
  @result{} ("http" () 80 "tcp")
@end example
@end defun

@defun sys-getservbyport port proto
@c MOD gauche.net
@c EN
Looks up the network service database with a service port @var{port} and
a protocol @var{proto}.  @var{port} must be an exact integer, and
@var{proto} must be a string.
If a service is found, an instance of @code{<sys-servent>} is returned.
Otherwise, @code{#f} is returned.
@c JP
ネットワークサービスデータベースをサービス名 @var{port} および
プロトコル @var{proto} で検索します。@var{port} は正確な整数でなければ
なりません。また、@var{proto} は文字列でなければなりません。
サービスが見つかれば、@code{<sys-servent>}
のインスタンスを返します。見つからなければ、@code{#f} を返します。
@c COMMON
@example
(let ((serv (sys-getservbyport 6000 "tcp")))
  (list (slot-ref serv 'name)
        (slot-ref serv 'aliases)
        (slot-ref serv 'port)
        (slot-ref serv 'proto)))
  @result{} ("x-server" () 6000 "tcp")
@end example
@end defun

@deftp {Builtin Class} <sys-protoent>
@clindex sys-protoent
@c MOD gauche.net
@c EN
An entry of the protocol database.   Corresponds to @code{struct protoent}
in C.   The following slots are available read-only.
@c JP
プロトコルデータベースのエントリです。C の @code{struct protoent}に
対応しています。以下のスロットは読み込み専用です。
@c COMMON

@defivar {<sys-servent>} name
@c EN
The formal name of the protocol (string).
@c JP
プロトコルの正式名(文字列)
@c COMMON
@end defivar
@defivar {<sys-servent>} aliases
@c EN
A list of alias names of the protocol (list of strings).
@c JP
プロトコルの別名のリスト(文字列のリスト)
@c COMMON
@end defivar
@defivar {<sys-servent>} proto
@c EN
A protocol number (exact integer).
@c JP
プロトコル番号(正確な整数)
@c COMMON
@end defivar
@end deftp

@defun sys-getprotobyname name
@c MOD gauche.net
@c EN
Looks up the network protocol database with a name @var{name},
which must be a string.
If a protocol is found, an instance of @code{<sys-protoent>} is returned.
Otherwise, @code{#f} is returned.
@c JP
名前 @var{name} でネットワークプロトコルデータベースを検索します。
名前 @var{name} は文字列でなければなりません。
プロトコルが見つかれば、@code{<sys-protoent>}
のインスタンスを返します。見つからなければ、@code{#f} を返します。
@c COMMON
@example
(let ((proto (sys-getprotobyname "icmp")))
  (list (slot-ref proto 'name)
        (slot-ref proto 'aliases)
        (slot-ref proto 'proto)))
  @result{} ("icmp" ("ICMP") 1)
@end example
@end defun

@defun sys-getprotobynumber number
@c MOD gauche.net
@c EN
Looks up the network protocol database with a protocol number @var{number},
which must be an exact integer.
If a protocol is found, an instance of @code{<sys-protoent>} is returned.
Otherwise, @code{#f} is returned.
@c JP
プロトコル番号 @var{number} でネットワークプロトコルデータベースを検索
する。プロトコル番号 @var{number} は正確な整数でなければなりません。
プロトコルが見つかれば、@code{<sys-protoent>}
のインスタンスを返します。見つからなければ、@code{#f} を返します。
@c COMMON
@example
(let ((proto (sys-getprotobynumber 17)))
  (list (slot-ref proto 'name)
        (slot-ref proto 'aliases)
        (slot-ref proto 'proto)))
  @result{} ("udp" ("UDP") 17)
@end example
@end defun

@deftp {Builtin Class} <sys-addrinfo>
@clindex sys-addrinfo
@c MOD gauche.net
@c EN
The new interface to keep address information.
Corresponds to @code{struct addrinfo} in C.
This is only available if gauche is configured with --enable-ipv6 option.
The following slots are provided.
@c JP
アドレス情報を保持する新しいインタフェースです。C の @code{struct addrinfo}
に対応しています。これは gauche が --enable-ipv6 オプションで設定され、
ビルドされた場合にのみ利用可能です。以下のスロットが提供されます。
@c COMMON

@defivar {<sys-addrinfo>} flags
@end defivar
@defivar {<sys-addrinfo>} family
@end defivar
@defivar {<sys-addrinfo>} socktype
@end defivar
@defivar {<sys-addrinfo>} protocol
@end defivar
@defivar {<sys-addrinfo>} addrlen
@end defivar
@defivar {<sys-addrinfo>} addr
@end defivar
@end deftp

@defun sys-getaddrinfo nodename servname hints
@c MOD gauche.net
@c EN
Returns a list of @code{<sys-addrinfo>} instances from the given @var{nodename},
@var{servname} and @var{hints}.
This is only available if gauche is compiled with --enable-ipv6 option.
@c JP
与えられた @var{nodename}、@var{servname} および @var{hints} から
@code{<sys-addrinfo>} のインスタンスのリストを返します。
これは gauche が --enable-ipv6 オプションで設定され、
ビルドされた場合にのみ利用可能です。
@c COMMON
@end defun

@defun sys-getnameinfo sockaddr :optional flags
@c MOD gauche.net
@c EN
Lookup host and service name of the given socket address,
and returns two strings for hostname and service.
@c JP
与えられたソケットアドレスのホスト名とサービス名を2つの文字列として返します。
@c COMMON

@example
(sys-getnameinfo (make <sockaddr-in> :host "127.0.0.1" :port 80))
 @result{} "localhost" @r{and} "http"
@end example
@end defun


@defun sys-ntohs integer
@defunx sys-ntohl integer
@defunx sys-htons integer
@defunx sys-htonl integer
@c MOD gauche.net
@c EN
Utility functions to convert 16bit (@code{s}) or 32bit (@code{l}) integers
between @emph{network} byte order (@code{n}) and @emph{host} byte order
(@code{h}).

Scheme API to the netdb interface calls those byte order conversion
functions internally, so you don't usually need them so much as in C
programs.  However, it may be useful when you're constructing or
analyzing binary packets.  See also @ref{Packing binary data} to handle
binary data.
@c JP
16bit (@code{s})もしくは32bit (@code{l}) の整数を
ネットワークバイト順 (@code{n}) とホストバイト順 (@code{h}) の間で
相互変換するユーティリティ関数です。

netdbインタフェースのScheme APIは必要な箇所ではこれらの関数を内部的に
呼んでいるので、Cでプログラミングしている時ほどこれらの関数を必要とする
ことはないでしょう。ただ、バイナリデータパケットを構築したり解析したり
する際は便利かもしれません。バイナリデータの扱いについては
@ref{Packing binary data}も参照して下さい。
@c COMMON
@end defun

@c ----------------------------------------------------------------------
@node Package metainformation, Parameters (legacy), Networking, Library modules - Gauche extensions
@section @code{gauche.package} - Package metainformation
@c NODE パッケージメタ情報, @code{gauche.package} - パッケージメタ情報

@deftp {Module} gauche.package
@mdindex gauche.package
@c EN
Gauche manages extra libraries and extension modules as @emph{packages}.
@c JP
Gaucheは外部のライブラリや拡張モジュールを@emph{パッケージ}として管理します。
@c COMMON

@c EN
Each package source tree has @file{package.scm} on top directory, which
contains @code{define-gauche-package} form that provides metainformation
about the package---the package name, version, author, dependencies, etc.
@c JP
各パッケージのソースツリーのトップディレクトリには@file{package.scm}が置かれていて、
その中では@code{define-gauche-package}フォームによってパッケージの
メタ情報が記されています。パッケージ名、バージョン、作者、依存関係等です。
@c COMMON

@c EN
When the package is installed, the standard installation process copies
that information, with additional information such as the version of
Gauche used to build the package, into @file{.packages} subdirectory
of the library installation path, with the name @file{PACKAGENAME.gpd},
where @code{PACKAGENAME} is the name of the package.
@c JP
パッケージのインストールに標準のインストール手順を使えば、
このメタ情報にパッケージをビルドしたGaucheのバージョン情報などが付け加えられ、
ライブラリインストールパスの@file{.packages}サブディレクトリの下に
@file{PACKAGENAME.gpd}という名前で保存されます。ここで
@code{PACKAGENAME}はパッケージの名前です。
@c COMMON

@c EN
We collectively call @file{package.scm} and @file{*.gpd} as
@emph{package description file}.
@c JP
@file{package.scm}と@file{*.gpd}ファイルを@emph{パッケージ記述ファイル}と
総称することにします。
@c COMMON

@c EN
This module provides utility procedures to read and write package
description files, and search installed @file{*.gpd} files.
@c JP
このモジュールはパッケージ記述ファイルの読み書きと、
インストールされたパッケージのパッケージ記述ファイルを探すユーティリティ手続きを
提供します。
@c COMMON
@end deftp

@subheading @file{package.scm}

@c EN
A package file, @file{package.scm}, must contain one package definition
in the following form.  It is not evaluated; it is read as a literal data.
@c JP
パッケージファイル@file{package.scm}は、
下に示すひとつのパッケージ定義を含みます。このフォームは評価されません。
単にリテラルデータとして読まれます。
@c COMMON

@c EN
Note that @file{package.scm} may be referenced directly from its
source repository.  Gauche packages are uniquely identified by
the repository URL, and its @file{package.scm} file is the
definite source of metainformation of the package.
@c JP
@file{package.scm}はソースリポジトリにあるものが直接参照されることもあります。
GaucheのパッケージはリポジトリURLによって一意に識別され、そのリポジトリにある
@file{package.scm}がメタ情報の一次ソースとして扱われます。
@c COMMON

@deffn {Package definition} define-gauche-package name key-value-list @dots{}
@c EN
Defines a package @var{name}. @var{Name} must be a symbol.
It is followed by a keyword-value list.  The following keywords are
recognized.
@c JP
パッケージ@var{name}を定義します。@var{name}はシンボルでなければなりません。
続くのはキーワード-値リストです。以下のキーワードが認識されます。
@c COMMON

@table @code
@item repository
@c EN
(string) A repository URL of the package.  This is used as a unique identifier of
the package when the package is published.
@c JP
(文字列) パッケージのソースリポジトリのURL。パッケージを公開する際には、
これがパッケージを一意に識別します。
@c COMMON
@item version
@c EN
(String) The version of the package, e.g. @code{"1.0"}.
@c JP
(文字列) パッケージのバージョン。例: @code{"1.0"}。
@c COMMON
@item stable-version
@c EN
(String) When the package is actively developed, and you want
to recommend the general user to use the stable version instead of the HEAD,
you can put that version here.  If this slot has a value,
it is used in the Gauche package listings page instead of the value
of @code{version} slot.
@c JP
(文字列) パッケージが活発に開発されていて、一般のユーザに対しては
HEADよりも安定したバージョンを使うことを勧めたい場合は、
そのバージョンをこのスロットに書いておくことができます。
このスロットが値を持つ場合、Gaucheのパッケージリストページでは
@code{version}スロットの値の代わりにこの値が表示されます。
@c COMMON
@item description
@c EN
(String) The description of the pacakge.  The first line (up to the
first newline character) should be the one-line summary of the package.
@c JP
(文字列) パッケージの説明。最初の行 (最初の改行文字まで) はパッケージの1行のサマリに
なっていなければなりません。
@c COMMON
@item require
@c EN
(List) A list of requirements.  Each requirement is
@code{(<package-name> <version-spec>)}, where @code{<package-name>}
is a string package name, and @code{<version-spec>} determines
the accepable versions of the package.  @xref{Comparing version numbers},
for the details of @code{<version-spec>}.
@c JP
(リスト) 依存パッケージのリスト。各依存パッケージは、
@code{(<package-name> <version-spec>)}と記述されます。
ここで@code{<package-name>}は文字列のパッケージ名、
@code{<version-spec>}はパッケージの必要なバージョン範囲を示します。
@code{<version-spec>}については@ref{Comparing version numbers}を参照してください。
@c COMMON
@item providing-modules
@c EN
(List) A list of module names in symbols, that this package provides.
@c JP
(リスト) このパッケージが提供するモジュール名(シンボル)のリストです。
@c COMMON
@item authors
@c EN
(List) A list of name and contact info of the authors of this package.
@c JP
(リスト) このパッケージの作者名とコンタクト情報のリストです。
@c COMMON
@item maintainers
@c EN
(List) A list of name and contact info of the maintainers of this package,
if they differ from the @code{authors}.
@c JP
(リスト) このパッケージのメンテナの名前とコンタクト情報のリストです
作者とメンテナが別の場合のみ必要です。
@c COMMON
@item licenses
@c EN
(List) A list of licenses in strings.
@c JP
(リスト) ライセンス(文字列)のリストです。
@c COMMON
@item homepage
@c EN
(String) A homepage URL of the package, if any.
@c JP
(文字列) パッケージのホームページURL (もしあれば)。
@c COMMON
@item superseded-by
@c EN
(String) If the developers stop maintaining this package, but another developer
wants to continue development with a forked repository, the original
developer can officially appoint the successor by specifying
the new repository URL here.
@c JP
(文字列) もし開発者がこのパッケージの開発・メンテナンスをやめることにして、
他の開発者がフォークしたリポジトリで開発の継続を希望した場合、
元の開発者はここに新たなリポジトリのURLを指定することで、
正式にリポジトリの継承を示すことができます。
@c COMMON
@end table
@end deffn

@c EN
@subheading @code{configure} script and @code{*.gpd} file generation
@c JP
@subheading @code{configure}スクリプトと@code{*.gpd}ファイルの生成
@c COMMON

@c EN
If you use @code{configure} script based on @code{gauche.configure}
(@pxref{Generating build files}), a Gauche package description file
(@file{*.gpd}) is created with it.  The @code{gpd} file contains
information from @file{package.scm}, plus the information on the
installaion platform gathered by @code{configure}.
@c JP
@code{gauche.configure}を用いた@code{configure}スクリプトを使っている場合
Gaucheパッケージ記述ファイル(@file{*.gpd})はそれによって作成されます
(@pxref{Generating build files})。@code{gpd}ファイルは@file{package.scm}
の情報に加え、@code{configure}スクリプトが集めたインストール先プラットフォームについての
情報を保持しています。
@c COMMON

@c EN
The generated @code{gpd} file is installed with the package itself,
and will be used by @code{gauche-package} command, as well as
retrieved by the following utility APIs.
@c JP
生成された@code{gpd}ファイルはパッケージと一緒にインストールされ、
@code{gauche-package}コマンドで参照できます。
また、プログラム的に扱うためのユーティリティAPIが次のとおり用意されています。
@c COMMON

@c EN
@subheading Utility procedures
@c JP
@subheading ユーティリティ手続き
@c COMMON

@deftp {Class} <gauche-package-description>
@clindex gauche-package-description
@c MOD gauche.package
@c EN
An object to handle package descriptions programatically.
It has the following slots.
@c JP
プログラム的にパッケージ記述を扱うためのオブジェクトです。
以下のスロットを持ちます。
@c COMMON

@defivar {<gauche-package-description>} name
@c EN
The name of the package, a string.
@c JP
パッケージの名前 (文字列)。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} repository
@c EN
An URL to the repository of this package, a string.
A package is primarily identified by the repository URL.
@c JP
このパッケージのリポジトリURL(文字列)。
パッケージはリポジトリURLによってユニークに同定されます。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} version
@c EN
The version of the package, a string, e.g. @code{"1.0"}.
@c JP
パッケージのバージョン(文字列)。例:@code{"1.0"}。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} description
@c EN
The description of the package, a string.
Up to the first newline character may be used as a short summary.
@c JP
パッケージの説明 (文字列)。最初の改行文字までの1行がサマリとして扱われます。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} require
@c EN
A list of @code{(package-name version-spec)}, to specify
the other packages this package requires.
@c JP
@code{(package-name version-spec)}のリストで、
このパッケージが必要とする他のパッケージおよびそのバージョンを指定します。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} providing-modules
@c EN
A list of module names (symbols) that this package provides.
@c JP
このパッケージが提供するモジュール名(シンボル)のリスト。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} authors
@c EN
A list of author's name and contact info.
@c JP
作者の名前と連絡先のリスト。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} maintainers
@c EN
A list of maintainer's name and contact info, if it differs from
@code{authors}.
@c JP
パッケージメンテナが作者と異なる場合、メンテナの名前と連絡先のリスト。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} licenses
@c EN
A list of licenses.  E.g. @code{"BSD"},
@code{"MIT"}, @code{"GPL2"}, @code{"GPL3"}, @code{"Apache2"} etc.
@c JP
ライセンスのリスト。例: @code{"BSD"}、
@code{"MIT"}、@code{"GPL2"}、@code{"GPL3"}、@code{"Apache2"}等。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} homepage
@c EN
An URL to the homepage of this package, if any.
@c JP
このパッケージのホームページがあれば、そのURL。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} superseded-by
@c EN
If not @code{#f}, the value is a repository URL of the successor
of this package.
When development of a package is stopped and someone else
succeeded the further development, the original package specifies
the successor here to show the succession ``official''.
@c JP
@code{#f}でなければ、このパッケージを引き継いだパッケージのリポジトリURL。
パッケージの開発が停止し、他の誰かが将来の開発を引き継いだ場合、
元のパッケージはこのスロットで後継者を指定することで「正式に」継承を示すことができます。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} gauche-version
@c EN
Gauche version with which this module is installed.
@c JP
このモジュールがインストールされた時に使われたGaucheのバージョン。
@c COMMON
@end defivar

@defivar {<gauche-package-description>} configure
@c EN
A command-line string keeping how @code{configure} script was run
to build and install this package.
@c JP
このモジュールがビルド/インストールされた時に与えられた@code{configure}の
コマンドライン。
@c COMMON
@end defivar
@end deftp

@defun path->gauche-package-description filename
@c MOD gauche.package
@c EN
The named file must be a @code{gpd} file.  This reads the file
and returns an instance of @code{<gauche-package-description>}.

An error is thrown if @var{filename} can't be read, or doesn't
have a proper @code{define-gauche-package} form.
@c JP
@var{filename}は@code{gpd}ファイルでなければなりません。
この手続きはファイルをパーズし、@code{<gauche-package-description>}のインスタンスを
返します。

@var{filename}が読めなかったり、ファイルが正しい@code{define-gauche-package}フォームを
含んでいなかった場合はエラーが投げられます。
@c COMMON

@c EN
To find out installed @code{gpd} file(s), you can use
@code{find-gauche-package-description} below.
@c JP
インストール済みの@code{gpd}ファイルを見つけるには、
下の@code{find-gauche-package-description}が使えます。
@c COMMON
@end defun

@defun write-gauche-package-description description :optional oport
@c MOD gauche.package
@c EN
Write out the content of @code{<gauche-package-description>} instance,
@var{description} as a @code{define-gauche-package} form,
to an output port @var{oport}.  If @var{oport} is omitted,
current output port is used.
@c JP
@code{<gauche-package-description>}のインスタンスである
@var{description}の内容を、@code{define-gauche-package}形式として
出力ポート@var{oport}に書き出します。@var{oport}が省略された場合は
現在の出力ポートが使われます。
@c COMMON
@end defun

@defun make-gauche-package-description name :key version description require maintainers authors licenses homepage repository gauche-version configure providing-modules
@c MOD gauche.package
@c EN
Creates and returns a new instance of @code{<gauche-package-description>},
the slots of which is initialized with the given keyword arguments.
@c JP
@code{<gauche-package-description>}の新たなインスタンスを作って返します。
スロットは対応するキーワード引数によって初期化されます。
@c COMMON
@end defun

@defun gauche-package-description-paths :key all-versions
@c MOD gauche.package
@c EN
Gather all the @code{gpd} file paths installed in the standard location
on the system.  By default, it collects packages installed in
@code{(load-paths)}.  If you give a true value to @var{all-version},
it attempts to collect packages installed for other versions of
Gauche as well.
@c JP
システムの標準の場所にインストールされている全ての@var{gpd}ファイルのパスを
探し、そのリストを返します。
デフォルトでは@code{(load-paths)}にあるパスにインストールされたパッケージを探します。
@var{all-version}キーワード引数に真の値が指定された場合は、
それ以外のGaucheバージョン向けにインストールされたパッケージも探します。
@c COMMON
@end defun

@defun find-gauche-package-description name :key all-versions
@c MOD gauche.package
@c EN
Try to find a package description of @var{name} (string)
installed in the standard location,
and returns an instance of @code{<gauche-package-description>} if found.
Returns @code{#f} if the named package isn't found.
@c JP
名前@var{name} (文字列) を持つパッケージ記述を、標準的な場所にインストールされている
パッケージから探します。見つかればそのパッケージの
@code{<gauche-package-description>}インスタンスを、
見つからなければ@code{#f}を返します。
@c COMMON

@c EN
By default, it collects packages installed in
@code{(load-paths)}.  If you give a true value to @var{all-version},
it attempts to collect packages installed for other versions of
Gauche as well.
@c JP
デフォルトでは@code{(load-paths)}に含まれるディレクトリにインストールされた
パッケージから探します。@var{all-version}キーワード引数に真の値が与えられた
場合は、それに加えて他のGaucheバージョンのためにインストールされたパッケージも
探します。
@c COMMON
@end defun

@c ----------------------------------------------------------------------
@node Parameters (legacy), Parsing command-line options, Package metainformation, Library modules - Gauche extensions
@section @code{gauche.parameter} - Parameters (legacy)
@c NODE パラメータ(レガシー), @code{gauche.parameter} - パラメータ(レガシー)

@deftp {Module} gauche.parameter
@mdindex gauche.parameter
@c EN
This module is only provided for the backward compatibility.
@emph{We strongly discourage using this module}.

Parameters are now built-in, so you no longer need to @code{use} this
module for basic parameter functionalities.  However, they have
slightly different semantics from the legacy parameters Gauche had.
The parameters provided in this module is backward compatible, so that
you can run legacy code without changes.

When you use this module, those two identifiers are rebound
to the backward-compatibility API.

@table @code
@item make-parameter
This becomes an alias of @code{make-legacy-parameter}.
@item parameterize
This becomes an alias of @code{parameterize/dynwind}
@end table

@xref{Parameters and dynamic states}, for the details of
the difference.
@c JP
このモジュールは後方互換性のためだけに提供されています。
@emph{このモジュールを使うことはできるだけ避けてください。}

パラメータは組み込みになったので、パラメータの基本機能を使うだけなら
このモジュールを@code{use}する必要はありません。
ただ、組み込みのパラメータは従来のGaucheのパラメータと若干異なる動作をします。
このモジュールのパラメータは以前のものと互換なので、古いコードをそのまま
動かすことができます。

このモジュールをuseした場合、次の2つの識別子が互換性のあるものに再束縛されます。

@table @code
@item make-parameter
これは@code{make-legacy-parameter}の別名となります。
@item parameterize
これは@code{parameterize/dynwind}の別名となります。
@end table

新旧パラメータの違いについて詳しくは
@pxref{Parameters and dynamic states}を参照してください。
@c COMMON
@end deftp

@c EN
Legacy parameters also had a feature called @emph{observers}, a callback
procedure to be called when the parameter's value is modified.
You can add/delete observers by the following API.

Note that observers are only attachable to legacy parameters.
We plan to remove it eventually, so new code shouldn't use it.
@c JP
旧パラメータはまた、@emph{オブザーバ}という、パラメータの値が変わる時に
呼ばれるコールバックを登録することができました。下のAPIはそのためのものです。

オブザーバは旧パラメータのみに付加できます。
この機能はいずれ取り除く予定なので、新規コードでは使わないようにしてください。
@c COMMON

@defun parameter-observer-add! p proc :optional when where
@c MOD gauche.parameter
@c DEPRECATED
@c EN
Adds @var{proc} to "observer" procedures of a parameter @var{p}.
Observer procedures are called either (1) just before
a new value is set to the parameter, or (2) just after the new value
is set to the parameter.   In case of (1), a filter procedure is
already applied before a callback is called.
In either case, observer procedures are called with two arguments,
the old value and the new value.  The return value(s) of observer
procedures are discarded.
@c JP
@var{proc}をパラメータ@var{p}の``オブザーバ''手続きに追加します。
オブザーバ手続きは、(1)パラメータに新しい値がセットされる直前、
あるいは(2)パラメータに新しい値がセットされた直後、に呼ばれます。
(1)の場合、コールバックが呼ばれる前にフィルタ手続きがすでに適用
されています。どちらの場合も、オブザーバ手続きは、古い値と新しい
値の2引数を伴って呼ばれます。オブザーバ手続きの戻り値は無視されます。
@c COMMON

@c EN
The optional @var{when} argument must be either a symbol @code{before}
or @code{after}, to specify whether @var{proc} should be called
before or after the value is changed.   If omitted, @code{after} is
assumed.
@c JP
オプショナル引数@var{when}は、シンボル@code{before}か@code{after}の
いずれかでなければならず、値が変更された前と後のどちらで@var{proc}が
呼ばれるかを指定します。省略されると、@code{after}を指定したものと
されます。
@c COMMON

@c EN
The optional @var{where} argument must be either a symbol
@code{append} or @code{prepend}, to specify whether @var{proc} should
be prepended or appended to the existing observer procedure list.
If omitted, @code{append} is assumed.
@c JP
オプショナル引数@var{where}は、シンボル@code{append}か@code{prepend}の
いずれかでなければならず、@var{proc}が既存のオブザーバ手続きのリストの
前に追加されるか後に追加されるかを指定します。省略されると、@code{append}
を指定したものとされます。
@c COMMON

@c EN
@emph{Note}: Although the parameter value itself is thread-local,
the observer list is shared by all threads.
@c JP
@emph{注意}: パラメータの値自身がスレッドローカルであっても、
オブザーバのリストは全てのスレッドで共有されます。
@c COMMON
@end defun


@defun parameter-observer-delete! p proc :optional when
@c MOD gauche.parameter
@c DEPRECATED
@c EN
Deletes @var{proc} from observer procedure list of a parameter @var{p}.
If @var{proc} is not in the list, nothing happens.
You can give either a symbol @code{before} or @code{after} to
@var{when} argument to specify from which list @var{proc} should be
deleted.  If @var{when} argument is omitted, @var{proc} is deleted
from both lists.
@c JP
パラメータ@var{p}のオブザーバ手続きのリストから@var{proc}を削除します。
@var{proc}がリストになければ、何も起こりません。
@var{when}引数にシンボル@code{before}か@code{after}を与えて、
@var{proc}をどちらのリストから削除するかを指定することができます。
@var{when}引数が省略されると、@var{proc}は両方のリストから削除されます。
@c COMMON
@end defun

@defun parameter-pre-observers p
@defunx parameter-post-observers p
@c MOD gauche.parameter
@c DEPRECATED
@c EN
Returns a hook object (@pxref{Hooks}) that keeps
"before" or "after" observers, respectively.

@emph{Note}: Although the parameter value itself is thread-local,
these hook objects are shared by all threads.
@c JP
``before''か``after''オブザーバをそれぞれキープするフックオブジェクト
(@ref{Hooks}参照)を返します。

@emph{注意}: パラメータの値自身がスレッドローカルであっても、
オブザーバのリストは全てのスレッドで共有されます。
@c COMMON
@end defun


@c ----------------------------------------------------------------------
@node Parsing command-line options, Partial continuations, Parameters (legacy), Library modules - Gauche extensions
@section @code{gauche.parseopt} - Parsing command-line options
@c NODE コマンドライン引数の解析, @code{gauche.parseopt} - コマンドライン引数の解析

@deftp {Module} gauche.parseopt
@mdindex gauche.parseopt
@c EN
This module defines a convenient way to parse command-line options.
The interface is hinted by Perl, and conveniently handles long-format
options with multiple option arguments.

Actually, you have a few choices to parse command-line
options in Gauche.
SRFI-37 (@pxref{A program argument processor}) provides
functional interface to parse POSIX/GNU compatible argument syntax.
SLIB has @code{getopt}-compatible utility.
Required features may differ from application to application,
so choose whichever fits your requirement.
@c JP
このモジュールでは、コマンドラインオプションをパースするための便利な方法を定義
しています。インタフェースは Perl にヒントを受けたもので、複数のオプション引数を
伴う長い形式のオプションを便利に扱うことができます。

実際、Gauche でコマンドラインオプションをパースするにはいくつかの選択肢が
あります。SRFI-37 (@ref{A program argument processor}参照)では、
POSIX/GNU 互換の引数構文をパースするための関数的なインタフェースを提供しています。
SLIB は、@code{getopt} 互換のユーティリティを持っています。
要求される機能はアプリケーションごとに異なるので、
あなたの要求にフィットするものを選んで下さい。
@c COMMON
@end deftp

@c EN
@subheading High-level API
@c JP
@subheading 高レベルAPI
@c COMMON

@defmac let-args args (bind-spec @dots{} [. rest]) body @dots{}
@c MOD gauche.parseopt
@c EN
This macro captures the most common pattern of argument processing.
It takes a list of arguments, @var{args}, and scans it to find
Unix-style command-line options and binds their values to local
variables according to @var{bind-spec}, then executes @var{body} @dots{}.
@c JP
このマクロはコマンドライン引数処理の最も典型的なパターンを扱います。
引数のリスト@var{args}を取り、@var{bind-spec}で示される仕様をもとに
コマンドラインオプションを探してその値を変数に束縛し、それから
@var{body} @dots{}を実行します。
@c COMMON

@c EN
Let's look at a simple example first, which gives you a good idea of
what this form does. (See the ``Examples'' section below for more
examples).
@c JP
まず簡単な例を見てみましょう。このフォームが何をするか、だいたい想像できるのでは
ないかと思います。(より多くの例については下の``Examples''の項を参照して
ください)。
@c COMMON

@example
(define (main args)
  (let-args (cdr args)
      ((verbose     "v|verbose" ? "Run verbosely.")
       (outfile     "o|outfile=s@{FILE@}" ? "Write output to @{FILE@}.")
       (debug-level "d|debug-level=i@{LEVEL@}" 0 ? "Set debug level.")
       (help        "h|help" => (cut show-help (car args))
                    ? "Show help message and exit.")
       . restargs
      )
    ....))

(define (show-help progname)
  (print "Usage: ....")
  (print "Options:")
  (print (option-parser-help-string))
  (exit 0))
@end example

@c EN
The local variable @var{verbose} will be bound to @code{#t} if
a command-line argument @code{-v} or @code{--verbose} is given,
and to @code{#f} otherwise.
The variable @var{output} is specified to take one option argument;
if the command-line arguments are given like @code{-o out.txt},
@var{outfile} receives
@code{"out.txt"}.  The @var{debug-level} one is similar, but the
option argument is coerced to an integer, and also it has default
value 0 when the option isn't given.  The @var{help} clause
invokes an action rather than merely binding the value.
@c JP
ローカル変数@var{verbose}は、コマンドラインオプション@code{-v}や@code{--verbose}
が与えられれば@code{#t}に、そうでなければ@code{#f}に束縛されます。
変数@var{output}はオプション引数を取ると指定されており、例えば
@code{-o out.txt}のようにコマンドラインに指定されれば値@code{"out.txt"}が
束縛されます。@var{debug-level}も似ていますが、オプション引数は
整数へと変換され、またデフォルト値0が指定されています。
@var{help}節では、単に値を束縛するだけでなくアクションを起動しています。
@c COMMON

@c EN
(Note: Currently @code{let-args} does not distinguish so-called
short and long options, e.g. @code{-v} and @code{--v} have the same
effect, so as @code{-verbose} and @code{--verbose}.  In future we
may add an option to make it compatible with @code{getopt_long(3)}.)
@c JP
(註: 今のところ@code{let-args}は@code{-v}と@code{--v}を区別しません。
@code{-verbose}と@code{--verbose}も同様です。将来、@code{getopt_long(3)}と
互換になるオプションを追加するかもしれません。)
@c COMMON

@c EN
The string after @code{?} is used as a help string for the option.
You can get a formatted help string with
@code{option-parser-help-string}.
@c JP
@code{?}の後の文字列はオプションのヘルプ文字列です。
@code{option-parser-help-string}でフォーマットされたオプションのヘルプを
得ることができます。
@c COMMON

@c EN
The final @var{restargs} variable after the dot receives a list of
non-optional command-line arguments.
@c JP
最後のドットの後の@var{restargs}は、オプションでないコマンドライン引数のリストを
受け取ります。
@c COMMON

@c EN
Let's look at @var{bind-spec} in detail.
It must be one of the following forms.
@c JP
@var{bind-spec}について詳しく見てみましょう。
@var{bind-spec}は次のいずれかの形式でなければなりません。
@c COMMON

@example
1. (@var{var} @var{option-spec} [@var{default}] [? @var{helpstr}])
2. (@var{var} @var{option-spec} [@var{default}] => @var{callback} [? @var{helpstr}])

3. (else => @var{fallback})
4. (else @var{formals} @var{body} ...)
@end example

@c EN
A list of command-line arguments passed to @var{args} are parsed
according to @var{option-spec}s.  If the corresponding option
is given, the option's ``value'' is determined as follows:

@example
(a) If the @var{bind-spec} is 1., then
  (a1) If @var{option-spec} doesn't require an argument, then @code{#t}:
  (a2) If @var{option-spec} requires one argument, then the value of
       the argument:
  (a3) If @var{option-spec} requires more than one argument,
       the list of the values of the arguments.
(b) If the @var{bind-spec} is 2., then @var{callback} is called with
  the value(s) of arguments, and its return value.
@end example
@c JP
コマンドライン引数のリストが@var{args}に渡されると、それが
@var{option-spec}に基づいてパーズされます。該当するオプションが見付かれば、
オプションの「値」が次のとおり決定されます。

@example
(a) @var{bind-spec}の形式が上の1. の場合：
  (a1) @var{option-spec}が引数を要求しない場合は、@code{#t}。
  (a2) @var{option-spec}がひとつの引数を要求する場合は、その引数の値。
  (a3) @var{option-spec}がそれ以上の引数を要求する場合は、引数の値のリスト。
(b) @var{bind-spec}の形式が上の2.の場合、@var{callback}を引数の値を伴って呼び出し、その戻り値。
@end example
@c COMMON

@c EN
An option can be singular, meaning at most one appearance is effective,
or it can be plural, meaning multiple apperances are considered.
If an option is singular, @code{var} is bound to the value determined
as above.  If an option is plural, @var{var} is bound to the list of
above values from all occurrences.
@c JP
オプションには、「単数」、つまりたかだか一回までの指定が有効か、
「複数」、つまりコマンドラインに複数現れたらそれを全て考慮されるかがあります。
単数オプションでは、@var{var}は上で決定される値がそのまま束縛されます。
複数オプションでは、@var{var}は上で決定される値のリストが束縛されます。
@c COMMON

@c EN
We'll explain the details of @var{option-spec} later.
@c JP
@var{option-spec}の詳細については後で説明します。
@c COMMON

@c EN
As a special case, @var{var} can be @code{#f}, in which case
the value is ignored.  It is only useful for side effects in
@var{callback}.
@c JP
特別な場合として、@var{var}を@code{#f}とすることもできます。
その場合、値は無視されます。
@var{callback}での副作用だけに関心がある場合に使えるでしょう。
@c COMMON

@c EN
If the corresponding option is not given in @var{args},
@var{var} is bound to @var{default} if it is given,
@code{#f} otherwise.
@c JP
対応するオプションが@var{args}に与えられなかった場合、
@var{var}は@var{default}が与えられていればその値に、
そうでなければ@code{#f}に束縛されます。
@c COMMON

@c EN
The last @var{bind-spec} may be the form 3 or 4. in which case
the clause is selected when no other @var{option-spec} matches
a given command-line option.
In the form 3, @var{fallback} will be called with three arguments;
the given option, a list of remaining command-line arguments,
and a continuation procedure.  The @var{fallback}
is supposed to handle the given option, and it may call the
continuation procedure with the remaining arguments to continue
processing, or it may return a list of arguments which will
be treated as non-optional command-line arguments.
The form 4 is a shorthand notion of
@code{(else => (lambda @var{formals} @var{body} ...))}.
@c JP
最後の@var{bind-spec}には3か4の形式も許されます。
この節は、どの@var{option-spec}にもマッチしないコマンドラインオプションが
与えられた場合に選択されます。
3番目の形式では、@var{fallback}が3つの引数を伴って呼び出されます。
引数は、マッチしなかったコマンドラインオプション、
残りのコマンドライン引数、そして引数処理に戻るための継続手続きです。
@var{fallback}は与えられたコマンドラインオプションを処理した後、
オプション処理を続けたければ継続手続きに残りのコマンドライン引数を渡し、
オプション処理を打ちきりたければ残りのコマンドライン引数を戻り値として
返します。返された値は通常の(オプションでない)コマンドライン引数として扱われます。
4番目の形式は@code{(else => (lambda @var{formals} @var{body} ...))}の簡略表記です。
@c COMMON

@c EN
The @var{bind-spec} list can be an improper list, whose last cdr is
a symbol.  In which case, a list of the rest of the command-line arguments
is bound to the variable named by the symbol.
@c JP
束縛リストは、最後のcdrにシンボルを持つ不完全なリストであっても良く、
その場合はコマンドライン引数の残りのリストがその変数にと束縛されます。
@c COMMON

@c EN
Note that the @var{default}, @var{callback}, and forms in @code{else}
clause is evaluated outside of the scope of binding of @var{var}s
(as the name @code{let-args} implies).
@c JP
@var{default}、@var{callback}、@code{else}節のフォーム等は
@var{var}の束縛の外側のスコープで評価されることに注意して下さい。
@c COMMON

@c EN
Unlike typical @code{getopt} or @code{getopt_long} implementation in C,
@code{let-args} does not permute the given command-line arguments.
It stops parsing when it encounters a non-option argument (argument without
starting with a minus sign).
@c JP
C における典型的な @code{getopt} や @code{getopt_long} の実装とは異なり、
@code{let-args} は与えられたコマンドライン引数の順番を変えません。
オプションでない引数(ハイフンで始まらない引数)に遭遇した時点でパースを
中止します。
@c COMMON

@c EN
If the parser encounters an argument with only two minus signs `@code{--}',
it stops argument parsing and treats the rest of arguments as non-option
command-line arguments.
@c JP
パーサは、ハイフン2つのみの引数 `@code{--}' に遭遇すると、引数パーシングを
中止して`@code{--}' の後の引数リストをオプションでない引数リストとして扱います。
@c COMMON

@c EN
After all the bindings is done, @var{body} @dots{} are evaluated.
@var{Body} may began with internal define forms.
@c JP
全ての束縛が終了した後、@var{body} @dots{} が評価されます。
@var{body}は内部defineで始まっていても構いません。
@c COMMON

@c EN
Internally, @code{let-args} creates an ``option-parser'' object,
which is available within the dynamic extent of @code{let-args}
from the parameter @code{current-option-parser}.  See below.
@c JP
内部的に、@code{let-args}は「オプションパーザ」オブジェクトを作り、
それは@code{let-args}の動的エクステント中、@code{current-option-parser}パラメータで
取り出すことができます。下記参照。
@c COMMON

@end defmac

@deffn {Parameter} current-option-parser
@c MOD gauche.parseopt
@c EN
In the dynamic extent of @code{let-args}, this parameter
holds an option parser object that parses the command line
and stores the options' apparance and argument values.
It should be treated as an opaque object.   Its only public use
is to pass to @code{option-parser-help-string} to get a formatted
option help strings, which is done by default.
@c JP
@code{let-args}の動的エクステント中、
このパラメータは「オプションパーザ」オブジェクトに束縛されます。
オプションパーザはコマンドライン引数をパーズして、各オプションの出現および
引数の値を保持します。
このオブジェクトは不透明なオブジェクトとして扱われなければならず、
唯一の用途は@code{option-parser-help-string}に渡して
フォーマットされたオプションのヘルプ文字列を得ることです。
@c COMMON
@end deffn

@defun option-parser-help-string :key option-parser omit-options-without-help @
          option-indent description-indent width
@c MOD gauche.parseopt
@c EN
Returns a formatted help string of command-line option of an option parser
object @var{option-parser}.  Its default value is the value
of parameter @code{current-option-parser}, so if you invoke this
procedure in the dynamic extent of @code{let-args} to get
its help string, you don't need to pass the @var{option-parser}
argument explicitly.

With the example shown in the @code{let-args} above,
calling this procedure produces the following string:
@c JP
@var{option-parser}で指定されるオプションパーザの、コマンドラインオプション
ヘルプ文字列を返します。@var{option-parser}のデフォルト値は
パラメータ@code{current-option-parser}の値なので、
@code{let-args}で作られるオプションパーザのヘルプを
@code{let-args}の動的エクステント内で表示する場合は
@var{option-parser}引数を明示的に与える必要はありません。

上の@code{let-args}にあるコマンドラインオプション仕様の例では、
以下のようなヘルプ文字列が生成されます。
@c COMMON

@example
  -v, --verbose
               Run verbosely.
  -o, --outfile FILE
               Write output to FILE.
  -d, --debug-level LEVEL
               Set debug level.
  -h, --help   Show help message and exit.
@end example

@c EN
If the name of an option argument is given as surrounded by
curly braces in the option spec,
e.g. @code{"o|outfile=s@{FILE@}"}, the name is used
in the help message (see ``Option spec'' below).
Otherwise, the argument type character is
used.  In the help message, it is recommended to enclose the
reference to the option argument with curly braces.  Those braces
are simply removed in the help string.  However, in future, it
may be rendered differently if the output device has richer
presentation.
@c JP
オプション指定の中でオプション引数の名前がカーリーブレースで囲んで指定されて
いた場合は、その名前がヘルプ文字列に使われます
(例: @code{"o|outfile=s@{FILE@}"})。詳しくは下の「オプション指定」を
見てください。ヘルプメッセージ中でオプション引数の名前を参照する時にも、
その名前をカーリーブレースで囲んでおくことを推奨します。
今は単にそのカーリーブレースは除かれるだけですが、
将来、よりリッチな表現を許すデバイス向けにヘルプ文字列を生成する機会があれば、
別の表示が可能になるかもしれません。
@c COMMON

@c EN
If the @var{omit-options-without-help} keyword argument is true,
options without help string isn't included in the help string.
It is useful if you have an experimental options you don't want
to advertise for users.  The default is @code{#f}, which shows
@code{(No help available)} for such options.
@c JP
もし@var{omit-options-without-help}引数に真の値が与えられたら、
ヘルプ文字列が指定されていないオプションは返り値から除外されます。
実験的にオプションを追加して、でもユーザには広報したくない場合に便利です。
デフォルトは@code{#f}で、その場合、ヘルプ文字列が指定されていないオプションには
@code{(No help available)}と表示されます。
@c COMMON

@c EN
The arguments @var{option-indent}, @var{description-indent}, and
@var{width} controls the formatting.  Option names are
indented with @var{option-indent} characters, and their descriptions
are indented with @var{description-indent}.  The overall width
of text is governed by @var{width}.  The help string is formatted
with @code{text.fill} (@pxref{Text filling}).
@c JP
引数@var{option-indent}、@var{description-indent}、@var{width}は
ヘルプ文字列のフォーマットを制御します。各オプション名は
@var{option-indent}文字だけ、その記述は
@var{description-indent}文字だけインデントされ、
@var{width}が全体の幅を指定します。
ヘルプ文字列は@code{text.fill}の機能によってフォーマットされます
(@ref{Text filling}参照)。
@c COMMON
@end defun

@c EN
@subheading Option spec
@c JP
@subheading オプション指定
@c COMMON

@c EN
@var{option-spec} is a string literal that specifies the name of the option and
how the option takes the arguments.  An alphanumeric characters, underscore,
plus and minus sign is allowed for option's names, except that
minus sign can't be the first character, i.e. the valid option name
matches a regexp @code{#/[\w+][-\w+]*/}.
@c JP
@var{option-spec} は、オプションの名前とそのオプションがどのように引数を取るか
を指定する文字列リテラルです。オプションの名前には、アルファベット文字、数字、
アンダースコア、プラス記号、ハイフンが許されますが、ハイフンは最初の文字としては
使えません。すなわち、有効なオプションの名前は、@code{#/[\w+][-\w+]*/} という
正規表現にマッチするものです。
@c COMMON

@c EN
If the option takes argument(s), it can be specified by attaching
equal character and a character (or characters) that represents
the type of the argument(s) after the name.  The option
can take more than one arguments.
The following characters are recognized as a type specifier of
the option's argument.
@c JP
オプションが引数を取る場合、名前の後ろに等号文字と引数の型を表現する文字を
付けることで指定できます。オプションは一つ以上の引数を取ることができます。
以下の文字がオプションの引数の型を表現するものとして認識されます。
@c COMMON

@table @code
@item s
@c EN
String.
@c JP
文字列。
@c COMMON
@item n
@c EN
Number.
@c JP
数値。
@c COMMON
@item f
@c EN
Real number (coerced to flonum).
@c JP
実数 (flonumに変換されます)。
@c COMMON
@item i
@c EN
Exact integer.
@c JP
正確な整数。
@c COMMON
@item e
@c EN
S-expression.
@c JP
S式。
@c COMMON
@item y
@c EN
Symbol (argument is converted by @code{string->symbol}).
@c JP
シンボル (引数は@code{string->symbol}により変換される)。
@c COMMON
@end table

@c EN
Let's see some examples of @var{option-spec}:
@c JP
@var{option-spec}の例を見てみましょう：
@c COMMON

@table @code
@item "@var{name}"
@c EN
Specifies option @var{name}, that doesn't take any argument.
@c JP
引数を取らないオプションの @var{name} を指定します。
@c COMMON

@item "@var{name}=s"
@c EN
Option @var{name} takes one argument, and it is passed as a string.
@c JP
オプション @var{name} は引数を一つ取り、それは文字列として渡されます。
@c COMMON

@item "@var{name}=i"
@c EN
Option @var{name} takes one argument, and it is passed as an exact integer.
@c JP
オプション @var{name} は引数を一つ取り、それは正確整数として渡されます。
@c COMMON

@item "@var{name}=ss"
@c EN
Option @var{name} takes two arguments, both string.
@c JP
オプション @var{name} は引数を二つ取り、両方とも文字列です。
@c COMMON

@item "@var{name}=iii"
@c EN
Option @var{name} takes three integer arguments.
@c JP
オプション @var{name} は3つの整数の引数を取ります。
@c COMMON

@item "@var{name}=sf"
@c EN
Option @var{name} takes two arguments, the first is a string and the
second is a number.
@c JP
オプション @var{name} は2つの引数を取ります。一つ目は文字列で、
二つ目は数値です。
@c COMMON
@end table

@c EN
Each option argument letter can be follwed by an option argument
name, enclosed with curly braces.  Those names don't affect command-line
argument parsing, but are used to generate help string
(see @code{option-parser-help-string} above).
@c JP
各オプション引数文字の後に、カーリーブレースで囲んだオプション引数名を書いておくことが
できます。オプション引数名はコマンドライン引数のパーズには影響を与えませんが、
ヘルプ文字列を生成する時に使われます
(上の@code{option-parser-help-string}を参照)。
@c COMMON

@example
--file=s@{FILENAME@}
--origin=f@{XCOORD@}f@{YCOORD@}f@{ZCOORD@}
@end example

@c EN
If the option has alternative names, they can be concatenated by "|".
For example, an option spec @code{"h|help"} will match both
"h" and "help".
@c JP
オプションにいくつかの別名がある場合は、"|" でつなげて書いておくことができます。
例えば@code{"h|help"}という@var{option-spec}は
"h"にも"help"にもマッチします。
@c COMMON

@c EN
If an asterisk @code{*} is followed by the name(s) of the option,
the option is plural, that is, it can be specified multiple times and
you can get the values as a list.  For example, @code{I|incdir*=s} means
@code{-I} and @code{-incdir} option can appear more than once in
the command line, and its final value would be a list of string argument
given to all of the options.
@c JP
オプションの名前の後に@code{*}を置くと、オプションが複数であること、
つまり複数回指定できて、その値のリストを受け取れることを示します。
例えば@code{I|incdir*=s}という指定は、
@code{-I}や@code{-incdir}オプションがコマンドラインで複数回指定できて、
その最終的な値は与えられた文字列引数のリストになります。
@c COMMON

@c EN
In the command line, the option may appear with preceding
single or double minus signs.  The option's argument may be combined
by the option itself with an equal sign.  For example, all the following
command line arguments match an option spec @code{"prefix=s"}.
@c JP
コマンドラインでは、オプションは一つか二つのハイフンに続いて与えられます。
オプションの引数は、オプションそのものと等号記号でつながれていても構いません。
例えば、以下の全てのコマンドライン引数は、オプションの仕様、@code{"prefix=s"} に
マッチします。
@c COMMON
@example
-prefix /home/shiro
-prefix=/home/shiro
--prefix /home/shiro
--prefix=/home/shiro
@end example

@c EN
If the option consists of a single letter and takes arguments,
the first argument can follow immediately after the option letter
without a  whitespace.  If you have an option spec @code{"I=s"},
all the following command line arguments are recognized:
@c JP
オプションが一文字からなり、引数を取る場合、
最初の引数はスペースなしでオプション文字の直後に置かれても構いません。
例えばオプション仕様@code{"I=s"}は、以下のコマンドライン引数のいずれも認識します。
@c COMMON
@example
-I/foo
-I /foo
-I=/foo
--I/foo
--I /foo
--I=/foo
@end example

@c EN
If there's an ambiguity between a long option and a single-letter
option plus an argument, the long option takes precedence.
If you have an option spec @code{"long"} and @code{"l=s"}, command
line arguments @code{-long} is recognized as the former,
not @code{-l} option with arguments @code{ong}.
@c JP
長いオプション名と、一文字のオプション＋引数、の間で曖昧性が生じた場合は、
長いオプションの方が優先されます。例えば@code{"long"}および@code{"l=s"}という
オプション仕様があった場合、コマンドライン引数@code{-long}は
@code{-l}オプション＋引数@code{ong}@emph{ではなく}、ひとつのオプション@code{-long}と
解釈されます。
@c COMMON

@c EN
@subheading Error handling
@c JP
@subheading エラー処理
@c COMMON

@deftp {Condition Type} <parseopt-error>
@c MOD gauche.parseopt
@c EN
When @code{let-args} encounters an argument that cannot be
processed as specified by option specs, an error of condition type
@code{<parseopt-error>} is raised.   The cases include
when a mandatory option argument is missing, or when
an option argument has a wrong type.
@c JP
@code{let-args}が、@code{option-spec}に従わない引数を見つけた場合は、
コンディションタイプ@code{<parseopt-error>}のエラーを投げます。
例えば、必須のオプション引数が与えられていなかったり、異なる型であった
場合などです。
@c COMMON

@example
(let-args '("-a" "foo") ((a "a=i")) ; option a requires integer
  (list a))
 @result{} @r{parseopt-error}
@end example

@c EN
Note that this condition is about parsing the given @var{args}.
If an invalid @var{option-spec} is given,
an ordinary error is thrown.
@c JP
このコンディションはあくまで@var{args}に渡された引数をパーズする際に発生するものです。
@var{option-spec}が不正であった場合は通常のエラーが投げられます。
@c COMMON
@end deftp

@c EN
@subheading Examples
@c JP
@subheading 例
@c COMMON

@c EN
This example is taken from @code{gauche-install} script.
The @var{mode} option takes numbers in octal, so it
uses the callback procedure to convert it.
See also the @code{else} clause how to handle unrecognized option.
@c JP
これは@code{gauche-install}スクリプトから取った例です。
@var{mode}オプションは8進数のオプション引数を取るので、コールバック
手続きを使って変換しています。また、認識できないオプションをelse節で
処理しています。
@c COMMON

@example
(define (main args)
  (let-args (cdr args)
      ([mkdir   "d|directory"
                ? "Creates directories listed in the arguments. \
                   (3rd format only)."]
       [mode    "m|mode=s@{MODE@}" #o755 => (cut string->number <> 8)
                ? "Change mode of the installed file."]
       [owner   "o|owner=s@{OWNER@}"
                ? "Change owner of the installed file(s)."]
       [group   "g|group=s@{GROUP@}"
                ? "Change group of the installed file(s)."]
       [csfx    "C|canonical-suffix"
                ? "If installed file has a suffix *.sci, replace it for \
                   *.scm.   This is Gauche specific convention."]
       [srcdir  "S|srcdir=s@{DIR@}"
                ? "Look for files within @{DIR@}; useful if VPATH is used."]
       [target  "T|target=s@{DIR@}"
                ? "Installs files to the @{DIR@}, creating paths if needed. \
                   Partial path of files are preserved. (4th format only)."]
       [utarget "U|uninstall=s@{DIR@}"
                ? "Reverse of -T, e.g. removes files from its destination."]
       [shebang "shebang=s@{PATH@}"
                ? "Adds #!@{PATH@} before the file contents. \
                   Useful to install scripts."]
       [verb    "v|verbose" ? "Work verbosely"]
       [dry     "n|dry-run" ? "Just prints what actions to be done."]
       [sprefix "p|strip-prefix=s@{PREFIX@}"
                ? "Strip prefix dirs from FILEs before \
                  installation. (4th/5th format only)."]
       [#f      "h|help" => usage ? "Show this help message."]
       [#f      "c" ? "This option is ignored.  Recognized for the \
                       compatibility."]
       [else (opt . _) (print "Unknown option : " opt) (usage)]
       . args)
    ...)
  )
@end example

@c EN
The next example is a small test program to show the usage of
@code{else} clause.  It gathers all options into the variable @var{r},
except that when it sees @code{-c} it stops argument processing and
binds the rest of the arguments to @var{restargs}.
@c JP
次の例は@code{else}節の使い方を示す小さなプログラムです。
コマンドラインオプションを変数@var{r}に集めてゆきますが、
オプション @code{-c} に出会うとオプション処理を中止して残りを
@var{restargs}へと渡します。
@c COMMON

@example
(use gauche.parseopt)

(define (main args)
  (let1 r '()
    (let-args (cdr args)
      ((else (opt rest cont)
         (cond [(equal? opt "c") rest]
               [else (push! r opt) (cont rest)]))
       . restargs)
     (print "options: " r)
     (print "restargs: " restargs)
     0)))
@end example

@c EN
Sample session of the above script (suppose it is saved as @file{example}).
@c JP
上のスクリプトの実行例です (@file{example}というファイル名で保存されていると
します)。
@c COMMON

@example
$ ./example -a -b -c -d -e foo
options: (a b)
restargs: (-d -e foo)
$ ./example -a -b -d -e foo
options: (a b d e)
restargs: (foo)
@end example

@c EN
@subheading Low-level API
@c JP
@subheading 低レベルAPI
@c COMMON

@c EN
Internally, @code{let-args} creates an option parser object
and option spec objects which does the actual parsing work.
Those classes are internal, but a few procedures are exported
so that you can build your own parser.
@c JP
内部的に、@code{let-args}はオプションパーザオブジェクトと
オプション指定オブジェクトを作ってコマンドライン引数をパーズします。
これらのクラスの詳細は公開していませんが、それらを扱うためのいくつかの手続きが
提供されています。独自のパーザを作りたい時に便利です。
@c COMMON

@defun make-option-spec option-spec :key default callback help-string
@c MOD gauche.parseopt
@c EN
Parse a string @var{option-spec} (see ``Option spec'' above)
and returns an option spec object, which should
be treated as opaque.

The keyword arguments corresponds to the values in the @var{bind-spec}
of @code{let-args} form.
@c JP
@var{option-spec}にあるオプション指定文字列(上の「オプション指定」の項参照)を解析し、
オプション指定オブジェクトを作って返します。
オプション指定オブジェクトは不透明なオブジェクトとして扱ってください。

キーワード引数は@code{let-args}形式の@var{bind-spec}で指定するものに相当します。
@c COMMON
@end defun

@defun build-option-parser specs :key fallback
@c MOD gauche.parseopt
@c EN
Given a list of option spec objects creates and returns
an option parser object.  Each option spec object can be created
with @code{make-option-spec}.

The returned option parser object can be passed to
@code{run-option-parser} to handle the actual command-line argument list.

The optional @var{fallback} argument must be a procedure if provided.
See @code{run-option-parser}, for how and when it is called.
@c JP
オプション指定オブジェクトのリストを取り、オプションパーザオブジェクトを作って返します。
オプション指定オブジェクトは@code{make-option-spec}で作ることができます。

作られたオプションパーザオブジェクトは@code{run-option-parser}に渡して、
コマンドライン引数を処理するのに使えます。

省略可能な@var{fallback}引数は、渡す場合は手続きでなければなりません。
それがいつどのように呼ばれるかは@code{run-option-parser}を参照してください。
@c COMMON
@end defun

@defun run-option-parser option-parser args :optionap fallback
@c MOD gauche.parseopt
@c EN
Handle command-line argument list @var{args}, which must be a
list of string, with an option parser @var{option-parser}.
@c JP
文字列のリストで表されたコマンドライン引数のリスト@var{var}を、
オプションパーザオブジェクト@var{option-parser}によって処理します。
@c COMMON

@c EN
It handles the command-line options in @var{args} if any, and set up
each option's value in the option spec, then returns the rest of
the argument list.
@c JP
@var{args}の中にコマンドラインオプションが含まれていればそれを処理し、
その値を該当するオプション指定オブジェクトに保存します。
そしてオプションとその引数を取り除いた残りのコマンドライン引数リストを返します。
@c COMMON

@c EN
It looks for elements in @var{args} from left to right.  If it encounters
a string beginning with @code{-}, it thinks the string is a command-line
option and search option specs in @var{option-parser}.
Note that a string @code{--} marks the end of the option list; it is
consumed, and the remaining arguments are immediately returned.
@c JP
この手続きは、@var{args}の要素を順に見てゆきます。
引数が@code{-}で始まっていたら、それをコマンドラインオプションとみなし、
@var{option-parser}の持つオプション指定オブジェクトに該当するものを探します。
ただし、@code{--}だけの引数は特別で、コマンドラインオプションの終了とみなされ、
それ以降の引数リストが直ちに返されます。
@c COMMON

@c EN
If there's a matching option spec, the option itself and the option's
argument(s) (if the option takes ones) are taken out from @var{args}.
Then, the option's value is determined as follows.
@c JP
マッチするオプション指定があれば、オプションおよび(そのオプションが引数を取るなら)
オプション引数が@var{args}から除かれ、オプションの値が次のとおり決められます。
@c COMMON

@itemize @bullet
@item
@c EN
If the option spec has a handler, the handler is called with the option's
argument(s), and its return value becomes the option's value.
@c JP
オプション指定がハンドラを持っている場合は、オプション引数を引数にしてハンドラが呼ばれ、
その戻り値がオプションの値となります。
@c COMMON
@item
@c EN
Otherwise, if the option does not take an argument, @code{#t}.
@c JP
そうでなく、オプションが引数を取らない場合は、@code{#t}。
@c COMMON
@item
@c EN
Otherwise, if the option takes a single argument, the given argument itself.
@c JP
そうでなく、オプションが一つだけ引数を取る場合は、その与えられた引数。
@c COMMON
@item
@c EN
Otherwise, the list of arguments.
@c JP
そうでなければ、与えられた引数のリスト。
@c COMMON
@end itemize

@c EN
Furthermore, the option has plural flag, the final result of
the option's value is a list of all option values.
Otherwise, the option's value
is overwritten as the last value of the option.
@c JP
さらに、オプションが複数回指定可能な場合は、オプションの値がリストにまとめられます。
複数回指定不可の場合、最後の値が最終的なオプションの値となります。
@c COMMON

@c EN
If the given option-like string does not match any of the option specs,
a fallback procedure is called.  A fallback procedure can be given
by @var{fallback} optional argument, or the fallback argument
given to @code{build-option-parser}.  The fallback procedure is
called with three arguments: the unrecognized option string (without
preceding hyphen(s)), the argument list following it, and
a closure that takes an argument list to continue the parsing.
@c JP
オプションに見えるコマンドライン引数がオプション指定のいずれにもマッチしない場合、
fallback手続きが呼ばれます。fallback手続きは、省略可能な@var{fallback}引数に
与えられていればそれを、そうでなければ@code{build-option-parser}に与えられた
@var{fallback}が呼ばれます。fallback手続きは3つの引数を取ります:
認識されなかったオプション引数 (先行するハイフンを除いたもの)、
その後に続く引数リスト、そして、処理を続けるための継続手続きです。
@c COMMON

@c EN
The fallback procedure may process the unknown option as it pleases.
Whatever the fallback procedure returns becomes the return value
of @code{run-option-parser}.  If the fallback procedure wants to continue
processing the rest of the arugment list, tail call the third argument.
@c JP
fallback手続きは、好きなように未知のオプションを処理できます。
fallback手続きが返した値がそのまま@code{run-option-parser}の返り値となります。
もしfallback手続きが残りの引数リストに対してコマンドライン引数処理を継続したい場合は、
残りの引数リストを引数として継続手続きを末尾呼び出ししてください。
@c COMMON

@c EN
If no fallback argument is given to @code{run-option-parser} nor
@code{build-option-parser}, the default fallback procedure is called,
which throws ``unrecognized option'' @code{<parseopt-error>} error.
@c JP
@code{run-option-parser}にも@code{build-option-parser}にもfallback手続きが
与えられなかった場合はデフォルトの手続きが呼ばれます。それは
``unrecognized option''をメッセージとする@code{<parseopt-error>}エラーを
投げます。
@c COMMON
@end defun

@defun get-option-spec option-parser option-name
@c MOD gauche.parseopt
@c EN
Returns an option spec object that has the option name @var{option-name}
from @var{option-parser}.  After @code{run-option-parser},
you need to get an option spec to retrieve the option's value.

If no option spec matches @var{option-name}, @code{#f} is returned.
@c JP
@var{option-parser}の持つオプション指定オブジェクトから、@var{option-name}
にマッチするものを返します。@code{run-option-parser}を実行した後、
オプションの値を取り出すためにはオプション指定オブジェクトを得る必要があります。

@var{option-name}にマッチするオプション指定が無い場合は@code{#f}が返されます。
@c COMMON
@end defun

@defun option-spec-appeared? optspec
@c MOD gauche.parseopt
@c EN
Returns true if an option spec @var{optspec} has appeared
in the command-line argument list.  This must be called after
@code{run-option-parser}.
@c JP
オプション指定@var{optspec}で表されるオプションがコマンドライン引数に現れたかどうかを
真偽値で返します。これは@code{run-option-parser}呼び出しの後で呼ばなければなりません。
@c COMMON
@end defun

@defun option-spec-value optspec
@c MOD gauche.parseopt
@c EN
Returns the option's value of an option spec @var{optspec}.
This must be called after @code{run-option-parser}.
@c JP
オプション指定@var{optspec}の値を返します。
これは@code{run-option-parser}呼び出しの後で呼ばなければなりません。
@c COMMON

@c EN
The option's value is determined as follows.
@c JP
オプションの値は次のとおり決定されます。
@c COMMON

@itemize @bullet
@item
@c EN
If the option didn't appear in the command-line argument list,
the ``default'' value given to the @code{make-option-spec}.
@c JP
オプションがコマンドライン引数リストに現れなければ、
@code{make-option-spec}に与えたデフォルト値。
@c COMMON
@item
@c EN
If the option did appear in the comamnd-line argument list,
the value of each occurrence is determined as follows:
@c JP
オプションがコマンドライン引数リストに現れた場合は、
次のいずれか:
@c COMMON
@itemize @minus
@item
@c EN
If the option doesn't take an argument, @code{#t}.
@c JP
オプションが引数を取らない場合は@code{#t}。
@c COMMON
@item
@c EN
If the option takes one argument, the given argument.
@c JP
オプションが引数をひとつ取る場合は、与えられた引数。
@c COMMON
@item
@c EN
If the option takes multiple arguments, the list of the given arguments.
@c JP
オプションが複数の引数を取る場合は、与えられた引数のリスト。
@c COMMON
@end itemize
@c EN
Then, if the option is plural, all the value from occurrences
are gathered to a list in the order of appearance;
otherwise, the value form the last occurrence is kept.
@c JP
さらに、オプションが複数回指定可能な場合は、
全てのオプションの値がコマンドラインに出現した順でリストにまとめられます。
そうでない場合は、最後のオプションの値が保持されます。
@c COMMON
@end itemize
@end defun

@c EN
@subheading Deprecated API
@c JP
@subheading 非推奨API
@c COMMON

@c EN
The following macros are supersede by @code{let-args}.
New code should not use them.
@c JP
以下のマクロは@code{let-args}に置き換えられました。
新規コードでは使わないでください。
@c COMMON

@defmac parse-options args (option-clause @dots{})
@c MOD gauche.parseopt
@c DEPRECATED
@c EN
@var{args} is an expression that contains a list of command-line arguments.
This macro scans the command-line options (an argument that begins with
`@code{-}') and processes it as specified in @var{option-clause}s, then
returns the remaining arguments.
@c JP
@var{args} は、コマンドライン引数のリストを含む式です。
このマクロは、コマンドラインオプション(`@code{-}' で始まる引数)をスキャンし、
@var{option-clause} の指定に従って処理し、残りの引数を返します。
@c COMMON

@c EN
Each @var{option-clause} is consisted by a pair of @var{option-spec}
and its action.

If a given command-line option matches one of @var{option-spec}, then
the associated action is evaluated.  An action can be one of the
following forms.
@c JP
それぞれの @var{option-clause} は、@var{option-spec} とそのアクションのペアで
構成されます。

与えられたコマンドラインオプションが @var{option-spec} の一つにマッチすると、
関連付けられたアクションが評価されます。アクションは以下のフォームの一つです。
@c COMMON

@table @code
@item @var{bind-spec} @var{body} @dots{}
@c EN
@var{bind-spec} is a proper or dotted list of variables like lambda-list.
The option's arguments are bound to @var{bind-spec}, then
then @var{body} @dots{} is evaluated.
@c JP
@var{bind-spec} は、ラムダリストのような変数の正しいリストかドット対リストです。
オプションの引数は @var{bind-spec} に束縛され、@var{body} @dots{} が評価されます。
@c COMMON

@item => @var{proc}
@c EN
If a command-line option matches @var{option-spec}, calls a procedure
@var{proc} with a list of the option's arguments.
@c JP
コマンドラインオプションが @var{option-spec} にマッチすると、
@var{proc} がオプションの引数のリストとともに呼び出されます。
@c COMMON
@end table

@c EN
If a symbol @code{else} is at the position of @var{option-spec},
the clause is selected when no other option clause matches a given
command-line option.  Three ``arguments'' are associated to
the clause; the unmatched option, the rest of arguments, and
a procedure that represents the option parser.
@c JP
シンボル @code{else} が @var{option-spec} の位置にある場合、その節は、
与えられたコマンドラインオプションにマッチする他のオプション節が
ない場合に選択されます。その節には3つの``引数''が関連付けられます。
それらは、マッチしなかったオプション、引数の残り、オプションパーサを
表す手続きです。
@c COMMON

@end defmac

@defmac make-option-parser (option-clause @dots{})
@c MOD gauche.parseopt
@c DEPRECATED
@c EN
This is a lower-level interface.  @var{option-clause}s are the
same as @code{parse-options}.  This macro returns a procedure
that can be used later to parse the command line options.

The returned procedure takes one required argument and one
optional argument.  The required argument is a list of strings,
for given command-line arguments.  The optional argument may
be a procedure that takes more than three arguments, and if given,
the procedure is used as if it is the body of @code{else} option clause.
@c JP
これは低レベルのインタフェースです。@var{option-clause} は、
@code{parse-options} と同じです。このマクロは、コマンドラインオプションを
後でパースするために使うことができる手続きを返します。

返される手続きは、一つの必須の引数と一つのオプション引数を取ります。
必須の引数は、与えられたコマンドライン引数としての文字列のリストです。
オプションの引数は、三つ以上の引数を取る手続きで、それが与えられると
手続きはそれが @code{else} オプション節のボディであるかのように使われます。
@c COMMON
@end defmac

@c ----------------------------------------------------------------------
@node Partial continuations, High-level process interface, Parsing command-line options, Library modules - Gauche extensions
@section @code{gauche.partcont} - Partial continuations
@c NODE 部分継続, @code{gauche.partcont} - 部分継続

@deftp {Module} gauche.partcont
@mdindex gauche.partcont
@c EN
Gauche internally supports partial continuations
(a.k.a. delimited continuations) natively.
This module exposes the feature for general use.
@c JP
Gaucheは内部的に、部分継続(限定継続と呼ばれることもあります)を
ネイティブでサポートしています。このモジュールはその機能を
一般的に使えるように公開するものです。
@c COMMON
@end deftp

@c EN
Note:
Partial continuations use two operators, @code{reset} and @code{shift}.
Those names are introduced in the original papers, and stuck in the
programming world.  Unfortunately those names are too generic as
library function names.  We thought giving them more descriptive names,
but decided to keep them after all; when you talk about partial
continuations you can't get away from those names.  If these names
conflict to other names in your program, you can use @code{:prefix}
import specifier (@pxref{Using modules}), for example as follows:
@c JP
註: 部分継続はふたつのオペレータ、@code{reset}と@code{shift}を使います。
これらは元の論文で導入された名前ですが、既に用語として定着した感があります。
ライブラリ関数名としては一般的に過ぎる名前なので、よりわかりやすい名前を
つけようかとも考えたのですが、部分継続を話題にする際にはこれらの用語が
使われるのが普通なので、最終的にこの名前をキープすることにしました。
プログラム中で他の識別子とぶつかったり紛らわしい場合は、モジュールのimport
時に@code{:prefix}インポート指示子(@ref{Using modules}参照)を
次のように使うと良いでしょう。
@c COMMON

@example
;; Add prefix pc: to the 'reset' and 'shift' operators.
(use gauche.partcont :prefix pc:)

(pc:reset ... (pc:shift k ....) )
@end example

@defmac reset expr @dots{}
@c MOD gauche.partcont
@c EN
Saves the current continuation, and executes @var{expr} @dots{} with
a @emph{null continuation} or @emph{empty continuation}.
The @code{shift} operator captures the continuation from the @code{shift}
expression to this null continuation.
@c JP
現在の継続を保存し、@var{expr} @dots{} を@emph{空の継続}を伴って実行します。
空の継続は@code{shift}オペレータが捕捉する継続の終端になります。
@c COMMON

@c EN
Note on @emph{implicit delimited continuations}:
There's an occasion Gauche effectively calls @code{reset} internally:
When C routine calls back to Scheme in non-CPS manner.
(If you know C API, it is @code{Scm_EvalRec()}, @code{Scm_ApplyRec*()},
@code{Scm_Eval()} and @code{Scm_Apply()} family of functions.)  The callers
of such routines expect the result is returned at most once, which won't
work well with Scheme's continuations that have unlimited extent.
Such calls create delimited continuations implicitly.

For example, the @code{main} routine of @code{gosh} calls Scheme REPL by
@code{Scm_Eval()}, which means the entire REPL is effectively surrounded
by a @code{reset}.  So, if you call @code{shift} without corresponding
@code{reset}, the continuation of @code{shift} becomes the continuation
of the entire REPL---which is to exit from @code{gosh}.
This may be surprising if you don't know about the implicit delimited
continuation.

Other places the implicit delimited continuations are created
are the handlers virtual ports (@pxref{Virtual ports}),
@code{object-apply} methods called from @code{write} and @code{display},
and GUI callbacks such as the one registered by @code{glut-display-func}
(See the document of Gauche-gl for the details), to name a few.

In general you don't need to worry about it too much, since most
built-in and extension routines written in C calls back Scheme in CPS manner,
and works with both full and delimited continuations.
@c JP
@emph{暗黙の限定継続}について:
Gaucheは内部的に、@code{reset}相当の操作を行う場合があります。
CルーチンがSchemeを継続渡し形式でない方法で呼び出す場合です。
(C APIをご存知の方へ: @code{Scm_EvalRec()}, @code{Scm_Apply*Rec()},
@code{Scm_Eval()}、および@code{Scm_Apply()}が相当する関数です。)
これらの関数はCの呼び出し側へ、値をたかだか1度だけ返すことが期待されています。
Schemeの継続は無限エクステントを持ち、一度返ったルーチンから再び返ることが
あり得るため、こういったC関数とは相性が良くありません。
これらの関数を呼び出す時に、Gaucheは限定継続を自動的に作成します。

例えば、@code{gosh}の@code{main}関数はSchemeのREPLを
@code{Scm_Eval()}を通じて呼び出します。ということは、
REPL全体が@code{reset}で囲まれているということです。
従って@code{reset}の外側で@code{shift}を呼び出すと、その@code{shift}の
継続はREPL全体の継続と同じになります。すなわち、@code{gosh}が終了するということです。
暗黙の限定継続に気づかないと、この振る舞いにはびっくりするかもしれません。

他に暗黙の限定継続が作られる例をいくつかあげます。
仮想ポートのハンドラ (@ref{Virtual ports}参照)、
@code{write}や@code{display}から呼ばれる@code{object-apply}メソッド、
@code{glut-display-func}により登録されたGUIコールバック
(詳しくはGauche-glのマニュアル参照)などです。

そのような暗黙の限定継続を心配する必要は滅多にありません。Cで実装された
組み込み関数や拡張関数のほとんどは継続渡し形式でSchemeを呼んでいるため、
通常継続も限定継続も制限なく使うことができます。
@c COMMON
@end defmac

@defmac shift var expr @dots{}
@c MOD gauche.partcont
@c EN
Packages the continuation of this expression until the current null
continuation marked by the most recent @code{reset} into a procedure,
binds the procedure to @var{var}, then executes @var{expr} @dots{}
with the continuation saved by the most recent @code{reset}.
@c JP
この式からもっとも最近の@code{reset}により切り取られた空の継続までの継続を
手続きに包み、それを@var{var}に束縛します。
そしてもっとも近い@var{reset}式の継続を伴って@var{expr} @dots{}を実行します。
@c COMMON

@c EN
That is, after executing @var{expr} @dots{}, the value is passed
to the expression waiting for the value of the most recent @code{reset}.
When a partial continuation bound to @var{var} is executed, its
argument is passed to the continuation waiting for the value
of this @code{shift}.   When the execution of the partial continuation
reaches its end, it returns from the expression waiting
for the value of invocation of @var{var}.
@c JP
すなわち、@var{expr} @dots{}を実行後、その結果の値はもっとも最近の@code{reset}
の戻り値を待っている式に直ちに渡されます。
@var{var}に束縛されている部分継続が実行されると、それに渡された値は
@code{shift}の戻り値を待っている継続に直ちに渡されます。
その部分継続の実行が終了すると、その結果の値は@var{var}を呼び出した式の
戻り値となります。
@c COMMON
@end defmac

@defun call/pc proc
@c MOD gauche.partcont
@c EN
This is a wrapper of @code{shift}.  @code{(shift k expr @dots{})}
is equivalent to @code{(call/pc (lambda (k) expr @dots{}))}.
Sometimes this similarity of @code{call/cc} comes handy.
@c JP
これは@code{shift}のラッパーです。
@code{(shift k expr @dots{})}は@code{(call/pc (lambda (k) expr @dots{}))}
等価です。@code{call/cc}と似た形の呼び出し形式の方が便利な場合があるので
用意しました。
@c COMMON
@end defun

@c EN
Well, @dots{} I bet you feel like your brain is twisted hard
unless you are one of those rare breed from the land of continuation.
Let me break down what's happening here informally and intuitively.
@c JP
さてと… もしあなたが、継続の国の血を引く珍しい種族の一員でなければ、
たぶんここまで読んできて、脳みそがこんがらがっていることでしょう。
何が起きているか、厳密ではないが直感的な説明を試みてみます。
@c COMMON

@c EN
Suppose a procedure A calls an expression B.   If A expects a return
value from B and continue processing, we split the part after returning
from B into a separate chunk A', then we can think of the whole
control flow as this straight chain:
@c JP
手続きAが式Bを呼び出すとします。AがBの戻り値を受け取ってさらに計算を続ける場合、
Bが戻ってからの残りの計算部分をA'として分離することにすれば、全体の制御の流れは
次のように一本の鎖で表現できるでしょう。
@c COMMON

@example
A -> B -> A'
@end example

@c EN
@code{A -> B} is a procedure call and @code{B -> A'} is a return,
but we all know procedure call and return is intrinsically the
same thing, right?
@c JP
@code{A -> B}は手続き呼び出しで、@code{B -> A'}は手続きからのリターンですが、
手続き呼び出しとリターンは本質的には同じものでしたね。
@c COMMON

@c EN
Procedure B may call another procedure C, and so on.  So when
you look at an execution of particular piece of code, you can
think of a chain of control flow like this:
@c JP
Bはその中から別の手続きCをさらに呼び出しているかもしれません。
コードのある部分に着目した場合、そこにある制御の鎖を
次のようにイメージすることができるでしょう。
@c COMMON

@example
... -> A -> B -> C -> .... -> C' -> B' -> A' -> ...
@end example

@c EN
The magic procedure @code{call/cc} picks the head of the chain
following its execution (marked as @code{*} in the figure below),
and passes it to the given procedure (denoted @code{k} in the figure
below).
So, whenever @code{k} is invoked, the control goes through the
chain from @code{*}.
@c JP
魔法の手続き@code{call/cc}は、そのフォームの直後に来る鎖の先頭
(下の図で@code{*}で示されている部分)を取り上げて、それを
与えられた手続きに引数として渡すものです (下の図の@code{k})。
従って、@code{k}が呼び出されると、制御は直ちに@code{*}へとジャンプします。
@c COMMON

@example
... -> A -> B -> (call/cc -> (lambda (k) ... ) ) -> B' -> A' -> ...
                                      |             ^
                                      \-----------> *
@end example

@c EN
One difficulty with @code{call/cc} is that the extracted chain
is only one-ended---we don't know what is chained to the
right.  In fact, what will come after that depends
on the whole program; it's outside of local control.  This global
attribute of @code{call/cc} makes it difficult to deal with.
@c JP
@code{call/cc}で難しいのは、制御の鎖の片方しか取り出せないことです。
もう一方、鎖の右側がどこにつながっているのか、コードは知ることができません。
そもそも、鎖の右側に何が来るかは、プログラム全体を知らないとわからないのです。
この、グローバルな性質が、@code{call/cc}を扱い辛いものにしています。
@c COMMON

@c EN
The @code{reset} primitive @emph{cuts} this chain of
continuation.  The original chain of continuation (the @code{x}-end
in the following figure) is saved somewhere, and the continuation
of @code{reset} itself becomes open-ended (the @code{o}-end
in the following figure).
@c JP
@code{reset}プリミティブはこの継続の鎖を@emph{切断}します。
元の鎖 (下の図の@code{x}で示される端) は保存され、
@code{reset}式の継続自体は宙ぶらりんになります (下の図の@code{o}で示される端)。
@c COMMON

@example
... -> A -> B -> (reset ... ) -> o

                                 x -> B ' -> A' -> ...
@end example

@c EN
A rule: If control reaches to the @code{o}-end, we pick the
@code{x}-end @emph{most recently saved}.
Because of this, @code{reset} alone doesn't show any
difference in the program behavior.
@c JP
ここでひとつ規則を導入します。制御が@code{o}の端に達した場合、
直近に保存された@code{x}の端から制御を再開するとします。
従って、単に@code{reset}を挿入するだけでは、目に見える違いは生じません。
@c COMMON

@c EN
Now what happens if we insert @code{shift} inside @code{reset}?
This is a superficial view of inserting @code{shift} into
somewhere down the chain of reset:
@c JP
@code{reset}の中に@code{shift}を挿入したらどうなるでしょう。
resetの内部の鎖に@code{shift}を形式的に挿入してみるとこうなります。
@c COMMON

@example
... -> (reset -> X -> Y -> (shift k ... ) -> Y' -> X' ) -> o
@end example

@c EN
What actually happens is as follows.
@c JP
実際には次のような動作となります。
@c COMMON

@enumerate
@item
@c EN
@code{shift} packages @emph{the rest of the chain of work} until the
end of @code{reset}, and bind it to the variable @var{k}.
@c JP
@code{shift}は、@code{reset}の終端までの@emph{仕事の残りの部分}を取り出し、
それを変数@var{k}に束縛します。
@c COMMON
@item
@c EN
The continuation of @code{shift} becomes a null continuation as well,
so after @code{shift} returns, the control skips the rest of
operations until the corresponding @code{reset}.
@c JP
@code{shift}自身の継続は、空の継続となります。したがって@code{shift}から抜けると、
@code{shift}以降対応する@code{reset}までの操作はスキップされます。
@c COMMON
@end enumerate

@example
... -> (reset -> X -> Y -> (shift k ... ) ---------> ) -> o
                                  |
                                  \-------> Y' -> X' ) -> o
@end example

@c EN
In other words, when you consider the @code{reset} form as
one chunk of task, then @code{shift} in it
@emph{stashes away} the rest of the task and immediately
returns from the task.
@c JP
別の言い方をすれば、@code{reset}フォームをひとつの仕事の単位とすれば、
その中の@code{shift}は、その仕事の残りの部分を@emph{一時保存}して
仕事を中断して戻ってくるのです。
@c COMMON

@c EN
Let's see an example.  The @var{walker} argument in
the following example is a procedure that takes a procedure
and some kind of collection,
and applies the procedure to the each element in the collection.
We ignore the return value of @var{walker}.
@c JP
例を見てみます。次に示す@var{walker}引数は、
「手続きと何らかのコレクションを取り、手続きをコレクションの各要素に
適用してゆく」という手続きとします。
@var{walker}の戻り値は無視します。
@c COMMON

@example
(define (inv walker)
  (lambda (coll)
    (define (continue)
      (reset (walker (lambda (e) (shift k (set! continue k) e)) coll)
             (eof-object)))
    (lambda () (continue))))
@end example

@c EN
A typical example of @var{walker} is @code{for-each}, which takes
a list and applies the procedure to each element of the list.
If we pass @code{for-each} to @code{inv}, we get a procedure
that is inverted @emph{inside-out}.  What does that mean?
See the following session:
@c JP
@var{walker}の典型的な例は@code{for-each}です。手続きとリストを取り、
リストの各要素に手続きを適用するからです。
@code{for-each}を上の@code{inv}に渡すと、@code{for-each}を
@emph{裏返した}手続きが得られます。どういうことでしょう?
下のやりとりを見てみましょう。
@c COMMON

@example
gosh> (define inv-for-each (inv for-each))
inv-for-each
gosh> (define iter (inv-for-each '(1 2 3)))
iter
gosh> (iter)
1
gosh> (iter)
2
gosh> (iter)
3
gosh> (iter)
#<eof>
@end example

@c EN
When you pass a list to @code{inv-for-each}, you get an iterator
that returns each element in the list for each call.  That's because every
time @code{iter} is called, @code{shift} in @code{inv}
stashes away the task of @emph{walking the rest of the collection}
and set it to @code{continue}, then returns the current element @var{e}.
@c JP
リストを@code{inv-for-each}に渡すと、呼ばれる度にリストの各要素を順に返す
イテレータ手続きが得られます。というのも、@code{iter}が呼ばれる度に、
@code{inv}の中で作られた@code{shift}は@emph{リストの残りの部分をたどって行く}
という仕事の残りを@code{continue}に束縛して、現在の要素@var{e}を返すからです。
@c COMMON

@c EN
@var{walker} doesn't need to work just on list.  The following
function @code{for-each-leaf} traverses a tree and
apply @var{f} on each non-pair element.
@c JP
@var{walker}はリストを取る必要はありません。次に示す@code{for-each-leaf}は
木を取って、@var{f}をペアでない要素に適用してゆく手続きです。
@c COMMON

@example
(define (for-each-leaf f tree)
  (match tree
   [(x . y) (for-each-leaf f x) (for-each-leaf f y)]
   [x (f x)]))
@end example

@c EN
And you can inverse it just like @code{for-each}.
@c JP
これも@code{for-each}と同じように裏返すことができます。
@c COMMON

@example
gosh> (define iter2 ((inv for-each-leaf) '((1 . 2) . (3 . 4))))
iter2
gosh> (iter2)
1
gosh> (iter2)
2
gosh> (iter2)
3
gosh> (iter2)
4
gosh> (iter2)
#<eof>
@end example

@c EN
The @code{util.combinations} module (@pxref{Combination library})
provides a procedure that @emph{calls} a given procedure with
every permutation of the given collection.  If you pass
it to @code{inv}, you get a procedure that @emph{returns}
every permutation each time.
@c JP
@code{util.combinations}モジュール (@ref{Combination library}参照) には、
コレクションの全ての並べ替えに対して与えられた手続きを@emph{呼び出す}手続きがあります。
それを@code{inv}に渡せば、呼ばれる度に並べ替えを@emph{返す}手続きが得られます。
@c COMMON

@example
gosh> (define next ((inv permutations-for-each) '(a b c)))
next
gosh> (next)
(a b c)
gosh> (next)
(a c b)
gosh> (next)
(b a c)
gosh> (next)
(b c a)
gosh> (next)
(c a b)
gosh> (next)
(c b a)
gosh> (next)
#<eof>
@end example



@c ----------------------------------------------------------------------
@node High-level process interface, Record types, Partial continuations, Library modules - Gauche extensions
@section @code{gauche.process} - High-level process interface
@c NODE 高レベルプロセスインタフェース, @code{gauche.process} - 高レベルプロセスインタフェース

@deftp {Module} gauche.process
@mdindex gauche.process
@c EN
This module provides a higher-level API of process control,
implemented on top of low-level system calls.
This module also provides ``process ports'',
a convenient way to send/receive information to/from subprocesses.
@c JP
このモジュールは、低レベルなシステムコールの上に実装された、
プロセス制御の高レベル API を提供します。
また、このモジュールは、サブプロセスに情報を送ったり、サブプロセスから
情報を受け取ったりするのに便利な「プロセスポート」を提供します。
@c COMMON

@c EN
Note: This module used to provide
@code{shell-escape-string} and @code{shell-tokenize-string}, but they're
purely text manipulation and not really related to subprocesses, so
we moved them to @code{text.sh}.  @xref{Shell text utilities}, for the
details.  For the backward compatibility, we keep exporting those
two procedures from @code{gauche.process}.
@c JP
註: このモジュールでは@code{shell-escape-string}と@code{shell-tokenize-string}
というユーティリティ手続きを提供していましたが、これらはテキスト操作でありサブプロセスと
直接の関係がないので、@code{text.sh}に移されました。
詳しくは@ref{Shell text utilities}を参照してください。
互換性のため、@code{gauche.process}からもこれらの手続きはエクスポートされます。
@c COMMON
@end deftp

@menu
* Running subprocess::
* Running process pipeline::
* Process object::
* Process ports::
* Process connection::
@end menu

@node Running subprocess, Running process pipeline, High-level process interface, High-level process interface
@subsection Running subprocess
@c NODE サブプロセスの実行

@defun do-process cmd/args :key redirects input output error @
                   fork environment directory host sigmask on-abnormal-exit
@defunx do-process! cmd/args :key redirects input output error @
                    fork environment directory host sigmask
@defunx run-process cmd/args :key redirects input output error @
                   fork environment directory host sigmask wait
@c MOD gauche.process
@c EN
Runs a command with arguments given to @var{cmd/args} in a subprocess.
The @var{cmd/args} argument must be a list, whose car specifies
the command name and whose cdr is the command-line arguments.

If the command name contains a slash, it is taken as the
pathname of the executable.  Otherwise the named command
is searched from the directories in the @code{PATH} environment variable.

Each element in @var{cmd/args} are converted to a string
by @code{x->string}, for the convenience.
@c JP
サブプロセスで、@var{cmd/args}に与えられたコマンドと引数を実行します。
@var{cmd/args}引数はリストで、その@code{car}がコマンド名を、
@code{cdr}がコマンドラインに渡す引数を指定します。

コマンド名がスラッシュを含んでいた場合、それは実行可能ファイルへの
パス名と解釈されます。そうでなければ、コマンド名が@code{PATH}環境変数
にあるディレクトリから探されます。

@var{cmd/args}の各要素は、@code{x->string}で文字列に変換されます。
@c COMMON

@c EN
@code{Do-process} always waits the subprocess to terminate, and
returns @code{#t} if it exits successfully (i.e. with zero exit status).
If the subprocess terminates abnormally, the behavior is controled
by @var{on-abnormal-exit} keyword argument:
@itemize @bullet
@item
If it is @code{#f} (default), @code{#f} is returned.
Note that this default is different from @code{call-with-input-process} etc.,
which raise an error by default.  It is because @code{do-process} is
intended to be used with conditionals
like shell-script's @code{if} command; i.e.
@code{(if (do-process command) then-expr else-expr)} works just
like shell's @code{if command; then then-command; else else-command; fi}.
@item
If it is @code{:error}, a @code{<process-abnormal-exit>} error is thrown.
@item
If it is @code{:exit-code}, and the subprocess terminates with
non-zero exit status, the integer exit code (the integer value passed
to subprocess's @code{exit()}) is returned.  Note that if the
subprocess is terminated with a signal, a @code{<process-abnormal-exit>}
is still thrown.
@end itemize
@c JP
@code{do-process}は常にサブプロセスが終了するまで待ち、正常終了した場合(終了ステータスが
0の場合)に@code{#t}を返します。サブプロセスが異常終了した場合の
ふるまいはキーワード引数@var{on-abnormal-exit}によって次のように決定されます。
@itemize @bullet
@item
引数が@code{#f}の場合(デフォルト)、単に@code{#f}が返されます。
これは@code{call-with-input-process}などのデフォルト(エラーを投げる)とは
異なっていることに注意してください。@code{do-process}は、条件分岐と組み合わせて
シェルスクリプトの@code{if}コマンドのように使うことを想定しています。
@code{(if (do-process command) then-expr else-expr)}は
シェルの@code{if command; then then-command; else else-command; fi}
のように動作します。
@item
引数が@code{:error}の場合、@code{<process-abnormal-exit>}エラーが投げられます。
@item
引数が@code{:exit-code}の場合、サブプロセスがゼロ以外の終了ステータスで終了したなら、
その終了コード (サブプロセスの@code{exit()}に渡された整数値) を整数で返します。
サブプロセスがシグナルにより終了した場合は
@code{<process-abnormal-exit>}エラーが投げられることに注意してください。
@end itemize
@c COMMON

@c EN
@code{Do-process!} is like @code{do-process} except that
it raises @code{<process-abnormal-exit>} error when the process
exists with non-zero status.  It's the same behavior as
giving @code{:error} to the @code{on-abnormal-exit} keyword argument
of @code{do-process}.  This is convenient if you want to let the script
just fail when the command fails.
@c JP
@code{do-process!}は@code{do-process}とほぼ同じですが、
プロセスが0以外の終了ステータスを返した場合に@code{<process-abnormal-exit>}エラーを
投げます。@code{do-process}の@code{on-abnormal-exit}に@code{:error}を
渡した場合の振る舞いと同じです。シェルスクリプト的な仕事で、
コマンドが失敗したらそこで終わってよいといった場合に便利です。
@c COMMON

@c EN
@code{Run-process} can run the subprocess concurrently by default,
that is, it returns immediately.  The return value is a @code{<process>}
object, which can be used to track the status of the subprocess
(@pxref{Process object}).
@c JP
@code{run-process}はデフォルトでサブプロセスを並行して走らせます。
つまり、直ちに返ってきます。返り値は@code{<process>}オブジェクトで、それを
用いてサブプロセスの状態を追跡できます
(@ref{Process object}参照)。
@c COMMON

@c EN
For example, the following expression runs @code{ls -al}.
@c JP
例えば、次の式は@code{ls -al}を実行します。
@c COMMON

@example
(do-process '(ls -al))
@end example

@c EN
You see the output of @code{ls -al}, then it returns @code{#t},
unless the execution of @code{ls} command fails with some reason.
@c JP
@code{ls}コマンドが何らかの理由で失敗しない限り、
@code{ls -al}の出力が表示されてから、@code{#t}が返されるでしょう。
@c COMMON

@c EN
Since @code{do-process} returns the success or failure of the command
by a boolean value, you can use @code{and} and @code{or} to combine
commands pretty much the same way as shell's @code{&&} and @code{||}
operators.
@c JP
@code{do-process}はコマンドの成功失敗を真偽値で返すので、
シェルの@code{&&}や@code{||}オペレータでコマンドを組み合わせるのと同じことが
@code{and}や@code{or}でできます。
@c COMMON

@example
;; shell: make && make -s check
(and (do-process '(make))
     (do-process '(make -s check)))

;; shell: mv x.tmp x.c || rm -f x.tmp
(or (do-process '(mv x.tmp x.c))
    (do-process '(rm -f x.tmp)))
@end example

@c EN
If you use @code{run-process} instead, you'll get @code{<process>} object
without waiting @code{ls -al} to finish.  If you run the following expression
on REPL, you'll likely to see the return value before output of @code{ls}.
@c JP
代わりに@code{run-process}を使った場合は、@code{ls -al}の終了を待たずに
@code{<process>}オブジェクトが返されます。
次の式をREPLで実行したなら、おそらく
@code{ls}の出力の前に@code{<process>}オブジェクトが表示されるでしょう。
@c COMMON

@example
(run-process '(ls -al))
@end example

@c EN
You can keep the returned @code{<process>} object
and call @code{process-wait} on it to wait for its termination.
@xref{Process object}, for the details of @code{process-wait}.
@c JP
戻り値の@code{<process>}オブジェクトを保持しておいて、後で
@code{process-wait}を呼ぶことによって子プロセスの終了を待つことができます。
@code{process-wait}については@ref{Process object}で説明します。
@c COMMON

@example
(let1 p (run-process '(ls -al))
  ... do some other work ...
  (process-wait p))
@end example

@c EN
You can tell @code{run-process} to wait for the subprocess to exit; in
that case, @code{run-process} calls @code{process-wait} internally.
It is useful if you want to examine the exit status of the subprocess,
rather than just caring its success/failure as @code{do-process} does.
@c JP
@code{run-process}に、プロセス終了を待つように指示することもできます。
その場合、@code{run-process}は内部で@code{process-wait}を呼びます。
@code{do-process}は成功/失敗しかわからないのに対し、
プロセスの終了ステータスを後で調べたい場合に便利です。
@c COMMON

@c EN
Note that @code{-i} is read as an imaginary number,
so be careful to pass @code{-i} as a command-line
argument; you should use a string, or write @code{|-i|} to make it
a symbol.
@c JP
ところで、@code{-i}は虚数として読まれることに注意してください。
@code{-i}を引数として渡したい場合は文字列にするか、@code{|-i|}のように
エスケープしてシンボルにする必要があります。
@c COMMON

@example
(run-process '(ls "-i"))
@end example

@c EN
Note: An alternative way to run external process is @code{sys-system},
which takes a command line as a single string (@pxref{Process management}).
The string is passed to the shell to be interpreted,
so you can include redirections, or can pipe several commands.
It would be handy for quick throwaway scripts.

On the other hand, with @code{sys-system},
if you want to change command parameters
at runtime, you need to worry about properly escape them
(actually we have one to do the job:
@code{shell-escape-string}, @pxref{Shell text utilities});
you need to be aware that @code{/bin/sh}, used by
@code{sys-system} via @code{system(3)} call, may differ among
platforms and be careful not to rely on specific features on
certain systems.  As a rule of thumb, keep @code{sys-system} for
really simple tasks with a constant command line,
and use @code{run-process} and @code{do-process}
for all other stuff.
@c JP
注：外部プロセスを走らせる方法にはもうひとつ、@code{sys-system}があります。
こちらはコマンド行を単一の文字列で渡し、シェルを呼び出して解釈させます
(@ref{Process management}参照)。
したがって、入出力のリダイレクトや、パイプでつないだコマンド等もそのまま渡せます。
書き捨てのスクリプトを素早く書くときはそちらの方が便利でしょう。

一方、@code{sys-system}を使う場合には、コマンドの引数を実行時に可変にしたい場合に
きちんとエスケープされているかどうかを確認したり (実はそれをやってくれる
@code{shell-escape-string}という手続きがあります。@ref{Shell text utilities}参照)、
また@code{sys-system}が@code{system(3)}経由で
呼び出す@code{/bin/sh}のプラットフォーム間の違いを気にしたりする必要があります。
原則として、@code{sys-system}の使用は固定コマンドを呼び出す簡単な場合に
止めておき、他の仕事には@code{run-process}や
@code{do-process}を使うのが良いでしょう。
@c COMMON

@c EN
Note: Old version of this procedure took arguments differently,
like @code{(run-process "ls" "-al" :wait #t)}, which was compatible
to STk.  This is still supported but deprecated.
@c JP
注：以前のバージョンのこの手続きは引数の取りかたが若干異なっており、
例えば@code{(run-process "ls" "-al" :wait #t)}のように呼び出しました。
これはSTkとの互換性によるものです。現在でもこの呼び出しはサポートされていますが、
非推奨です。
@c COMMON

@c EN
Large number of keyword arguments can be passed to
@code{do-process} and
@code{run-process}
to control execution of the child process.  We describe them by
categories.
@c JP
子プロセスの実行を細かく制御するために、@code{do-process}と
@code{run-process}はたくさんの
キーワード引数を取ります。以下でそれらをいくつかのカテゴリに分類して説明します。
@c COMMON
@end defun


@c EN
@subsubheading Synchronization
@c JP
@subsubheading 同期
@c COMMON

@deftp {Subprocess argument} wait @var{flag}
@c EN
This can only be given to @code{run-process}.
If @var{flag} is true, @code{run-process} waits until the
subprocess terminates, by calling @code{process-wait} internally.
Otherwise the subprocess runs asynchronously
and @code{run-process} returns immediately, which is the default behavior.

Note that if the subprocess is running asynchronously, it is the
caller's responsibility to call @code{process-wait} at a certain
timing to collect its exit status.
@c JP
この引数は@code{run-process}のみに渡すことができます。
@var{flag} が真の場合、@code{run-process} は内部で
@code{process-wait}を呼びだし、サブプロセスが終了するまで待ちます。
そうでなければ、サブプロセスは非同期に実行され、@code{run-process} は
すぐに返ります。これがデフォルトの振る舞いになります。

サブプロセスが非同期に実行している場合、その終了ステータスを回収するために
適切なタイミングで @code{process-wait} を呼ぶことは、呼び出し側の責任であることに
注意してください。
@c COMMON

@example
;; This returns after wget terminates.
(define p (run-process '(wget http://practical-scheme.net/) :wait #t))

;; Check the exit status
(let1 st (process-exit-status p)
  (cond [(sys-wait-exited? st)
         (print "wget exited with status " (sys-wait-exit-status st))]
        [(sys-wait-signaled? st)
         (print "wget interrupted by signal " (sys-wait-termsig st))]
        [else
         (print "wget terminated with unknown status " st)]))
@end example
@end deftp

@deftp {Subprocess argument} on-abnormal-exit @var{how}
@c EN
This can only be given to @code{do-process}.
If @var{how} is @code{#f}, which is the default,
@code{do-process} returns @code{#f} when
the subprocess exits abnormally (i.e. with nonzero exit status).
If @var{how} is @code{:error}, it raises an error in such a case.
@c JP
この引数は@code{do-process}のみに渡すことができます。
@var{how}が@code{#f}の場合(デフォルト)、
サブプロセスが異常終了(ゼロ以外の終了ステータスを返)した場合は@code{#f}を返します。
@var{how}が@code{:error}なら、その場合はエラーを投げます。
@c COMMON
@end deftp

@deftp {Subprocess argument} fork @var{flag}
@c EN
If @var{flag} is true, @code{do-process} and
@code{run-process} forks to run
the subprocess, which is the default behavior.  If @var{flag} is
false, @code{do-process} and
@code{run-process} directly calls @code{sys-exec}, so
it never returns.
@c JP
@var{flag} が真の場合、@code{do-process}と
@code{run-process} はサブプロセスを実行するために
フォークします。これはデフォルトの振る舞いです。@var{flag} が偽の場合、
@code{do-process}と
@code{run-process} は直接 @code{sys-exec} を呼ぶので、戻って来ません。
@c COMMON
@end deftp

@c EN
@subsubheading I/O redirection
@c JP
@subsubheading I/Oリダイレクト
@c COMMON

@deftp {Subprocess argument} redirects (@var{iospec} @dots{})
@c EN
Specifies how to redirect child process's I/Os.
Each @var{iospec}
can be one of the followings, where @var{fd}, @var{fd0}, and @var{fd1}
are nonnegative integers referring to the file descriptor
@emph{of the child process}.
@c JP
子プロセスのI/Oをどのようにリダイレクトするかを指定します。
各@var{iospec}は次の形式のいずれかです。ここで@var{fd}, @var{fd0}および@var{fd1}は
@emph{子プロセスにおける}ファイルディスクリプタを指定する非負の整数です。
@c COMMON

@c EN
(Note: If you just want to run a command and get its output as a string
take a look at @code{process-output->string} (@pxref{Process ports}).
If you want to pipe multiple commands together,
@pxref{Running process pipeline}.)
@c JP
(註：簡単にコマンドを走らせて結果を文字列で得たい場合は、
@code{process-output->string}が使えます(@ref{Process ports}参照)。
また、複数のコマンドをパイプでつなぎたい場合は
@ref{Running process pipeline}を見てください。)
@c COMMON

@table @code
@item (< @var{fd} @var{source})
@c EN
@var{source} can be a string, a symbol, a keyword @code{:null},
an integer, or an input port.

If it is a string, it names a file opened for read
and the child process can reads the content of the file from @var{fd}.
An error is signaled if the file does not exist or cannot open for read.

If it is a symbol, an unidirectional pipe is created, whose reader end
is connected to the child's @var{fd}, and whose writer end is
available as an output port returned from
@code{(process-input @var{process} @var{source})}.

If it is @code{:null}, the child's @var{fd} is connected to the
null device.

If it is an integer, it should specify a parent's file descriptor
opened for read.  The child sees the duped file descriptor as @var{fd}.

If it is an input port, the underlying file descriptor is duped
into child's @var{fd}.  It is an error to pass an input port without
associated file descriptor (See @code{port-file-number} in
@ref{Common port operations}).
@c JP
@var{source}は文字列、シンボル、キーワード@code{:null}、整数、入力ポートのいずれかです。

文字列の場合、それはファイル名を指定します。そのファイルが読み込み用にオープンされ、
子プロセスはfdからその内容を読み込みます。指定されたファイルが存在しないか
読み込み用にオープンできなければエラーが報告されます。

シンボルの場合、一方向のパイプが作られ、その読み出し側の端が子プロセスのfdへと
接続されます。書き込み側の端は
@code{(process-input @var{process} @var{source})}
を呼び出すことで入手できます。

@code{:null}の場合、@var{fd}はシステムのヌルデバイスからの
読み込みになります。

整数の場合は、現プロセスの読み込み用ファイルディスクリプタを指定します。
そのファイルディスクリプタの読み込み元が@code{dup}されて、子プロセスからは@var{fd}として
見えます。

入力ポートの場合は、入力元のファイルディスクリプタが@code{dup}されて
子プロセスの@var{fd}になります。ファイルディスクリプタを持たないポートを渡した
場合はエラーになります(@ref{Common port operations}の@code{port-file-number}参照)。
@c COMMON

@item (<< @var{fd} @var{value})
@itemx (<<< @var{fd} @var{obj})
@c EN
Feeds @var{value} or @var{obj} to the input file
descriptor @var{fd} of the child process.

With @code{<<}, @var{value} must be either a string or a uniform
vector (@pxref{Uniform vectors}).  It is sent to the child process as is.
Using a uniform vector is good to pass binary content.

With @code{<<<}, @var{obj} can be any Scheme object, and
the result of @code{(write-to-string obj)} is sent to the child process.
@c JP
@var{value}または@var{obj}を子プロセスの入力ファイルディスクリプタ@var{fd}への
入力とします。

@code{<<}を使う場合、@var{value}は文字列かユニフォームベクタ
(@pxref{Uniform vectors})でなければなりません。その内容がそのまま
子プロセスの入力へと送られます。ユニフォームベクタはバイナリデータを渡すのに便利です。

@code{<<<}を使う場合、@var{obj}には任意のSchemeオブジェクトを渡せます。
@code{(write-to-string obj)}の結果の文字列が子プロセスの入力へと送られます。
@c COMMON

@item (<& @var{fd0} @var{fd1})
@c EN
Makes child process's file descriptor @var{fd0} refer to the same input
as its file descriptor @var{fd1}.  Note the difference from @code{<};
@code{(< 3 0)} makes the parent's stdin (file descriptor 0) be read
by the child's file descriptor 3, while  @code{(<& 3 0)} makes
the child's file descriptor 3 refer to the same input as child's stdin
(which may be redirected to a file or something else by another @var{iospec}).

See the note below on the order of processing @code{<&}.
@c JP
子プロセスのファイルディスクリプタ@var{fd0}が、
同じく子プロセスのファイルディスクリプタ@var{fd1}が指しているものと
同じ入力を参照するようにします。
@var{<}との違いに注意してください。@code{(< 3 0)}とすると、
現プロセスのstdin (ファイルディスクリプタ0) が子プロセスからはファイルディスクリプタ3
として見えるようになります。@code{(<& 3 0)}とすると、子プロセスのファイルディスクリプタ3
は子プロセスのstdinと同じものを見るようになります (それは他の@var{iospec}によって
ファイル等にリダイレクトされているかもしれません)。

@code{<&}の処理の順番について、下の方にある註も参照してください。
@c COMMON

@item (> @var{fd} @var{sink})
@itemx (>> @var{fd} @var{sink})
@c EN
@var{sink} must be either a string, a symbol, a keyword @code{:null},
an integer or a file output port.

If it is a string, it names a file.  The output of the child to
the file descriptor @var{fd} is written to the file.
If the named file already exists, @code{>} first truncates its
content, while @code{>>} appends to the existing content.

For other arguments, @code{>} and @code{>>} works the same.

If @var{sink} is a symbol, an unidirectional pipe is created
whose writer end is connected to the child's @var{fd}, and whose
reader end is available as an input port returned by
@code{(process-output @var{process} @var{sink})}.

If @var{sink} is @code{:null}, child's @var{fd} is connected
to the system's null device.

If @var{sink} is an integer, it must specify a parent's file
descriptor opened for output.  The child sees the duped file descriptor
as @var{fd}.

If @var{sink} is an output port, the underlying file descriptor is
duped into @var{fd} in the child process.
@c JP
@var{sink}は文字列、シンボル、キーワード@code{:null}、整数、あるいは
ファイル出力ポートでなければなりません。

文字列の場合、それはファイル名です。指定されたファイルが書き込み用にオープンされ、
子プロセスのファイルディスクリプタ@var{fd}からそこに書き込むことができます。
指定のファイルが既に存在している場合、@code{>}はファイルをまず空にするのに対し、
@code{>>}はファイルの後に追加します。
@code{>}と@code{>>}の違いが出るのは@var{sink}がファイルの場合のみです。

@var{sink}がシンボルなら、一方向のパイプが作られ、その入力端が
子プロセスの@code{fd}へと繋がれます。パイプに送られた子プロセスの出力を
読み出す入力ポートは、
@code{(process-output @var{process} @var{sink})}で得ることができます。

@var{sink}が@code{:null}なら、@var{fd}はシステムのヌルデバイスへの
書き出しになります。

整数の場合、それは現プロセスの書き込み用ファイルディスクリプタを
指定します。それが@code{dup}されて子プロセスの@var{fd}となります。

出力ポートの場合は、出力先のファイルディスクリプタが@code{dup}されて
子プロセスの@var{fd}になります。ファイルディスクリプタを持たないポートを渡した
場合はエラーになります(@ref{Common port operations}の@code{port-file-number}参照)。
@c COMMON

@item (>& @var{fd0} @var{fd1})
@c EN
Makes child process's file descriptor @var{fd0} refer to the same output
as its file descriptor @var{fd1}.  Note the difference from @code{>};
@code{(> 2 1)} makes the child's stderr go to parent's stdout,
while  @code{(>& 2 1)} makes the child's stderr go to the same
output as child's stdout (which may be redirected by another @var{iospec}).
@c JP
子プロセスのファイルディスクリプタ@var{fd0}が、子プロセスのファイルディスクリプタ@var{fd1}
が参照するのと同じ出力先を参照するようにします。
@var{>}との違いに注意: @code{(> 2 1)}は子プロセスのstderrが現プロセスのstdout
と同じところに送られるようにするのに対し、@code{(>& 2 1)}は子プロセスのstderr
が子プロセスのstdoutに送られます (それは別の@var{iospec}によってリダイレクト
されているかもしれません)。
@c COMMON

@example
@c EN
;; Read both child's stdout and stderr
@c JP
;; 子プロセスのstdoutとstderrを一緒にして読み込む
@c COMMON
(let1 p (run-process '(command arg)
                     :redirects '((>& 2 1) (> 1 out)))
  (begin0 (port->string (process-output p 'out))
          (process-wait p)))
@end example

@end table

@c EN
Note: You can't use the same name (symbol) more than once for
the pipe of source or sink.  For example, the following code
signals an error:
@c JP
註: 入力元や出力先にパイプを使う場合、同じ名前(シンボル)を複数の入出力に
指定することはできません。例えば次のコードはエラーとなります。
@c COMMON
@example
(run-process '(command) :redirects '((> 1 out) (> 2 out))) ; error!
@end example
@c EN
You can use @code{>&} to ``merge'' the output to one sink,
or @code{<&} to ``split'' the input from one source, instead:
@c JP
複数の出力を一つの出力先にマージするには@code{>&}を、
一つの入力元を複数の入力で読み込みには@code{<&}を使ってください。
@c COMMON
@example
(run-process '(command) :redirects '((> 1 out) (>& 2 1)))
@end example
@c EN
It is allowed to give the same file name more than once,
just like the Unix shell.  However, note that the file is
opened individually for each file descriptor, so simply
writing to them may not produce desired result (for regular
files, most likely that one output would overwrite another).
@c JP
同じファイル名を複数の入出力に指定することは、Unixのシェル同様、可能です。
ただしその場合、ファイルはそれぞれの入出力ごとに別々にオープンされる
ことに注意してください。例えば同じファイルを複数の出力からオープンして
書き込んだ場合、求める結果が得られないかもしれません(通常のファイルであれば、
一方の出力がもう一方の出力を上書きしてしまうでしょう)。
@c COMMON

@c EN
Note: I/O redirections are processed @emph{at once}, unlike the way
unix shell does.  For example, both of the following expression
works the same way, that is, they redirect
both stdout and stderr to a file @file{out}.
@c JP
註: I/Oリダイレクト指定は、unixのシェルと違って、
全て@emph{同時に}処理されます。つまり、以下の式はどちらも同じように、
stdoutとstderrをファイル@file{out}に書き出す処理となります。
@c COMMON

@example
(run-process '(command arg) :redirects '((>& 2 1) (> 1 "out")))
(run-process '(command arg) :redirects '((> 1 "out") (>& 2 1)))
@end example

@c EN
Most unix shells process redirections @emph{in order}, so the following
two command line works differently: The first one redirects child's
stderr to the @emph{current} stdout, which is the same as the parent's
stdout, then redirects child's stdout to a file @file{out}.  So the
error messages appear in the parent's stdout.  The second one first
redirects the child's stdout to a file @file{out}, so at the time
of processing @code{2>&1}, the child's stderr also goes to the file.
@c JP
unixのシェルではリダイレクト指定は@emph{順に}処理されるので、
次の二つのコマンドラインは異なる動作となります。最初の例では
子プロセスのstderrが@emph{現時点での}stdout (それは現プロセスのstdoutでもある)
へと向けられ、次に子プロセスのstdoutがファイル@file{out}に向けられます。
従ってエラーメッセージは現プロセスのstdoutへと現れます。二番目の例では
最初に子プロセスのstdoutがファイル@file{out}へ向けられるので、
@code{2>&1}が処理される時にはstderrの行き先はやはり@file{out}となります。
@c COMMON

@example
$ command arg 2>&1 1>out
$ command arg 1>out 2>&1
@end example

@c EN
You can say @code{do-process} and
@code{run-process} always works like the latter,
regardless of the order in @var{redirects} argument.

If you want to redirect child's stderr to parent's stdout,
you can use @code{>} like the following:
@c JP
@code{do-process}と
@code{run-process}は@var{redirects}引数の順番にかかわらず
常に後者のように動作すると言ってもよいでしょう。

もし前者の例のように子プロセスのstderrだけを親プロセスのstdoutに
向けたいのであれば、次のように@code{>}を使うことで実現できます。
@c COMMON

@example
(run-process '(command arg) :redirects '((> 2 1) (> 1 "out")))
@end example

@end deftp


@deftp {Subprocess argument} input @var{source}
@deftpx {Subprocess argument} output @var{sink}
@deftpx {Subprocess argument} error @var{sink}
@c EN
Redirects child's standard i/o.
@var{source} and @var{sink} may be either a string, one
of keywords @code{:null}, @code{:pipe}, or @code{merge},
an integer file descriptor, or a symbol.

These are really shorthand notations of the @var{redirects} argument:
@c JP
サブプロセスの標準入出力を制御します。
@var{source}及び@var{sink}は、文字列、キーワード @code{:pipe}、
@code{:null}、@code{:merge}、整数のファイルディスクリプタ、もしくはシンボルです。

実のところ、これらは@var{redirects}引数の略記にすぎません。
@c COMMON

@example
:input x   @equiv{} :redirects '((< 0 x))
:output x  @equiv{} :redirects '((> 1 x))
:error x   @equiv{} :redirects '((> 2 x))
@end example

@c EN
The keyword @code{:pipe} as @var{source} or @var{sink} is supported
just for the backward compatibility.  They work as if a symbol
@code{stdin}, @code{stdout} or @code{stderr} is given, respectively:
@c JP
キーワード@code{:pipe}は互換性のためだけにサポートされています。
それぞれ、シンボル@code{stdin}、@code{stdout}、@code{stderr}が
指定されたかのように振る舞います。
@c COMMON

@example
:input :pipe   @equiv{} :redirects '((< 0 stdin))
:output :pipe  @equiv{} :redirects '((> 1 stdout))
:error :pipe   @equiv{} :redirects '((> 2 stderr))
@end example

@c EN
That is, a pipe is created and its one end is connected to the
child process's stdio, and the other end is available
by calling @code{(process-input @var{process})},
@code{(process-output @var{process})} or @code{(process-error @var{process})}.
(That is because @code{process-input} and @code{process-output}
uses @code{stdin} and @code{stdout} respectively when @var{name} argument
is omitted, and @code{(process-error p)} is equivalent
to @code{(process-output p 'stderr)}.)
@c JP
すなわち、パイプが作成され、その一方が子プロセスの標準入出力のいずれかに接続されます。
もう一方の端は@code{(process-input @var{process})}、
@code{(process-output @var{process})}および
@code{(process-error @var{process})}によって得ることができます。
(@code{process-input}, @code{process-output}は@var{name}引数が
省略されるとそれぞれ@code{stdin}, @code{stdout}をデフォルトとし、
また@code{(process-error p)}は@code{(process-output p 'stderr)}と
等価だからです)
@c COMMON

@c EN
The keyword @code{:merge} can only be used for @code{:error} keyword
argument, and it is a shorthand notation of
@code{:redirects '((>& 2 1))}, that is, merge the child process's
stderr into child process's stdout.
@c JP
キーワード@code{:merge}は@code{:error}キーワード引数のみに有効で、
@code{:redirects '((>& 2 1))}の略記になります。
すなわち、子プロセスのstderrを子プロセスのstdoutにマージします。
@c COMMON

@c EN
See the description of @var{redirects} above for the meanings
of the argument values.
@c JP
引数の意味の詳しい説明については上の@var{redirects}の項を参照してください。
@c COMMON
@end deftp


@c EN
@subsubheading Execution environment
@c JP
@subsubheading 実行環境
@c COMMON

@deftp {Subprocess argument} environment @var{env-list}
@c EN
The argument must be @code{#f} (default) or a list of strings,
each of which has the form @code{@var{NAME}=@var{VALUE}}.
If it is @code{#f}, the subprocess inherits the same environment
variables as the current process.  If it is a list of strings,
it specifies the environment variables the subprocess sees.
The form is the same as what @code{sys-environ} returns, so you
can easily add to/remove from the current environment
(@pxref{Environment inquiry}).
@c JP
引数は@code{#f}(デフォルト)もしくは文字列のリストでなければなりません。
文字列のリストの場合、各文字列は@code{@var{NAME}=@var{VALUE}}という形式でなければなりません。
これが@code{#f}の場合、子プロセスは現在のプロセスの環境変数を引き継ぎます。
文字列のリストの場合であれば、それが子プロセスの環境変数を指定します。
この形式は@code{sys-environ}が返すものと同じなので、
容易に現在の環境変数に環境変数を加えたり取り除いたりすることができます
(@ref{Environment inquiry}参照)。
@c COMMON
@end deftp

@deftp {Subprocess argument} directory @var{directory}
@c EN
If a string is given to @var{directory},
the process starts with @var{directory} as its working directory.
If @var{directory} is @code{#f}, this argument is ignored.
An error is signaled if @var{directory} is other type of objects,
or it is a string but is not a name of a existing directory.

When @var{host} keyword argument is also given, this argument
specifies the working directory of the @emph{remote} process.

Note: @code{do-process} and
@code{run-process} check the validity of @var{directory},
but actual @code{chdir(2)} is done just before @code{exec(2)},
and it is possible that @code{chdir} fails in spite of previous
checks.  At the moment when @code{chdir} fails, there's no
reliable way to raise an exception to the caller,
so it writes out an error message to standard error port and exits.
A robust program may take this case into account.
@c JP
@var{directory}に文字列が与えられた場合、
そのディレクトリが起動されるプロセスのワーキングディレクトリとなります。
@code{#f}が与えられた場合はの引数は何もしません。
文字列か@code{#f}以外が与えられた場合、もしくは文字列が存在するディレクトリの
名前でない場合はエラーが報告されます。

@var{host}キーワード引数も与えられている場合、この引数は
リモートプロセスのワーキングディレクトリを指定します。

註: @code{do-process}と
@code{run-process}は@var{directory}が有効な値であることを事前に
チェックしますが、実際の@code{chdir(2)}は@code{exec(2)}の直前に
行われます。事前のチェックにもかかわらず@code{chdir}が失敗する可能性が
あります。その時点では呼び出し元にエラーを伝える
確実な方法が無いため、Gaucheは標準エラー出力にメッセージを印字して
exitします。頑健なプログラムを書く場合、そのようなケースにも留意して下さい。
@c COMMON
@end deftp


@deftp {Subprocess argument} sigmask @var{mask}
@c EN
@var{Mask} must be either an instance of @code{<sys-sigset>},
a list of integers, or
@code{#f}.  If an instance of @code{<sys-sigset>} is given, the
signal mask of executed process is set to it.   A list of integers
are treated as a list of signals to mask.  It is important
to set an appropriate mask if you call @code{run-process} from
multithreaded application.
See the description of @code{sys-exec} (@ref{Process management})
for the details.

If the @var{host} keyword argument is specified, this argument
merely sets the signal mask of the local process (@code{ssh}).
@c JP
@var{mask}は@code{<sys-sigset>}のインスタンス、整数のリスト、
あるいは@code{#f}でなければなりません。
@code{<sys-sigset>}のインスタンスである場合、それが実行する
プロセスのシグナルマスクになります。整数のリストの場合は各整数が
マスクすべきシグナル番号とみなされます。マルチスレッドアプリケーションで
@code{run-process}を使う場合はシグナルマスクを適切に設定することが重要です。
@code{sys-exec}の説明を参照して下さい (@ref{Process management})。

@var{host}キーワード引数が与えられている場合は、この引数は
ローカル側のプロセス(@code{ssh})のみのシグナルマスクをセットします。
@c COMMON
@end deftp

@deftp {Subprocess argument} detached @var{flag}
@c EN
When a true value is given, the new process is detached from
the parent's process group and belongs to its own group.
It is useful when you run a daemon process.
See @code{sys-fork-and-exec} (@pxref{Process management}), for
the detailed description of @var{detached} argument.
@c JP
真の値が渡されると、作られるプロセスは親プロセスのプロセスグループから
切り離され、独自のプロセスグループを作ります。
デーモンプロセスを作る際に便利です。@var{detached}引数の詳しい動作については、
@code{sys-fork-and-exec} を見てください (@ref{Process management}参照)。
@c COMMON
@end deftp


@deftp {Subprocess argument} host @var{hostspec}
@c EN
This argument is used to execute @var{command} on the remote host.
The full syntax of @var{hostspec} is @code{protocol:user@@hostname:port},
where @var{protocol:}, @var{user@@}, or @var{:port} part can be
omitted.

The @var{protocol} part specifies the protocol to communicate
with the remote host; currently only @code{ssh} is supported, and
it is also the default when @var{protocol} is omitted.
The @var{user} part specifies the login name of the remote host.
The @var{hostname} specifies the remote host name, and the
@var{port} part specifies the alternative port number which
@var{protocol} connects to.

The command line arguments are interpreted on the remote host.
On the other hand, the I/O redirection is done on the local end.
For example, the following code reads the file @file{/foo/bar} on
the remote machine and copies its content into the local file
@file{baz} in the current working directory.
@c JP
この引数は、@var{command}をリモートホストで実行させるのに使います。
@var{hostspec}の完全な構文は@code{protocol:user@@hostname:port}で、
@var{protocol:}、@code{user@@}、@code{:port}の部分は省略可能です。

@var{protocol}はリモートに接続するプロトコルを指定します。現在のところ
@code{ssh}だけがサポートされており、また省略された場合も@code{ssh}が
使われます。@var{user}はリモートでのユーザ名を、@var{hostname}は
リモートホスト名を指定します。@var{port}は@var{protocol}のデフォルト
以外のポートを使いたい場合に指定します。

コマンドライン引数はリモートホスト上で解釈されます。
一方、I/Oリダイレクトはローカル側で処理されす。
例えば、次のコードはリモートマシンの@file{/foo/bar}の内容を読み、
それをローカルのワーキングディレクトリ内のファイル@file{baz}へとコピーします。
@c COMMON

@example
(do-process '(cat "bar")
            :host "remote-host.example.com"
            :directory "/foo"
            :output "baz")
@end example
@end deftp

@node Running process pipeline, Process object, Running subprocess, High-level process interface
@subsection Running process pipeline
@c NODE プロセスパイプラインの実行

@defun do-pipeline commands :key input output error directory sigmask on-abnormal-exit
@defunx run-pipeline commands :key input output error wait directory sigmask
@c MOD gauche.process
@c EN
Convenience routines to run pipeline of processes at once.
Example:
@c JP
複数のプロセスでパイプラインを構成するための便利関数です。例:
@c COMMON

@example
(do-pipeline '((ls "src/")
               (grep "\\.c$")
               (wc -l)))
@end example

@c EN
This is equivalent to shell command pipeline
@code{ls src/ | grep '\.c$' | wc -l}, i.e. shows the
number of C source files in the @file{src} subdirectory.
@c JP
これはシェルのコマンドでのパイプライン@code{ls src/ | grep '\.c$' | wc -l}
と同等で、@file{src}ディレクトリにあるCソースファイルの数を数えます。
@c COMMON

@c EN
The @var{commands} argument is a list of lists.  Each list
must be @code{cmd/args} argument @code{do-process}/@code{run-process} can accept.
At least one command must be specified.
@c JP
@var{commands}引数はリストのリストです。
それぞれの内側のリストは
@code{do-process}/@code{run-process}が受け付ける@code{cmd/args}
の形式でなければなりません。少なくともひとつのコマンドが指定される必要があります。
@c COMMON

@c EN
The specified commands will run concurrently, with the stdout of
the first command is connected to the stdin of the second, and
stdout of the second to the stdin of the third, and so on.
The stdin of the first command is fed from the source specified
by the @var{input} keyword argument, and the stdout of the last
command is sent to the sink specified by the @var{output} keyword
argument.  The default values of these are the calling process's
stdin and stdout, respectively.  See @code{do-process}/@code{run-process},
for the possible values of these arguments
(@pxref{Running subprocess}).
@c JP
指定されたコマンドは、最初のコマンドのstdoutが次のコマンドのstdinに、
そのコマンドのstdoutがさらに次のコマンドのstdinに、@dots{}という具合に
接続されてから、全てが並行して実行されます。
最初のコマンドのstdinは@var{input}キーワード引数で指定された入力から供給され、
最後のコマンドのstdoutは@var{output}キーワード引数で指定された出力へと流れます。
これらのキーワード引数の省略時の値は、呼び出すプロセスのstdinとstdoutです。
これらキーワード引数に与えられる値については
@code{do-process}/@code{run-process}の項を見てください
(@ref{Running subprocess})。
@c COMMON

@c EN
The stderr of all the processes are sent to the sink specified
by the @var{error} keyword argument, which is defaulted by the
calling process's stderr.
@c JP
全てのプロセスのstderrは@var{stderr}キーワード引数で指定される出力へと流されます。
省略時は呼び出すプロセスのstderrが使われます。
@c COMMON

@c EN
Like @code{do-process}, @code{do-pipeline} waits for completion of
all the processes, and returns @code{#t} if the tail process
succeeds (i.e. exits with zero status) or @code{#f} if the last process
fails (i.e. exits with non-zero status).   If you give
@code{:error} to @code{on-abnormal-exit} keyword arguments, however,
a failure of the tail process raises an error.
Exit statuses of subprocesses other than the tail one are
collected by @code{process-wait}, but won't affect the
return value, and won't cause an error even
@code{on-abnormal-exit} is @code{:error}.
@c JP
@code{do-process}と同じように、@code{do-pipeline}は全てのプロセスの終了を待ち、
パイプライン末尾のプロセスが成功した(終了ステータスが0)場合に@code{#t}を、
失敗した(終了ステータスが0以外)場合に@code{#f}を返します。
ただし、@code{on-abnormal-exit}キーワード引数に@code{:error}を渡した場合は、
末尾のプロセスが失敗した場合にエラーが投げられます。
末尾以外のプロセスの終了ステータスは@code{process-wait}によって回収されますが、
返り値には影響を与えず、
失敗した場合に@code{on-abnormal-exit}引数が@code{:error}であってもエラーは投げられません。
@c COMMON

@c EN
On the other hand, @code{run-pipeline} returns a @code{<process>} object of
the tail process.  You can get other process objects in
the pipeline by applying @code{process-upstreams} to the tail process.
By default, @code{run-pipeline} runs all the subprocesses in background
and returns immediately.  Calling @code{process-wait} on the returned
process object will waits for all the subprocesses.
If you give a true value to @var{wait} keyword argument,
@code{run-process} waits for all the subprocesses to finish
before returning.
@c JP
一方、@code{run-pipeline}は末尾のプロセスの@code{<process>}オブジェクトを返します。
パイプライン中の他のプロセスは末尾プロセスに@code{process-upstreams}
を適用すれば得られます。
デフォルトでは、@code{run-pipeline}は全てのサブプロセスをバックグラウンドで起動して
直ちに戻ってきます。返り値の末尾プロセスに対して@code{process-wait}を呼ぶと、
全てのサブプロセスが終了するまで待ちます。
@var{wait}キーワード引数に真の値を渡した場合は、
@code{run-process}は全てのサブプロセスの終了を待ってから戻ります。
@c COMMON

@c EN
The @var{directory} and @var{sigmask} keyword arguments are applied
to all the processes;
see @code{do-process}/@code{run-process} for the description
of these arguments
(@pxref{Running subprocess}).
@c JP
@var{directory}と@var{sigmask}キーワード引数は全てのプロセスに適用されます。
これらの引数の説明は@code{do-process}/@code{run-process}の項を見てください
(@ref{Running subprocess})。
@c COMMON

@c EN
Note: In Gauche 0.9.5, we introduced @code{run-process-pipeline}.  It is similar
to the current @code{run-pipeline} but returns a list of subprocess objects
instead of a single one.  We realized it's not very convenient, so we
deprecated @code{run-process-pipeline} and replaced it with @code{run-pipeline}.
We still support @code{run-process-pipeline}, but strongly recommend
to move to @code{run-pipeline} as soon as possible.
@c JP
註: Gauche 0.9.5で、@code{run-process-pipeline}というAPIを導入しました。
これは現在の@code{run-pipeline}に似ていますが、起動したプロセスのリストを返します。
しかし使い勝手が悪いことがわかったので、@code{run-process-pipeline}は非推奨とし、
@code{run-pipeline}で置き換えることにしました。
@code{run-process-pipeline}もしばらくサポートされますが、
できるだけ早く@code{run-pipeline}に移行してください。
@c COMMON
@end defun


@node Process object, Process ports, Running process pipeline, High-level process interface
@subsection Process object
@c NODE プロセスオブジェクト

@deftp {Class} <process>
@clindex process
@c MOD gauche.process
@c EN
An object to keep the status of a child process.  You can create
the process object by @code{run-process} procedure described below.
The process ports explained in the next section also use process objects.
@c JP
子プロセスの状態を保持するためのオブジェクト。以下で説明される
@code{run-process} 手続きにより、プロセスを作ることができます。
次章で説明するプロセスポートもプロセスオブジェクトを用いています。
@c COMMON

@c EN
The @code{<process>} class keeps track of
the child processes spawned by high-level APIs such
as @code{run-process} or @code{open-input-process-port}.
The exit status of such children must be collected by
@code{process-wait} or @code{process-wait-any} calls,
which also do some bookkeeping.   Using
the low-level process calls such as @code{sys-wait} or
@code{sys-waitpid} directly will cause inconsistent state.
@c JP
@code{<process>}クラスは、@code{run-process}や@code{open-input-process-port}
といった高レベルAPIで作られた子プロセスの状態を管理しています。
それらの子プロセスの終了ステータスをとるには、
@code{process-wait}や@code{process-wait-any}といった
高レベルAPIを利用してください。これらの手続きはシステムコール以外の情報管理も
行います。@code{sys-wait}や@code{sys-waitpid}といった低レベルAPIで
直接子プロセスの終了ステータスを取ると、@code{<process>}クラスの
内部状態に矛盾が生じます。
@c COMMON
@end deftp

@deftp {Class} <process-abnormal-exit>
@clindex process-abnormal-exit
@c MOD gauche.process
@c EN
A condition type mainly used by the process port utility procedures.
Inherits @code{<error>}.  This type of condition is thrown when
the high-level process port utilities detect the child process exited
with non-zero status code.
@c JP
主にプロセスポートユーティリティ関数で使われるコンディション型。
@code{<error>}を継承。このコンディション型は高レベルプロセスポートユーティ
リティが子プロセスが非ゼロのexitステータスで終了したことを検知したとき
に投げられます。
@c COMMON

@defivar {<process-abnormal-exit>} process
@c EN
A process object.
@c JP
プロセスオブジェクト。
@c COMMON
@end defivar

@c EN
Note: In Unix terms, exiting a process by calling @code{exit(2)} or
returning from @code{main()} is a normal exit, regardless of the
exit status.  Some commands do use non-zero exit status
to tell one of the normal results of execution (such as @code{grep(1)}).
However, large number of commands uses non-zero exit status to
indicate that they couldn't carry out the required operation,
so we treat them as exceptional situations.
@c JP
注: Unix用語では，exitステータスにかかわらず，プロセスがcalling
@code{exit(2)}を呼ぶか，@code{main()}から帰った場合を「正常な終了」と
しています。コマンドによっては非ゼロのexitステータスで何らかの正常な実行結果を
示すものもあります(@code{grep(1)}など)。しかし，ほとんどのコマ
ンドでは，非ゼロの exit ステータスは要求された操作が実行できなかったこ
とを表わします。それゆえ上のような場合を例外的な場合として扱います。
@c COMMON
@end deftp


@defun process? obj
@c MOD gauche.process
@equiv{} @code{(is-a? @var{obj} <process>)}
@end defun

@deffn {Method} process-pid (process <process>)
@c MOD gauche.process
@c EN
Returns the process ID of the subprocess @var{process}.
@c JP
サブプロセス @var{process} のプロセスIDを返します。
@c COMMON
@end deffn

@deffn {Method} process-command (process <process>)
@c MOD gauche.process
@c EN
Returns the command invoked in the subprocess @var{process}.
@c JP
サブプロセス @var{process} 内で起動されたコマンドを返します。
@c COMMON
@end deffn

@deffn {Method} process-input (process <process>) :optional name
@deffnx {Method} process-output (process <process>) :optional name
@c MOD gauche.process
@c EN
Retrieves one end of a pipe, whose another end is connected
to the process's input or output, respectively.
@var{name} is a symbol given to the @var{redirects} argument
of @code{run-process} to distinguish the pipe.  See the following
example:
@c JP
プロセスの入力もしくは出力に一方の端がつながれたパイプの、もう一方の端を取り出します。
@var{name}は@code{run-process}の@var{redirects}引数に与えた
識別用の名前です。次の例を見てください。
@c COMMON

@example
(let1 p (run-process '(command arg)
                     :redirects '((< 3 aux-in)
                                  (> 4 aux-out)))
  (let ([auxin  (process-input p 'aux-in)]
        [auxout (process-output p 'aux-out)])
    ;; feed something to the child's input
    (display 'something auxin)
    ;; read data from the child's output
    (read-line auxout)
    @dots{}
    )
  (process-wait p))
@end example

@c EN
The symbols @code{aux-in} and @code{aux-out} is used to
identify the pipes.  Note that @code{process-input} returns
@emph{output} port, and @code{process-output} returns
@emph{input} port.
@c JP
シンボル@code{aux-in}と@code{aux-out}がパイプを識別するのに
使われています。@code{process-input}が返すのは@emph{出力}ポートであり、
@code{process-output}が返すのは@emph{入力}ポートであることに注意してください。
@c COMMON

@c EN
When @var{name} is omitted, @code{stdin} is used for @code{process-input}
and @code{stdout} is used for @code{process-output}.  These are
the names used if child's stdin and stdout are redirected by
@code{:input :pipe} and @code{:output :pipe} arguments, respectively.
@c JP
@var{name}が省略された場合、@code{process-input}は@code{stdin}を、
@code{process-output}は@code{stdout}を使います。これらは
子プロセスの標準入力/出力をそれぞれ@code{:input :pipe}/@code{:output :pipe}で
リダイレクトした場合に使われる名前です。
@c COMMON

@c EN
If there's no pipe with the given name, @code{#f} is returned.
@c JP
名前に対応するパイプが無い場合は@code{#f}が返ります。
@c COMMON

@example
(let* ((process (run-process '("date") :output :pipe))
       (line (read-line (process-output process))))
  (process-wait process)
  line)
 @result{} "Fri Jun 22 22:22:22 HST 2001"
@end example

@c EN
If @var{process} is a result of @code{run-pipeline},
@code{(process-input process)} and @code{(process-input process 'stdin)}
behave slightly differently---they return the pipe connected to the
stdin of the @emph{head} process of the pipeline, not the
process represented by @var{process} (which is the tail of the pipeline).
This allows you to treat the whole pipeline as one entity.
@c JP
@var{process}が@code{run-pipeline}の結果であった場合、
@code{(process-input process)}と@code{(process-input process 'stdin)}は
少し違う振る舞いをします。
@var{process}自体はプロセスパイプラインの末尾のプロセスを表していますが、
上記二つの呼び出しに限り、
プロセスパイプラインの先頭のプロセスのstdinにつながれたパイプを返します。
これによって、パイプライン全体をひとまとめに扱うことができます。
@c COMMON

@example
(let1 p (run-pipeline `((cat)
                        (grep "aba"))
                       :input :pipe :output :pipe)
  (display "banana\nhabana\ntabata\ncabara\n"
           (process-input p))    ; head of the pipeline
  (close-port (process-input p))
  (process-wait p)
  (port->string (process-output p)))
  @result{} "habana\ntabata\ncabara\n"
@end example

@c EN
If you want to connect one process's output to another process's input
without using @code{do-pipeline}/@code{run-pipeline}, you need to have
coroutine or thread that actively reads from one process's output
and feed it to another process's input.  You can use a plumbing
in @code{control.plumbing}
(@pxref{Plumbing ports}) to do so easily.  Plumbing also allows
you to ``tap'' the pipe, i.e. to monitor the data that flows
between processes.
@c JP
もし@code{do-pipeline}/@code{run-pipeline}を使わずに
一つのプロセスの出力を別のプロセスの入力につなげたい場合、
何らかのコルーチンかスレッドで一つのプロセスの出力をアクティブに読んで
もう一つのプロセスの入力へと送ることが必要になります。
@code{control.plumbing}を使えばそれは簡単にできます
(@ref{Plumbing ports}参照)。また、流れるデータをモニタするといったことも可能です。
@c COMMON

@c EN
Another common pattern is that you want to log the output of the process
while it is running concurrently.  You can use
@code{log-from-input-port} in @code{gauche.logger}
(@pxref{User-level logging}).
@c JP
起動したプロセスを並行して走らせながら
その出力をロギングしたいということも良くあります。
それには@code{gauche.logger}の@code{log-from-input-port}が使えます
(@ref{User-level logging}参照）。
@c COMMON
@end deffn


@deffn {Method} process-error (process <process>)
@c MOD gauche.process
@c EN
This is equivalent to @code{(process-output @var{process} 'stderr)}.
@c JP
これは@code{(process-output @var{process} 'stderr)}と等価です。
@c COMMON
@end deffn

@defun process-alive? process
@c MOD gauche.process
@c EN
Returns true if @var{process} is alive.  Note that Gauche can't
know the subprocess' status until it is explicitly checked by
@code{process-wait}.
@c JP
@var{process} が生きている場合は真を返します。@code{process-wait} によって
明示的にチェックされない限り、Gauche はサブプロセスのステータスを知ることが
できないことに注意してください。
@c COMMON
@end defun

@defun process-upstreams process
@c MOD gauche.process
@c EN
If @var{process} is the result of @code{run-pipeline}, this returns
a list of processes that are upstream of @var{process} in the pipeline.
If @var{process} is not the result of @code{run-pipeline}, this returns
an empty list.
@c JP
@var{process}が@code{run-pipeline}の結果であった場合、
パイプライン中で@var{process}の上流にあるプロセスのリストが返ります。
@var{process}が@code{run-pipeline}の結果でなかった場合は空リストが返ります。
@c COMMON

@example
(define p (run-pipeline `((cat) (grep "ho") (wc)) :input :pipe))

p @result{} #<process 20658 "wc" active>

(process-upstreams p)
  @result{} (#<process 20656 "cat" active> #<process 20657 "grep" active>)
@end example
@end defun

@defun process-list
@c MOD gauche.process
@c EN
Returns a list of active processes.  The process remains active
until its exit status is explicitly collected by @code{process-wait}.
Once the process's exit status is collected and its state changed
to inactive, it is removed from the list @code{process-list} returns.
@c JP
アクティブなプロセスのリストを返します。プロセスは、その終了ステータスが
@code{process-wait} によって明示的に回収されない場合は、アクティブなまま
残ります。
ひとたび終了ステータスが回収され、プロセスの状態がインアクティブに
変更されると、そのプロセスは@code{process-list}が返すリストからは除かれます。
@c COMMON
@end defun

@defun process-wait process :optional nohang error-on-nonzero-status
@c MOD gauche.process
@c EN
Obtains the exit status of the subprocess @var{process}, and stores it
to @var{process}'s status slot.  The status can be obtained by
@code{process-exit-status}.

This suspends execution until @var{process} exits by default.
However, if a true value is given to the optional argument @var{nohang},
it returns immediately if @var{process} hasn't exit.

If a true value is given to the optional argument
@var{error-on-nonzero-status}, and the obtained status code is not zero,
this procedure raises @code{<process-abnormal-exit>} error.

Returns @code{#t} if this call actually obtains the exit status,
or @code{#f} otherwise.
@c JP
サブプロセス @var{process} の終了ステータスを取得し、@var{process}
のstatusスロットに値を格納します。statusスロットの値は
@code{process-exit-status}で得ることができます。

デフォルトでは、この手続きは@var{process} が終了するまで実行を一時停止します。
しかし、@var{nohang}に真の値が与えられた場合は、@var{process}が終了して
いない場合にも直ちに返ります。

オプショナル引数@var{error-on-nonzero-status}に真の値が与えられた場合、
この手続きは得られた終了ステータスが0で無い場合に
@code{<process-abnormal-exit>}エラーを投げます。

この呼び出しによって@var{process}の終了ステータスが実際に取得された場合は
@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON

@c EN
If the process object is created by @code{run-pipeline}
(@pxref{Running process pipeline}), @code{process-wait} waits
@emph{all} of the subprocesses in the pipeline, not just the last one,
unless true value is given to the @var{nohang} argument.
However, @var{error-on-nonzero-status} only affects to the status
of @var{process}, which represents the last process in the pipeline;
if an other subprocess exits with nonzero status, it is stored in
its respective process objects, but won't cause a fuss.

If you specify a true value to @var{nohang} for the pipelined
process, @code{process-wait} still
probes other subprocesses in the pipeline and updates exit statuses
of terminated ones, but doesn't wait unterminated subprocesses.
The unterminated subprocesses should be waited individually, or
by @code{process-wait-any}, to collect their exit statuses.
@c JP
プロセスオブジェクトが@code{run-pipeline}によって作られたものである場合、
@code{process-wait}は、@var{nohang}に真の値が与えられなければ、
パイプラインに関わる全てのサブプロセスの終了を待ちます。
但し、@var{error-on-nonzero-status}は@var{process}引数、すなわちパイプラインの
最後のプロセスにしか効力を持ちません。その他のサブプロセスがステータス0以外で終了
したとしても、その事実は各サブプロセスのプロセスオブジェクトに記録されるだけで、
エラーは通知されません。

パイプラインのプロセスに対して@var{nohang}に真の値を指定した場合、
@code{process-wait}はパイプラインの上流のプロセスに対しても終了のチェックを
行い、終了していた場合は対応するプロセスオブジェクトの終了ステータスを更新しますが、
終了していないサブプロセスについてはそのままにします。
それらのサブプロセスの終了ステータスを回収するには、それぞれのプロセスオブジェクト
について@code{process-wait}を発行するか、下の@code{process-wait-any}を使います。
@c COMMON
@end defun

@defun process-wait-any :optional nohang
@c MOD gauche.process
@c EN
Obtains the exit status of any of the subprocesses created by
@code{run-process}.
Returns a process object whose exit status is collected.

If a true value is given to the optional argument @var{nohang}, this procedure
returns @code{#f }immediately even if no child process has exit.
If @var{nohang} is omitted or
@code{#f}, this procedure waits for any of children exits.

If there's no child processes, this procedure immediately returns @code{#f}.
@c JP
@code{run-process}で作られたサブプロセスのどれかの終了ステータスを取得します。
終了ステータスが取得できたプロセスのプロセスオブジェクトを返します。

真の値が@var{nohang}に与えられた場合は、どの子プロセスも終了していない場合は
直ちに@code{#f}を返します。そうでなければ、この手続きはいずれかの子プロセスが
終了するまで待ちます。

子プロセスが存在しない場合は、この手続きは直ちに@code{#f}を返します。
@c COMMON
@end defun

@defun process-wait/poll process :key interval max-wait continue-test raise-error?
@c MOD gauche.process
@c EN
Polls wait status of @var{process} periodically, sleeping
@var{interval} nanoseconds (default 2e6 ns, i.e. 2ms) between each poll.
It returns as soon as it finds the process has exitted and its status is
retrieved.

If @var{max-wait} is given and not @code{#f}, it species maximum duration
in nanoseconds to keep polling.  Once the duration expires, the procedure
gives up and return.  If it is not given or @code{#f},
the procedure keeps polling until the process exits.

The @var{continue-test}, if given and not @code{#f}, must be a procedure
that takes one argument, poll count.  It is called after each unsuccessul
polling (that is, the process hasn't been exitted), and the argument begins
with 0 and incretemented for each callback.  The procedure can return
@code{#f} to give up polling.  When it returns a true value, polling continues.

The @var{raise-error?} argument is the same as @code{process-wait}; an
error is raised if @var{process}'s exit status isn't zero.

The procedure returns @code{#t} if the process exitted, and @code{#f} if
it has given up.  The process's exit status should be retrieved
with @code{process-exit-status} from @var{process}.
@c JP
@var{process}の終了ステータスを、@var{interval}ナノ秒間隔でポーリングします
(デフォルトは2e6ns=2msです)。@var{process}が終了していることを見つけたら
終了ステータスを回収して直ちに戻ります。

@var{max-wait}が指定されて@code{#f}でなければ、それはポーリングを続ける期間の
最大値をナノ秒単位で指定します。その期間が過ぎたら、この手続きは諦めて戻ります。
指定されないか@code{#f}の場合は、プロセスが終了するまでポーリングしつづけます。

@var{continue-test}が与えられて@code{#f}でなければ、
それは1引数の手続きでなければなりません。
ポーリングでプロセスが終了してなかったら、その度にこの手続きが呼ばれます。
引数はポーリングした回数で、0から始まりポーリングの度に1つづつ増えてゆきます。
この手続きが@code{#f}を返したら、その時点でポーリングは打ちきられ
@code{process-wait/poll}は直ちに戻ります。
真の値を返したらポーリングは継続されます。

@var{raise-error?}は@code{process-wait}と同じで、
@var{process}の終了ステータスが0でなければエラーを投げます。

戻り値は、プロセスが終了してステータスを回収できれば@code{#t}、
途中で諦めた場合は@code{#f}となります。終了ステータス自体は
@var{process}から@code{process-exit-status}で読み出してください。
@c COMMON
@end defun


@defun process-exit-status process
@c MOD gauche.process
@c EN
Returns exit status of @var{process} retrieved by @code{process-wait}.
If this is called before @code{process-wait} is called on @var{process},
the result is undefined.

The meaning of exit status depends on the platform.  You need to
use @code{sys-wait-exited?} or @code{sys-wait-signaled?} to
see if it is terminated voluntarily or by a signal, and
use @code{sys-wait-exit-status} or @code{sys-wait-termsig}
to extract the exit code or the terminating signal
(@pxref{Process management}).
@c JP
@code{process-wait}によって取得された@var{process}の終了ステータスを
返します。@var{process}に対して@code{process-wait}を呼ぶ前にこの手続きを
呼んだ場合の結果は未定義です。

終了ステータスの解釈はプラットフォームに依存します。プロセスが自発的に
(@code{exit}を呼んで)終了したか、それともシグナルによって終了させられたかを
確かめるには@code{sys-wait-exited?}か@code{sys-wait-signaled?}を
使ってください。また、終了コードもしくは終了と原因となったシグナルを
知るには@code{sys-wait-exit-status}を@code{sys-wait-termsig}
使ってください (@ref{Process management}参照)。
@c COMMON
@end defun

@defun process-send-signal process signal
@c MOD gauche.process
@c EN
Sends a signal @var{signal} to the subprocess @var{process}.
@var{signal} must be an exact integer for signal number.
@xref{Signal}, for predefined variables of signals.
@c JP
サブプロセス @var{process} にシグナル @var{signal} を送ります。
@var{signal} は正確整数のシグナルナンバーでなければなりません。
シグナルの定義済み変数については、@ref{Signal}を参照して下さい。
@c COMMON
@end defun

@defun process-kill process
@defunx process-stop process
@defunx process-continue process
@c MOD gauche.process
@c EN
Sends SIGKILL, SIGSTOP and SIGCONT to @var{process}, respectively.
@c JP
それぞれ、@var{process} に、SIGKILL、SIGSTOP、SIGCONT を送ります。
@c COMMON
@end defun

@defun process-shutdown process :key ask ask-interval ask-retry signals signal-interval
@c EN
Tries to terminate @var{process} in the gradually escalating means.
@c JP
@var{process}を、徐々に強力な方法を使って終了させようとします。
@c COMMON

@c EN
The @var{ask} argument is, if not @code{#f}, a procedure taking one argument,
the retry count.  The @var{ask} procedure is responsible to interact with
@var{process} in a proper protocol (e.g. send @code{exit} command via
comminucation channel).  After @var{ask} is executed (the return value
is ignored), the process's status is monitored, and
@code{process-shutdown} returns @code{#t} as soon as the
process exits.  If the process doesn't exit, the procedure repeats
calling @var{ask} up to @var{retry} times, with @var{ask-interval} nanoseconds
delay inbetween, incrementing the retry count
argument.   If @var{ask} argument is @code{#f}, this step is skipped.
The default value of @var{ask} is @code{#f}, @var{ask-interval} is
50e6 ns (50ms), and @var{ask-retry} is 1.
@c JP
@var{ask}引数は、@code{#f}でなければ、試行回数を引数にとる手続きでなければなりません。
@var{ask}手続きは@var{process}に何らかの方法で作用して終了を試みるものです
(例えば、通信チャネルから@code{exit}コマンドを送る等)。
@var{ask}を呼び出し後(戻り値は捨てられます)、プロセスの状態が検査され、
プロセスがexitしたら直ちに@code{process-shutdown}は@code{#t}を返します。
プロセスがすぐにexitしなければ、@var{ask-interval}ナノ秒おきに@var{ask}手続きが
最大@var{retry}回まで呼び出されます。@var{ask}に渡される引数は呼び出しの度に
インクリメントされます。
@var{ask}引数に@code{#f}が渡された場合、このステップは省かれます。
省略時のデフォルト値は、@var{ask}が@code{#f}、@var{ask-interval}が50e6 ns (50ms)、
@var{ask-retry}が1です。
@c COMMON

@c EN
If the first step fails, this procedure starts sending signals.
The process's status is checked every time after a signal is sent.
As soon as the process exists, @code{process-shutdown}
returns @code{#t}.
The sequence of signals is specified by @var{signals} argument,
and the interval of sending signals is specified by @var{signal-interval}
argument.  The default value of @var{signals} is
@code{(list SIGTERM SIGTERM SIGKILL)}, and @var{singal-interval} is
50e6 ns (50ms).
@c JP
最初のステップでプロセスが止まらなければ、次にシグナルを送り始めます。
シグナルが送られるたびにプロセスの状態が検査され、終了していれば直ちに
@code{process-shutdown}は@code{#t}を返します。
どのシグナルが送られるかは@var{signals}引数で決まり、
またシグナルを送る間隔は@var{signal-interval}で指定されます。
@var{signals}のデフォルト値は@code{(list SIGTERM SIGTERM SIGKILL)}、
@var{signal-interval}のデフォルト値は50e6 ns (50ms)です。
@c COMMON

@c EN
If all the measures fail, @code{#f} is returned.
@c JP
全てを試みてもまだプロセスが終了していなければ、@code{#f}が返されます。
@c COMMON

@c EN
(Hint: If you wants to keep sending signals until the process really
exits, you can pass a circular list to the @var{signals}.)
@c JP
(ヒント: プロセスが終了するまでシグナルを送りつづけたければ、
@var{signals}に循環リストを渡すことで実現できます)
@c COMMON
@end defun

@node Process ports, Process connection, Process object, High-level process interface
@subsection Process ports
@c NODE プロセスポート

@defun open-input-process-port command :key input error encoding conversion-buffer-size
@c MOD gauche.process
@c EN
Runs @var{command} asynchronously in a subprocess.  Returns
two values, an input port which is connected to the stdout of the
running subprocess, and a process object.
@c JP
@var{command} を子プロセスで非同期に実行します。
走らせた子プロセスの標準出力につながれた入力ポートと、
プロセスオブジェクトの二つの値を返します。
@c COMMON

@c EN
@var{Command} can be a string, a list of command name and arguments,
or a list of lists of command name and arguments.

If it is a string, it is passed to @code{/bin/sh}.
You can use shell metacharacters in this form, such as
environment variable interpolation, globbing, and redirections.
If you create the command line by concatenating strings,
it's your responsibility to ensure escaping special characters
if you don't want the shell to interpret them.
The @code{shell-escape-string} function in @code{text.sh} might
be a help (@pxref{Shell text utilities}).
@c JP
@var{command}は文字列か、コマンド名と引数のリストか、「コマンド名と引数のリスト」のリストです。

文字列の場合、それは@code{/bin/sh}に渡されます。
環境変数の置換やグロブパターン、リダイレクトなどのシェルの機能が
文字列中で使えます。
文字列をつなぎ合わせてコマンドラインを作成する場合、
特殊文字をシェルに解釈してほしくなければ、それを正しくエスケープするのは
呼び出し元の責任です。@code{text.sh}の@code{shell-escape-string}は
助けになるかもしれません(@ref{Shell text utilities}参照)。
@c COMMON

@c EN
If @var{command} is a list (but not a list of lists),
each element is converted to a
string by @code{x->string} and then passed directly to @code{sys-exec}
(the @code{car} of the list is used as both the command path
and the first element of argv, i.e. @code{argv[0]}).
Use this form if you want to avoid the shell from interfering;
i.e. you don't need to escape special characters.
@c JP
@var{command}がリスト(ただしリストのリストではない)の場合は、
各要素が@code{x->string}で文字列に
変換された後に、@code{sys-exec}を使って直接コマンドを起動します
(リストの@code{car}がコマンドのパス名と@code{argv[0]}の両方に使われます)。
シェルの介入を避けたい場合はこの形式を使うと良いでしょう。
特殊文字をエスケープする必要はありません。
@c COMMON

@c EN
The subprocess's stdin is redirected from @code{/dev/null},
and its stderr shares the calling process's stderr by default.
You can change these by giving file pathnames to @var{input} and
@var{error} keyword arguments, respectively.
@c JP
デフォルトでは、子プロセスの標準入力は@code{/dev/null}にリダイレクトされ、
標準エラー出力は呼び出したプロセスと共有されます。
@var{input}と@var{error}キーワード引数にパス名を与えることで、
これらの出力をリダイレクトすることができます。
@c COMMON

@c EN
If @var{command} is a list of lists, it creates a command pipeline,
as in @code{run-pipeline} (@pxref{Running process pipeline}).
Each inner list should consists of a command path, followed by command-line
arguments.  They are applied on @code{x->string} before passed to
@code{sys-exec}.
The stdout of the last command is available from the returned input port,
and the stdin of the first command is provided by @var{input} keyword
arguments, or @code{/dev/null} by default.  The stderr of all the commands
goes to @var{error} keyword arguments if given, or shared with
the caller process's stderr.
@c JP
@var{command}がリストのリストの場合は、コマンドパイプラインが作られます
(@code{run-pipeline}, @ref{Running process pipeline}参照)。
内側のリストは、コマンドパスとそのコマンドへの引数で、@code{x->string}で文字列に
変換された後、@code{sys-exec}に渡されます。
最後のコマンドの標準出力を、返されるポートから読み出すことができます。
最初のコマンドの標準入力は、@var{input}キーワード引数にパス名が渡されれば
そのファイルから、そうでなければ@code{/dev/null}から供給されます。
各コマンドの標準エラー出力は、@var{error}キーワード引数にパス名が渡されればそのファイルに、
そうでなければ呼び出したプロセスの標準エラー出力に流れます。
@c COMMON

@c EN
You can also give the @var{encoding} keyword argument
to specify character encoding of the process output.  If it is
other than @code{utf-8},
@code{open-input-process-port} inserts a character encoding
conversion port.
If @var{encoding} is given, the @var{conversion-buffer-size} keyword
argument can control the conversion buffer size.
See @ref{Character code conversion}, for
the details of character encoding conversions.
@c JP
また、プロセスの出力の文字エンコーディングを指定するために
@var{encoding}キーワード引数を与えることもできます。
それが@code{utf-8}でなければ、
@code{open-input-process-port}は文字コード変換ポートを挿入します。
@var{encoding}が与えられた場合、@var{conversion-buffer-size}キーワード引数で
変換バッファの大きさを指定することも可能です。文字コード変換の詳細については
@ref{Character code conversion}を参照して下さい。
@c COMMON
@example
(receive (port process) (open-input-process-port "ls -l Makefile")
  (begin0 (read-line port)
          (process-wait process)))
 @result{} "-rw-r--r--   1 shiro    users        1013 Jun 22 21:09 Makefile"

(receive (port process) (open-input-process-port '(ls -l "Makefile"))
  (begin0 (read-line port)
          (process-wait process)))
 @result{} "-rw-r--r--   1 shiro    users        1013 Jun 22 21:09 Makefile"

(open-input-process-port "command 2>&1")
 @result{} ;@r{the port reads both stdout and stderr}

(open-input-process-port "command 2>&1 1>/dev/null")
 @result{} ;@r{the port reads stderr}
@end example
@c EN
The exit status of subprocess is not automatically collected.
It is the caller's responsibility to issue @code{process-wait},
or the subprocess remains in a zombie state.  If it bothers you,
you can use one of the following functions.
@c JP
サブプロセスの終了ステータスは自動的に回収されません。
@code{process-wait} を呼ぶことは呼び出し側の責任であり、これを怠ると
サブプロセスはゾンビプロセスになります。それが面倒であれば、以下の
手続きを使うことができます。
@c COMMON
@end defun

@defun call-with-input-process command proc :key input error encoding conversion-buffer-size on-abnormal-exit
@c MOD gauche.process
@c EN
Runs @var{command} in a subprocess and pipes its stdout
to an input port, then call @var{proc} with the port as an argument.
When @var{proc} returns, it collects its exit status,
then returns the result @var{proc} returned.
The cleanup is done even if @var{proc} raises an error.

The keyword argument @var{on-abnormal-exit} specifies what happens
when the child process exits with non-zero status code.
It can be either @code{:error} (default), @code{:ignore},
@code{#f}, or a procedure that takes one argument.  If it is @code{:error},
a @code{<process-abnormal-exit>} error condition is thrown by
non-zero exit status; the @code{process} slot of the condition
holds the process object.  If it is @code{:ignore}, nothing is done
for non-zero exit status.  If it is @code{#f}, the result of
@var{proc} is discarded and @code{#f} is returned.
If it is a procedure, it is called with
a process object; when the procedure returns, @code{call-with-input-process}
returns normally.

Note that @var{on-abnormal-exit} differs from @code{do-process}
(@pxref{Running subprocess}).  We want finer control over the situation
than merely check if the subprocess is succeeded or failed.

The semantics of @var{command} and other keyword arguments are the same
as @code{open-input-process-port} above.
@c JP
子プロセスで@var{command} を実行し、その標準出力と入力ポートを
パイプで繋ぎ、そのポートを引数として @var{proc} を呼び出します。
@var{proc} が返るとその終了ステータスを回収し、@var{proc} が返した
結果を返します。@var{proc} がエラーを通知しても、クリーンアップは
行われます。

キーワード引数@var{on-abnormal-exit}は子プロセスが0以外の終了ステータス
を返した場合の振舞いを指定します。その値は@code{:error}(デフォルト)、
@code{:ignore}、@code{#f}、もしくは一引数の手続きでなければなりません。
値が@code{:error}の場合、0以外の終了ステータスは
@code{<process-abnormal-exit>}エラーコンディションを発生させます。
コンディションオブジェクトの@code{process}スロットには子プロセスオブジェクトが
保持されます。値が@code{:ignore}の場合、0以外の終了ステータスに対して
特別なアクションは取られません。値が@code{#f}の場合、プロセスの終了ステータスが
0以外であれば、@var{proc}の結果は捨てられ、@code{#f}が返されます。
値が手続きの場合、0以外の終了ステータスに対して
子プロセスオブジェクトを引数にしてその手続きが呼ばれます。その手続きが
戻れば、@code{call-with-input-process}は正常動作と同じように戻ります。

@var{on-abnormal-exit}の意味が@code{do-process}とは異なることに注意してください
(@ref{Running subprocess}参照)。この手続きを使う場合は、
単にサブプロセスの成功/失敗を知るだけでなく、より細かな制御を必要とする場合が多いからです。

@var{command}および他のキーワード引数の意味は@code{open-input-process-port}と
同じです。
@c COMMON
@example
(call-with-input-process "ls -l *"
  (lambda (p) (read-line p)))
@end example
@end defun

@defun with-input-from-process command thunk :key input error encoding conversion-buffer-size on-abnormal-exit
@c MOD gauche.process
@c EN
Runs @var{command} in a subprocess, and calls @var{thunk}
with its current input port connected to the command's stdout.
The command is terminated and its exit status is collected,
after @var{thunk} returns or raises an error.

The semantics of @var{command} and keyword arguments are the same
as @code{call-with-input-process} above.
@c JP
子プロセスで @var{command} を実行し、コマンドの標準出力に
接続された現在の入力ポートとともに @var{thunk} を呼び出します。
@var{thunk}が終了するかエラーを投げた後に、コマンドの終了ステータスが
回収されます。

@var{command}およびキーワード引数の意味は@code{call-with-input-process}と
同じです。
@c COMMON
@example
(with-input-from-process "ls -l *" read-line)
@end example
@end defun

@defun open-output-process-port command :key output error encoding conversion-buffer-size
@c MOD gauche.process
@c EN
Runs @code{command} in a subprocess asynchronously.  Returns two values,
an output port which is connected to the stdin of the subprocess.
and the process object.

The semantics of @var{command} is the same as
@code{open-input-process-port}.  The semantics of
@var{encoding} and @var{conversion-buffer-size} are also the same.

The subprocess's stdout is redirected to @code{/dev/null} by default,
and its stderr shares the calling process's stderr.
You can change these by giving file pathnames to @var{output} and
@var{error} keyword arguments, respectively.

The exit status of the subprocess is not automatically collected.
The caller should call @code{process-wait} on the subprocess
at appropriate time.
@c JP
子プロセスで @code{command} を非同期に実行します。
子プロセスの標準入力に接続された出力ポートと、
プロセスオブジェクトの二つの値を返します。

@var{command}引数、および@var{encoding}と@var{conversion-buffer-size}の
意味は、@code{open-input-process-port}と同じです。

デフォルトでは、子プロセスの標準出力は@code{/dev/null}にリダイレクトされ、
標準エラー出力は呼び出したプロセスと共有されます。
@var{output}と@var{error}キーワード引数にパス名を与えることで、
これらの出力をリダイレクトすることができます。

サブプロセスの終了ステータスは自動的には回収されません。
適切なタイミングで、サブプロセスに対して @code{process-wait} を呼ぶ
必要があります。
@c COMMON
@end defun

@defun call-with-output-process command proc :key output error encoding conversion-buffer-size on-abnormal-exit
@c MOD gauche.process
@c EN
Runs @code{command} in a subprocess, and calls @var{proc}
with an output port which is connected to the stdin of the command.
The exit status of the command is collected after either @var{proc}
returns or raises an error.

The semantics of keyword arguments are the same as
@code{open-output-process-port}, except @var{on-abnormal-exit},
which is the same as described in @code{call-with-input-process}.
@c JP
@code{command} を子プロセスで実行し、コマンドの標準入力に
接続された出力ポートとともに @var{proc} を呼び出します。
コマンドの終了ステータスは、@var{proc} が返るかエラーを通知した
後に回収されます。

キーワード引数の意味は@var{open-output-process-port}と同じです。
ただし@var{on-abnormal-exit}については@code{call-with-input-process}
で説明したのと同じ意味です。
@c COMMON
@example
(call-with-output-process "/usr/sbin/sendmail"
  (lambda (out) (display mail-body out)))
@end example
@end defun

@defun with-output-to-process command thunk :key output error encoding conversion-buffer-size on-abnormal-exit
@c MOD gauche.process
@c EN
Same as @code{call-with-output-process}, except that the
output port which is connected to the stdin of the command
is set to the current output port while executing @var{thunk}.
@c JP
コマンドの標準入力に接続された出力ポートが、@var{thunk} の実行中は
現在の出力ポートにセットされることを除いて、@code{call-with-output-process}
と同じです。
@c COMMON
@end defun

@defun call-with-process-io command proc :key error encoding conversion-buffer-size on-abnormal-exit
@c MOD gauche.process
@c EN
Runs @var{command} in a subprocess, and calls @var{proc}
with two arguments; the first argument is an input port which
is connected to the command's stdout, and the second is an output
port connected to the command's stdin.  The error output from
the command is shared by the calling process's, unless
an alternative pathname is given to the @var{error} keyword argument.

The exit status of the command is collected when @var{proc}
returns or raises an error.
@c JP
@var{command} をサブプロセスで実行し、@var{proc} を2つの引数と
ともに呼び出します。最初の引数は入力ポートで、コマンドの標準出力に
接続されたものです。2番目の引数は出力ポートでコマンドの標準入力に
接続されたものです。コマンドからのエラー出力は、@var{error}キーワード
引数でパス名が指定されない限り、呼び出したプロセスのエラー出力が共有されます。

コマンドの終了ステータスは、@var{proc}が戻るかエラーを投げた場合に
回収されます。
@c COMMON
@end defun

@defun process-output->string command :key error encoding conversion-buffer-size on-abnormal-exit
@defunx process-output->string-list command :key error encoding conversion-buffer-size on-abnormal-exit
@c MOD gauche.process
@c EN
Runs @var{command} and collects its output (to stdout) and returns them.
@code{process-output->string} concatenates all the output from @var{command}
to one string, replacing any sequence of whitespace characters to
single space.   The action is similar to ``command substitution''
in shell scripts.
@code{process-output->string-list} collects the output from
@var{command} line-by-line and returns the list of them.  Newline
characters are stripped.
@c JP
@var{command} を実行し、その(標準出力への)出力を回収して返します。
@code{process-output->string} は @var{command} からの全ての出力を連結し
1つの文字列とします。その際、空白文字からなるシーケンスは1つの空白に
置換されます。このアクションは、シェルスクリプトにおける「コマンド置換」
に似たものです。
@code{process-output->string-list} は @var{command} からの出力を行ごとに
回収し、それらをリストにしたものを返します。改行文字は削除されます。
@c COMMON

@c EN
Internally, @var{command} is run by @code{call-with-input-process},
to which keyword arguments are passed.
@c JP
内部的には、@var{command} は @code{call-with-input-process} により
実行されます。キーワード引数は@code{call-with-input-process}に
そのまま渡されます。
@c COMMON

@c EN
If you want to use this just like shell's command substituion,
specifying @code{:on-abnormal-exit :ignore} is usually what you want.
However, if you try another command when one fails,
@code{:on-abnormal-exit #f} may be suitable, for @code{:ignore}
returns empty string when the command fails without producing output.
@c JP
シェルのコマンド置換と同じように使いたい場合、
通常は @code{:on-abnormal-exit :ignore} を指定するのが良いでしょう。
ただし、ひとつコマンドを試してそれが失敗したら別のを試す、という場合は
@code{:on-abnormal-exit #f} の方が有用です。@code{:ignore}だと
コマンドが何も出力せず失敗した場合でも空文字列が返るからです。
@c COMMON

@c EN
(Tip: To receive stderr output of the child process in the result as well,
pass @code{:merge} to @code{:error}.  See @code{run-process} above
for the details.)
@c JP
(ヒント: 子プロセスのstderr出力も一緒に結果として得たい場合は、
@code{:error}引数に@code{:merge}を渡します。
詳しくは上の@code{run-process}の項を見てください。)
@c COMMON
@example
(process-output->string '(uname -smp))
  @result{} "Linux i686 unknown"

(process-output->string '(ls))
  @result{} "a.out foo.c foo.c~ foo.o"

(process-output->string-list '(ls))
  @result{} ("a.out" "foo.c" "foo.c~" "foo.o")

;; Suppress error message when the-file doesn't exist:
(process-output->string-list '(cat "the-file") :error :null)

;; If the-file doesn't exit, want to try another-file:
(any (^[flie] (process-output->string-list `(cat ,file)
                 :error :null :on-abnormal-exit #f))
     '("the-file" "another-file"))
@end example
@end defun

@node Process connection,  , Process ports, High-level process interface
@subsection Process connection
@c NODE プロセスコネクション

@deftp {Class} <process-connection>
@c EN
A connection abstraction to communicate with an external processs.
Inherits @code{<connection>}.
@xref{Connection framework}, for the details of the connection interface.
@c JP
外部プロセスとの通信を@code{<connection>}として見せるクラスです。
コネクションインタフェースについては@ref{Connection framework}を参照してください。
@c COMMON

@c EN
This is useful to give an external process to the code that expects
connection.  For example, instead of direct network connection, you can
insert a filter process between remote server and your client code.
@c JP
これを使うとコネクションを期待しているコードに外部プロセスを渡せます。
例えばネットワークと通信する部分を、直接の通信のかわりにリモートサーバの間に
フィルタプロセスを入れる、といったことが簡単にできます。
@c COMMON
@end deftp

@defun make-process-connection process-or-spec
@c EN
Run an external process and returns a connection that's connected
to standard I/O of the process.
@c JP
外部プロセスを起動し、その標準入出力とコネクションとして通信する
コネクションオブジェクトを返します。
@c COMMON

@c EN
You can pass a list of command and its arguments, or
a @code{<process>} object, to the @var{process-or-spec} argument.
If you it's a @code{<process>} object, it's stdin and stdout
must be connected to pipes.  If it is a list, it is passed to @code{run-process}
to run a new process.
@c JP
@var{process-or-spec}にはコマンドと引数からなるリストか、
@code{<process>}オブジェクトを渡すことができます。
@code{<process>}オブジェクトならそのプロセスの標準入力と標準出力はパイプに
なっていなければなりません。
リストの場合は、それが@code{run-process}に渡されて新たなプロセスが起動されます。
@c COMMON

@c EN
Shutting down both channels of the connection terminates the process.
Most processes that reads from stdin would exits after it reads EOF
from input, so we just poll the process exit status for a short period of time.
If the process doesn't exit, we send signals (first SIGTERM, then SIGKILL)
to ensure the termination of the process.
@c JP
コネクションの入出力チャネルを両方ともシャットダウンすれば、プロセスは終了します。
多くのプロセスは、標準入力からEOFを読むと終了するので、
まずは標準入力へのチャネルをシャットダウンしてから少し待ちます。
もしそれでプロセスが終了する気配を見せなかった場合、シグナルSIGTERMを送り、
それでも終了しなかったらSIGKILLを送ります。
@c COMMON

@c EN
Merely closing the connection doesn't terminate the process, so that
the forked process can keep talking to the process.
@c JP
コネクションをクローズするだけではプロセスは終了しません。
forkしたプロセスがまだ通信するかもしれないからです。
@c COMMON
@end defun


@c ----------------------------------------------------------------------
@node Record types, Reloading modules, High-level process interface, Library modules - Gauche extensions
@section @code{gauche.record} - Record types
@c NODE レコード型, @code{gauche.record} - レコード型

@deftp {Module} gauche.record
@mdindex gauche.record
@c EN
This module provides a facility to define @emph{record types},
user-defined aggregate types.
The API is upper compatible to SRFI-9 (Defining Record Types) and
SRFI-99 (ERR5RS Records).
@c JP
このモジュールは、@emph{レコード型}、すなわち、ユーザ定義の集合型を定義する機能を提供します。
APIは、SRFI-9 (Defining Record Types) および SRFI-99 (ERR5RS Records)
の上位互換です。
@c COMMON
@end deftp

@c EN
Record types are implemented as Gauche's classes,
but have different characteristics from the general classes.
@xref{Record types introduction}, for when you want to
use record types.
@c JP
レコード型は、Gaucheのクラスとして実装されていますが、
一般的なクラスとは異なる特徴を持っています。
どういった時にレコード型を使うと良いかについては
@ref{Record types introduction}を参照してください。
@c COMMON

@c EN
The record API consists of three layers, following
SRFI-99 and R6RS design.
@c JP
レコードAPIは、SRFI-99およびR6RSの設計に従い、3つの層から構成されています。
@c COMMON

@c EN
The syntactic layer is the @code{define-record-type} macro
that conveniently defines a record type and related procedures
(a constructor, a predicate, accessors and modifiers) all at once
declaratively.   Knowing this macro alone is sufficient for
most common usage of records.
@c JP
構文層は、@code{define-record-type}マクロで、レコード型と関連する手続き
(コンストラクタ、述語、アクセサ、モディファイア)を、
一括して宣言的に定義します。このマクロを知っているだけで、
ほとんどの一般的なレコードの使用方法においては十分です。
@c COMMON

@c EN
The inspection layer defines common procedures
to query information to the records and record types.
@c JP
インスペクション層は、レコードおよびレコード型の情報を問い合わせるための
共通の手続きを定義します。
@c COMMON

@c EN
The procedural layer is a low-level machinery to implement
the syntactic layer; you don't usually need to use them
in day-to-day programming, but they might be handy to
create record types on-the-fly at runtime.
@c JP
手続き層は、構文層を実装するための低レベルの機構です。
日常的なプログラミングにおいて使う必用はありませんが、
実行時にその場でレコード型を作成するような場合には便利かもしれません。
@c COMMON

@menu
* Record types introduction::
* Record types syntactic layer::
* Record types inspection layer::
* Record types procedural layer::
* Pseudo record types::
@end menu

@node Record types introduction, Record types syntactic layer, Record types, Record types
@subsection Introduction
@c NODE レコード型のイントロダクション, イントロダクション

@c EN
Gauche provides a general way for users to define new types as new
classes, using object system (@pxref{Object system}), and indeed
record types are implemented as Gauche's classes.
However, using record types instead of classes has several advantages.
@c JP
Gaucheは、オブジェクトシステム(@ref{Object system}参照)により、
新しい型を新しいクラスとして定義する一般的な方法を提供しています。
そして、実際にレコード型はGaucheのクラスとして実装されています。
しかし、クラスではなくレコード型を使うことには、いくつかの利点があります。
@c COMMON

@itemize
@item
@c EN
It is portable.  The API conforms two major record SRFIs,
SRFI-9 and SRFI-99, so the code using record types can run on
various Scheme systems.
@c JP
ポータブルであること。 APIは2つの有名なレコードSRFIであるSRFI-9とSRFI-99に適合しています。
このため、レコード型を使用したコードは、様々なSchemeシステム上で動作します。
@c COMMON
@item
@c EN
It is efficient.  Record types are less flexibile than classes,
but that allows Gauche to optimize more.  Hence creating records and
accessing/modifying them are much faster than creating instances
of general classes and accessing/modifying them.  It makes record
types preferable choice when you only need a mechanism to bundle
several related values to carry around, and don't need fancier
mechanisms such as class redefinitions.
@c JP
効率的であること。 レコード型はクラスほど柔軟ではありませんが、
このためGaucheはより最適化を行えます。したがって、レコードを作成し、
それらにアクセス/変更することは、一般的なクラスのインスタンスを作成して、
それらにアクセス/変更することよりも高速に行えます。
いくつかの関連する値をまとめて運用するメカニズムがほしいだけであり、
クラスの再定義のような手の込んだメカニズムが不要な場合には、
レコード型は良い選択肢になります。
@c COMMON
@item
@c EN
As Gauche's extension, you can define pseudo record types,
which interprets ordinary aggregate types such as vectors and lists
as records.  (For Common Lisp users; it is like the @code{:type}
option of @code{defstruct}).
This helps flexibility of interface.  For example, you can ask
your library's users to pass a point in a vector of three numbers,
instead of asking users to pack their point data into your
custom point record type.  Yet inside your library you can
treat the passed data as if it is your point record type.
See @ref{Pseudo record types}, for more details.
@c JP
Gaucheの拡張として、疑似レコード型を定義することができます。
これは、ベクタやリストのような通常の集合型を、レコードとして扱うものです
(Common Lisp ユーザにとっては、@code{defstruct}の@code{:type}が近いものです)。
これは、インタフェースの柔軟性向上に役立ちます。
例えば、あなたのライブラリのユーザに、
独自の座標レコード型に座標データを格納するように依頼するのではなく、
3個の数値を持つベクタを渡すように依頼することができます。
そしてライブラリ内では、渡されたデータを座標レコード型として扱うことができるのです。
詳しくは、@ref{Pseudo record types}を参照してください。
@c COMMON
@end itemize

@c EN
On the other hand, record types restrict some flexibilities
of Gauche's standard classes.
@c JP
一方で、レコード型はGaucheの標準なクラスに比べて柔軟性を制限されています。
@c COMMON

@itemize @bullet
@item
@c EN
Only single inheritance is allowed.  This is from SRFI spec, and
(with the slot inheritance rule) it makes the slot offset fixed
and allows optimizing accessors.
(Gauche relaxes this and allows mixin classes as long as they are
pure interface, e.g. they don't have slots.
It allows a new record type to implement interfaces
such  as @code{<collection>}.)
@c JP
単一継承しか許されません。これはSRFIの仕様からで、
スロット継承ルールと相まって、スロットのオフセットを固定することができ、
アクセサの最適化に寄与します。
(Gaucheはこの制限を若干緩めて、@code{<collection>}のような純粋なインタフェース、
すなわちスロットを持たないクラスならミックスインとして
多重継承できるようにしています)。
@c COMMON
@item
@c EN
The @code{initialize} method is not called.  SRFI records does
not have a way to initialize records except slots specified
in the constructor call.  Allowing extra initialization diverges
from it.
@c JP
@code{initialize}メソッドは呼ばれません。
SRFIレコードはコンストラクタ呼び出しに渡されるスロット以外を初期化する
手段を持たないのでそれに合わせてあります。
@c COMMON
@item
@c EN
Record types don't obey Gauche's class redefinition
protocol (@pxref{Class redefinition}).
That is, if you redefine a record with the same name,
it creates a new record type unrelated to the old one.
The record instances created from the old definition
won't be updated according to the new definition.
@c JP
レコード型は、Gaucheのクラス再定義プロトコル(@ref{Class redefinition}を参照)
に従いません。
すなわち、同じ名前でレコードを再定義すると、
古いものとは無関係の新しいレコード型が作成されます。
古い定義で作成されたレコードのインスタンスは、
新しい定義によって更新されることはありません。
@c COMMON
@end itemize

@c EN
More importantly, record constructors, accessors and modifiers
are tend to be inlined where they are used, to achieve
better performance.   Since they are inlined, the code
that uses those procedures are not affected when
the record type is redefined.
This means if you redefine a record type, you have to
reload (recompile) the sources that uses any of
record constructors, accessors or modifiers.
@c JP
さらに重要なこととして、
レコードのコンストラクタ、アクセサ、および、モディファイアは、
パフォーマンス向上のため、使用箇所でインライン展開される傾向があります。
インライン展開により、これらの手続きを使用するコードは、
レコード型が再定義されても影響を受けません。
これは、レコード型を再定義した場合、レコードのコンストラクタ、アクセサ、
または、モディファイアを使用するソースは、
再ロード(再コンパイル)する必用があることを意味します。
@c COMMON

@c EN
You can use record types for simple, passive, plain old aggregate data.
If you want to do anything more sophisicated, you'd want to use
@code{define-class} instead.
@c JP
レコード型は、単純で受動的な「plain old data」に使うのに適しています。
それ以上に込み入ったことが必要なら、@code{define-class}を使ってください。
@c COMMON


@node Record types syntactic layer, Record types inspection layer, Record types introduction, Record types
@subsection Syntactic Layer
@c NODE レコード型の構文層, 構文層


@defmac define-record-type type-spec ctor-spec pred-spec field-spec @dots{}
[R7RS base][SRFI-9][SRFI-99+]
@c MOD gauche.record
@c EN
Defines a record type, and optionally defines
a constructor, a predicate, and field accessors and modifiers.
@c JP
レコード型を定義し、オプションとしてコンストラクタ、述語、
フィールドのアクセサ、および、モディファイアを定義します。
@c COMMON

@c EN
The @var{type-spec} argument names the record type,
and optionally specifies the supertype (@var{parent}).
@c JP
@var{type-spec}引数は、レコード型に名前を付けます。
また、オプションとしてスーパータイプ(@var{parent})を指定します。
@c COMMON

@example
@var{type-spec} : @var{type-name}
                | (@var{type-name} @var{parent} @var{option} @dots{})

@var{type-name} : @r{identifier}
@var{parent} : @r{expression}
@var{option} @dots{} : @r{keyword-value list}
@end example

@c EN
The @var{type-name} identifier will be bound to a
@emph{record type descriptor}, or rtd,
which can be used for introspection and reflection.
See @ref{Record types inspection layer} and @ref{Record types procedural layer}
for possible operations for record types.
In Gauche, a record type descriptor is a @code{<class>} with a metaclass
@code{<record-meta>}.
@c JP
@var{type-name}識別子は、
レコード型記述子(@emph{record type descriptor})すなわちrtdに束縛され、
イントロスペクションやリフレクションのために使用されます。
レコード型に対して可能な操作については、@ref{Record types inspection layer}と
@ref{Record types procedural layer}を参照してください。
Gaucheでは、レコード型記述子は、メタクラス@code{<record-meta>}を持つ
@code{<class>}です。
@c COMMON

@c EN
The @var{parent} expression should evaluate to a record type descriptor.
If given, the defined record type inherits it; that is, all the
slots defined in the parent type are available to the @var{type-name}
as well, and the instance of @var{type-name} answers @code{#t} to the
predicate of the parent type.
@c JP
@var{parent}式は、レコード型記述子に評価されなければなりません。
これが与えられると、定義されるレコード型はそれを継承します。
すなわち、親の型で定義されたすべてのスロットは、
@var{type-name}でも利用可能です。そして、@var{type-name}のインスタンスは、
親の型の述語に対しても@code{#t}を返します。
@c COMMON

@c EN
Since a record type is also a class, parent type is also a superclass
of the defined record type.  However, record types are limited to
have single implementation inheritance.  The parent type must be
a subclass of @code{<record>}.  (You can have abstract classes along
the main inheritance, though.  See @var{mixins} below.)
@c JP
レコード型もまたクラスであるため、親の型は定義されるレコード型の
スーパークラスでもあります。
しかし、レコード型には単一継承のみという制限があります。
そして、親の型は@code{<record>}のサブクラスである必要があります。
(ただし、メインの継承に加えて抽象クラスを持つことができます。
下記の@var{mixins}を参照してください。)
@c COMMON

@c EN
You can give a pseudo record base type as @var{parent} to define a
pseudo record type, which allows you to access ordinary aggregates
like vectors as records.  See @ref{Pseudo record types} for more details.
@c JP
疑似レコード型を定義するために、疑似レコード型のベースタイプを
@var{parent}に指定することができます。これによって、
ベクタのような通常の集合型を、レコードとしてアクセスできるようになります。
詳しくは、@ref{Pseudo record types}を参照してください。
@c COMMON

@c EN
the @var{option} @dots{} part is Gauche's extension.  It must be a
keyword-value list.  The following keywords are recognized:
@c JP
@var{option} @dots{} の部分は、Gaucheの拡張になります。それは、
キーワードと値のリストである必要があります。次のキーワードが認識されます。
@c COMMON

@table @asis
@item @code{:mixins} (@var{class} @dots{})
@c EN
Specifies auxiliary superclasses.  The classes must be abstract, that is,
must not have slots.  It is to implement protocols in the record type,
e.g. @code{<sequence>} (@pxref{Sequence framework}).
@c JP
補助的なスーパークラスを指定します。そのクラスは抽象クラス、すなわち、
スロットを持たないクラスである必要があります。
これは、レコード型でプロトコルを実装するためのものです
(例えば、@code{<sequence>} (@ref{Sequence framework}を参照) 等)。
@c COMMON
@item @code{:metaclass} @var{metaclass}
@c EN
Specifies alternative metaclass.  By default, metaclass of record types
is @code{<record-meta>}.  If you specify an alternative metaclass,
it must be a subclass of @code{<record-meta>}.
@c JP
メタクラスを変更する場合に指定します。
デフォルトでは、レコード型のメタクラスは@code{<record-meta>}です。
他のメタクラスを指定する場合、それは@code{<record-meta>}のサブクラスである
必用があります。
@c COMMON
@end table

@c EN
The @var{ctor-spec} defines the constructor of the record instance.
@c JP
@var{ctor-spec}は、レコードのインスタンスを作るコンストラクタを定義します。
@c COMMON

@example
@var{ctor-spec} : #f | #t | @var{ctor-name}
          | (@var{ctor-name} @var{field-name} @dots{})

@var{ctor-name} : @r{identifier}
@var{field-name} : @r{identifier}
@end example

@c EN
If it is @code{#f}, no constructor is created.
If it is @code{#t}, a default constructor is created with a name
@code{make-@var{type-name}}.  If it is a single identifier
@var{ctor-name}, a default constructor is created with the name.
The default constructor takes as many arguments as
the number of fields of the record, including inherited ones if any.
When called, it allocates an instance of the record, and initialize its
fields with the given arguments in the order (inherited fields comes
first), and returns the record.
@c JP
@code{#f}を指定すると、コンストラクタは生成されません。
@code{#t}を指定すると、デフォルトのコンストラクタが@code{make-@var{type-name}}
という名前で生成されます。
単一の識別子@var{ctor-name}を指定すると、デフォルトのコンストラクタが、
その名前で生成されます。
デフォルトのコンストラクタは、レコードのフィールドの数と同じ数の引数を取ります。
これには(もしあれば)継承されたものも含まれます。
これが呼ばれると、レコードのインスタンスを割り当て、そのフィールドを
与えられた引数で順番に(継承されたフィールドが先になります)初期化し、
作成したレコードを返します。
@c COMMON

@c EN
The last variation of @var{ctor-spec} creates a custom
constructor with the name @var{ctor-name}.  The custom constructor
takes as many arguments as the given @var{field-name}s, and initializes
the named fields.  If the inherited record type has a field of the same name
as the ancestor record type, only the inherited ones are initialized.
In Gauche, uninitialized fields remains unbound until some value is
set to it.
@c JP
@var{ctor-spec}の最後のバリエーションは、
@var{ctor-name}という名前のカスタムコンストラクタを生成します。
カスタムコンストラクタは、指定した@var{field-name}の数と同じ数の引数を取り、
その名前のフィールドを初期化します。
継承されたレコード型が祖先のレコード型と同名のフィールドを持っていた場合には、
継承されたレコード型のものだけが初期化されます。
Gaucheでは、初期化されていないフィールドは、何らかの値がセットされるまでは、
未束縛のままです。
@c COMMON

@c EN
The @var{pred-spec} defines the predicate of the record instance,
which takes one argument and returns @code{#t} iff it is an instance
of the defined record type or its descendants.
@c JP
@var{pred-spec}は、レコードのインスタンスの述語を定義します。
それはひとつの引数を取り、定義されるレコード型、もしくは、その子孫の
インスタンスであるときに@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON

@example
@var{pred-spec} : #f | #t | @var{pred-name}

@var{pred-name} : @r{identifier}
@end example

@c EN
If it is @code{#f}, no predicate is created.
If it is @code{#t}, a predicate is created with a name
@code{@var{type-name}?}.  If it is a single identifier,
a predicate is created with the given name.
@c JP
@code{#f}を指定すると、述語は生成されません。
@code{#t}を指定すると、述語が@code{@var{type-name}?}という名前で生成されます。
単一の識別子を指定すると、述語がその名前で生成されます。
@c COMMON

@c EN
The rest of the arguments specify fields (slots) of the record.
@c JP
残りの引数は、レコードのフィールド(スロット)を定めます。
@c COMMON

@example
@var{field-spec}
 : @var{field-name}   ; @r{immutable, with default accessor}
 | (@var{field-name}) ; @r{mutable, with default accessor/modifier}
 | (@var{field-name} @var{accessor-name}); @r{immutable}
 | (@var{field-name} @var{accessor-name} @var{modifier-name}); @r{mutable}

@var{field-name}    : @r{identifier}
@var{accessor-name} : @r{identifier}
@var{modifier-name} : @r{identifier}
@end example

@c EN
The first and the third forms define immutable fields, which can only
be initialized by the constructor but cannot be modified afterwards
(thus such fields don't have modifiers).
The second and the fourth forms define mutable fields.
@c JP
1番目と3番目の形式は、変更不可のフィールドを定義します。
それは、コンストラクタによる初期化のみが可能であり、
後から変更することはできません
(したがって、そのフィールドは、モディファイアを持ちません)。
2番目と4番目の形式は、変更可能なフィールドを定義します。
@c COMMON

@c EN
The third and fourth forms explicitly name the accessor and modifier.
With the first and second forms, on the other hand,
the accessor is named as
@code{@var{type-name}-@var{field-name}}, and the modifier is named
as @code{@var{type-name}-@var{field-name}-set!}.
@c JP
3番目と4番目の形式は、アクセサとモディファイアの名前を明示的に指定します。
一方、1番目と2番目の形式では、
アクセサは@code{@var{type-name}-@var{field-name}}という名前になり、
モディファイアは@code{@var{type-name}-@var{field-name}-set!}という
名前になります。
@c COMMON
@end defmac

@c EN
Let's see some examples.  Here's a definition of a record
type @code{point}.
@c JP
いくつかの例を見てみましょう。これは、レコード型@code{point}の定義です。
@c COMMON

@example
(define-record-type point #t #t
  x y z)
@end example

@c EN
The variable @code{point} is bound to a record type descriptor,
which is just a class.  But you can take its class and see it is
indeed an instance of @code{<record-meta>} metaclass.
@c JP
変数@code{point}は、レコード型記述子に束縛されています。
それは、単なるクラスです。しかし、さらにそのクラスを取得してみると、
実はメタクラス@code{<record-meta>}のインスタンスでもあることが分かります。
@c COMMON

@example
point            @result{} #<class point>
(class-of point) @result{} #<class <record-meta>>
@end example

@c EN
You can create an instance of @code{point} by the default
constructor @code{make-point}.  The predicate is given the
default name @code{point?}, and you can access the fields
of the created record by @code{point-x} etc.
@c JP
デフォルトコンストラクタ@code{make-point}を使用して、
@code{point}のインスタンスを生成できます。
述語はデフォルトの名前である@code{point?}になります。
そして、生成されたレコードのフィールドには、@code{point-x}等で
アクセスできます。
@c COMMON

@example
(define p (make-point 1 2 3))

(point? p)  @result{} #t
(point-x p) @result{} 1
(point-y p) @result{} 2
(point-z p) @result{} 3
@end example

@c EN
Since we defined all fields immutable, we cannot modify
the instance @code{p}.
@c JP
すべてのフィールドを変更不可として定義したため、
インスタンス@code{p}を変更することはできません。
@c COMMON

@c EN
Here's a mutable version of point, @code{mpoint}.
You can modify its fields by modifier procedures and
generalized @code{set!}.
@c JP
以下は、pointの変更可能バージョンである@code{mpoint}です。
そのフィールドは、モディファイア手続き、および、
一般化された@code{set!}によって変更することができます。
@c COMMON

@example
(define-record-type mpoint #t #t
  (x) (y) (z))

(define p2 (make-mpoint 1 2 3)) ; @r{create an instance}

(mpoint-x p2)  @result{} 1

(mpoint-x-set! p2 4)            ; @r{default modifier}
(mpoint-x p2)  @result{} 4

(set! (mpoint-x p2) 6)          ; @r{generalized @code{set!} also works}
(mpoint-x p2)  @result{} 6
@end example

@c EN
Next one is an example of inheritance.
Note that the default constructor takes arguments for
fields of the parent record as well.
@c JP
次は、継承の例です。
デフォルトコンストラクタは、親のレコードのフィールドの分も
引数に取ることに注意してください。
@c COMMON

@example
(define-record-type (qpoint mpoint) #t #t
  (w))

(define p3 (make-qpoint 1 2 3 4))

(qpoint? p3)  @result{} #t      ; @r{p3 is a qpoint}
(mpoint? p3)  @result{} #t      ; @r{... and also an mpoint}

(mpoint-x p3) @result{} 1       ; @r{accessing inherited field}
(mpoint-y p3) @result{} 2
(mpoint-z p3) @result{} 3
(qpoint-w p3) @result{} 4
@end example

@c EN
A small caveat: Accessors and modifiers for inherited fields
(e.g. @code{qpoint-x} etc.) are not created.
@c JP
ちょっとした注意：継承されたフィールドのアクセサとモディファイア
(例えば @code{qpoint-x} 等)は生成されません。
@c COMMON

@c EN
Gauche's convention is to enclose class name by @code{<>}.
You can follow the convention and still explicitly gives
simpler names (instead of @code{make-<point>} or @code{<point>-x}):
@c JP
Gaucheの慣例では、クラス名は@code{<>}で囲うようにしています。
この慣例にしたがい、さらに各手続きについては
(@code{make-<point>} や @code{<point>-x}) ではなく)
シンプルな名前を使うようにするには、次のようにします。
@c COMMON

@example
(define-record-type <point> make-point point?
  (x point-x)
  (y point-y)
  (z point-z))
@end example


@node Record types inspection layer, Record types procedural layer, Record types syntactic layer, Record types
@subsection Inspection layer
@c NODE レコード型のインスペクション層, インスペクション層

@c EN
This layer provides common procedures that operates on record type
descriptors and record instances.
@c JP
この層は、レコード型記述子、および、レコードのインスタンスを操作する
共通手続きを提供します。
@c COMMON

@c EN
Note that a record type descriptor is a class in Gauche, so
you can also use operators on classes (e.g. @code{class-name},
@code{class-slots} etc.) on record type descriptors as well.
However, these procedures are more portable.
@c JP
Gaucheでは、レコード型記述子はクラスであるため、クラスに対する操作
(例えば @code{class-name}や@code{class-slots} 等)を、
レコード型記述子に対して使用することもできます。
しかし、これらの手続きは、よりポータブルです。
@c COMMON

@defun record? obj
[SRFI-99][R6RS]
@c MOD gauche.record
@c EN
Returns @code{#t} iff @var{obj} is an instance of record type,
@code{#f} otherwise.
@c JP
@var{obj}がレコード型のインスタンスであれば@code{#t}を、
そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun record-rtd record
[SRFI-99][R6RS]
@c MOD gauche.record
@c EN
Returns the record type descriptor of the record instance.
@c JP
レコードインスタンスのレコード型記述子を返します。
@c COMMON
@end defun

@defun rtd-name rtd
[SRFI-99]
@c MOD gauche.record
@c EN
Returns the name of the record type descriptor @var{rtd}.
@c JP
レコード型記述子@var{rtd}の名前を返します。
@c COMMON
@end defun

@defun rtd-parent rtd
[SRFI-99]
@c MOD gauche.record
@c EN
Returns the parent type of the record type descriptor @var{rtd}.
If @var{rtd} doesn't have a parent, @code{#f} is returned.
@c JP
レコード型記述子@var{rtd}の親の型を返します。
@var{rtd}が親を持たなければ@code{#f}が返ります。
@c COMMON
@end defun

@defun rtd-field-names rtd
[SRFI-99]
@c MOD gauche.record
@c EN
Returns a vector of symbols, each of which is the names of the direct
fields of the record represented by @var{rtd}.   The result doesn't
include inherited fields.
@c JP
シンボルのベクタを返します。各シンボルは
@var{rtd}で示されるレコードの直属のフィールドの名前です。
この結果には、継承されたフィールドは含まれません。
@c COMMON
@end defun

@defun rtd-all-field-names rtd
[SRFI-99]
@c MOD gauche.record
@c EN
Returns a vector of symbols, each of which is the names of the
fields of the record represented by @var{rtd}.   The result includes
all inherited fields.
@c JP
シンボルのベクタを返します。各シンボルは
@var{rtd}で示されるレコードのフィールドの名前です。
この結果には、すべての継承されたフィールドが含まれます。
@c COMMON
@end defun

@defun rtd-field-mutable? rtd field-name
[SRFI-99]
@c MOD gauche.record
@c EN
Returns @code{#t} iff the field with the name @var{field-name}
of a record represented by @var{rtd} is mutable.
@c JP
@var{rtd}で示されるレコードの@var{field-name}という名前を持つフィールドが、
変更可能であれば@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun


@node Record types procedural layer, Pseudo record types, Record types inspection layer, Record types
@subsection Procedural layer
@c NODE レコード型の手続き層, 手続き層

@c EN
These procedures are low-level machinery on top of which
@code{define-record-type} is implemented.  They can be used
to create a new record type at runtime.
@c JP
これらの手続きは@code{define-record-type}を実装するための低レベルの機構です。
それらは実行時に新しいレコード型を作成するために使用できます。
@c COMMON

@defun make-rtd name field-specs :optional parent
[SRFI-99]
@c MOD gauche.record
@c EN
Creates and returns a new record type descriptor with name @var{name} and
having fields specified by @var{field-specs}.  If @var{parent}
is given, it must be a record type descriptor or @code{#f}.
If it is a record type descriptor, the created record type
inherits from it.
@c JP
@var{name}という名前を持ち@var{field-specs}で示されるフィールドを持つ
新しいレコード型記述子を作成して返します。
@var{parent}を指定した場合、それはレコード型記述子もしくは@code{#f}でなければなりません。
レコード型記述子であった場合、作成されるレコード型はそれを継承します。
@c COMMON

@c EN
The @var{field-specs} argument must be a vector, each
element of which is a @emph{field specifier}.  A field
specifier can be a symbol, a list @code{(mutable @var{symbol})},
or a list @code{(immutable @var{symbol})}.  The @var{symbol} names
the field.  A single symbol or @code{(mutable @var{symbol})} format
makes the field mutable, and @code{(immutable @var{symbol})} format
makes the field immutable.
@c JP
@var{field-specs}引数は、@emph{field specifier}を各要素に持つベクタ
でなければりません。@emph{field specifier}は、@var{symbol}、
@code{(mutable @var{symbol})}というリスト、もしくは、
@code{(immutable @var{symbol})}というリストのいずれかです。
@var{symbol}はフィールド名になります。@var{symbol}ひとつ、もしくは、
@code{(mutable @var{symbol})}形式の場合は、変更可能なフィールドを作ります。
そして、@code{(immutable @var{symbol})}形式の場合は、
変更不可のフィールドを作ります。
@c COMMON

@c EN
Note: Gauche does not implement the extension suggested in
SRFI-99 yet, which is @code{sealed}, @code{opaque} and @code{uid}
arguments.
@c JP
注意: Gaucheは、SRFI-99で提案されている拡張機能である
@code{sealed}、@code{opaque}、および、@code{uid}引数を、まだ実装していません。
@c COMMON
@end defun

@defun rtd? obj
[SRFI-99]
@c MOD gauche.record
@c EN
Returns @code{#t} if @var{obj} is a record type descriptor,
@code{#f} otherwise.
@c JP
@var{obj}がレコード型記述子であれば@code{#t}を、
そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun rtd-constructor rtd :optional field-specs
[SRFI-99]
@c MOD gauche.record
@c EN
Returns a procedure that creates an instance record of
the record type represented by @var{rtd}.
Without @var{field-specs}, it returns the default constructor,
which takes as many arguments as the number of fields of
the record to initialize them.
@c JP
@var{rtd}で示されるレコード型のインスタンスを作成する 手続きを返します。
@var{field-specs}がなければ、デフォルトコンストラクタを返します。
それは、初期化のためにレコードのフィールドの数と同じ数の引数を取ります。
@c COMMON

@c EN
You can give a vector of symbols as @var{field-specs}.  The @var{n}-th
symbol specifies which field of the instance should be initialized
by the @var{n}-th argument.   The @var{field-specs} vector cannot
contain duplicate names.  If the record type defines a field with
the same name as the one in the parent record type, the custom constructor
can only initialize the field of the derived type's instance.
@c JP
@var{field-specs}には、シンボルのベクタを指定できます。
@var{n}番目のシンボルは、そのインスタンスのフィールドが、
@var{n}番目の引数で初期化されることを示します。
@var{field-specs}ベクタは重複する名前を持つことはできません。
レコード型が親のレコード型と同じ名前のフィールドを定義した場合、
カスタムコンストラクタは継承先のフィールドのみを初期化します。
@c COMMON
@end defun

@defun rtd-predicate rtd
[SRFI-99]
@c MOD gauche.record
@c EN
Returns a predicate to test an object is an instance of @var{rtd}.
@c JP
オブジェクトが@var{rtd}のインスタンスであるかをテストする 述語を返します。
@c COMMON

@c EN
If @var{rtd} is a pseudo record type, the predicate merely tests
the given object is in an appropriate type and has enough size
to hold the contents.   See @ref{Pseudo record types} for the details.
@c JP
@var{rtd}が疑似レコード型であった場合、述語は、与えられたオブジェクトが、
内容を保持するのに十分なサイズを持つ適合した型かどうかをテストします。
詳しくは、@ref{Pseudo record types}を参照してください。
@c COMMON
@end defun

@defun rtd-accessor rtd field-name
[SRFI-99]
@c MOD gauche.record
@c EN
Returns a procedure that takes one argument, an instance of @var{rtd},
and returns the value of the @var{field-name} of the instance.
@c JP
1個の引数として@var{rtd}のインスタンスを取り、
そのインスタンスの@var{field-name}の値を返す 手続きを返します。
@c COMMON

@c EN
An error is signaled if the record type doesn't have the field
of name @var{field-name}.
@c JP
レコード型が@var{field-name}の名前のフィールドを持たない場合には、
エラーになります。
@c COMMON

@c EN
If @var{rtd} is inherits other record types, and it defines a field
of the same name as inherited ones, then the accessor returned by
this procedure retrieves the value of the field of the derived record.
@c JP
@var{rtd}が他のレコードを継承しており、
継承元と同名のフィールドを定義していた場合、この手続きが返すアクセサは、
継承先のレコードのフィールドの値を取得します。
@c COMMON
@end defun

@defun rtd-mutator rtd field-name
[SRFI-99]
@c MOD gauche.record
@c EN
Returns a procedure that takes two arguments, an instance of @var{rtd}
and a value, and sets the latter as the value of the @var{field-name}
of the instance.
@c JP
2個の引数として@var{rtd}のインスタンスと値を取り、
そのインスタンスの@var{field-name}に値をセットする 手続きを返します。
@c COMMON

@c EN
An error is signaled if the record type doesn't have the field
of name @var{field-name}, or the named field is immutable.
@c JP
レコード型が@var{field-name}の名前のフィールドを持たないか変更不可の場合には、
エラーになります。
@c COMMON

@c EN
Like @code{rtd-accessor}, if the record has a field with the same
name as inherited one, the modifier returned by this procedure
only modifies the field of the derived record.
@c JP
@code{rtd-accessor}と同様に、
レコードが継承元と同名のフィールドを定義していた場合、
この手続きが返すモディファイアは、
継承先のレコードのフィールドのみを変更します。
@c COMMON
@end defun


@node Pseudo record types,  , Record types procedural layer, Record types
@subsection Pseudo record types
@c NODE 疑似レコード型

@c EN
A pseudo record type is a record type that does not create
an instance of its own type.
Instead it treats an object of other collection
types, such as a vector, as if it had named fields.  It's easier
to understand by an example:
@c JP
疑似レコード型は、それ自身の型のインスタンスを作成しないレコード型です。
その代わり、ベクタのような他の集合型のオブジェクトを、
あたかもフィールド名を持っているかのように扱います。
例で理解するのが良いでしょう:
@c COMMON

@example
(define-record-type (vpoint (pseudo-rtd <vector>)) #t #t
  (x) (y) (z))

(make-vpoint 1 2 3)  @result{} #(1 2 3)
(vpoint-x '#(1 2 3)) @result{} 1

(rlet1 v (make-vpoint 1 2 3)
  (set! (vpoint-y v) -1))
 @result{} #(1 -1 3)
@end example

@c EN
To create a pseudo record type, specify another pseudo
record type as a parent.   The procedure @code{pseudo-rtd}
can be used to obtain a base pseudo record type of
the suitable instance class.
@c JP
疑似レコード型を作るには、他の疑似レコード型を親に指定します。
@code{pseudo-rtd}手続きは、適合するインスタンスクラスの
ベース疑似レコード型を取得するために使用できます。
@c COMMON

@defun pseudo-rtd instance-class
@c MOD gauche.record
@c EN
Returns a pseudo rtd suitable to use @var{instance-class} as
a pseudo record.
@c JP
@var{instance-class}を疑似レコードとして使うために
適合する疑似rtdを返します。
@c COMMON

@c EN
Currently, @code{<list>}, @code{<vector>}, and uniform vector
classes (@code{<u8vector>} etc.) are supported as @var{instance-class}.
@c JP
現在、@code{<list>}、@code{<vector>}、および、ユニフォームベクタ
(例えば @code{<u8vector>} 等)が、
@var{instance-class}としてサポートされています。
@c COMMON
@end defun

@c EN
The predicates of a pseudo record return @code{#t} if the given
object can be interpreted as the pseudo record.  In the above
example of @code{vpoint} record, the predicate @code{vpoint?}
returns @code{#t} iff the given object is a vector with 3 or more
elements:
@c JP
疑似レコード型の述語は、与えられたオブジェクトが
疑似レコード型として解釈できるときに@code{#t}を返します。
前述の@code{vpoint}レコードの例の場合、述語@code{vpoint?}は、
3かそれ以上の要素を持つベクタのオブジェクトが与えられた場合に
@code{#t}を返し、そうでなければ@code{#f}を返します。
@c COMMON

@example
(vpoint? '#(0 0 0))   @result{} #t
(vpoint? '#(0 0))     @result{} #f
(vpoint? '(0 0 0))    @result{} #f
(vpoint? '#(0 0 0 0)) @result{} #t
@end example

@c EN
We allow more elements so that the pseudo record can be used
to interpret the header part of the longer data.
@c JP
これは、より長いデータのヘッダ部分を解釈するために使えるように、
より多くの要素を許すようにしています。
@c COMMON

@c ----------------------------------------------------------------------
@node Reloading modules, Simple dispatcher, Record types, Library modules - Gauche extensions
@section @code{gauche.reload} - Reloading modules
@c NODE モジュールの再ロード, @code{gauche.reload} - モジュールの再ロード

@deftp {Module} gauche.reload
@mdindex gauche.reload
@c EN
In the development cycle, you often have to reload modules frequently.
This module supports it.

Note that some part of semantics of the program depends on
the order of loading modules, so reloading arbitrary modules
may change the program behavior unexpectedly.  This module
is for developers who knows what they are doing.
@c JP
開発のサイクルのなかで、モジュールを再ロードしなければならないことは
頻繁におこります。このモジュールはそれを支援するものです。

プログラムのいくつかの部分のセマンティクスはモジュールのロードの順に
依存します。それで、任意のモジュールを再ロードすることはプログラムの
ふるまいを予期せぬものに変えてしまう可能性があります。このモジュールは
自分がなにをしようとしているか判っている開発者向けのものです。
@c COMMON

@c EN
@strong{Redefinition rules}: Reloading a module resets all
the binding in the module by default.
Sometimes it is not desirable, however.  For example,
you might want to keep an intermediate results in some variable.
You can specify rules for the reloading procedure to determine
which binding to keep.

The rule is described in the following syntax.
@c JP
@strong{再定義ルール}: モジュールを再ロードすると、デフォルトでは、その
モジュール内のすべての束縛はリセットされます。
しかしながら、場合によってこれは望ましいことではありません。たとえば、
中間結果をある変数に残したままにしておきたい場合です。
再ロード手続きにどの束縛を保存するかを決めるためのルールを指定することが
できます。

このルールは以下の構文で記述します。
@c COMMON
@example
  <module-rules> : (<module-rule> @dots{})
  <module-rule>  : (<module-pattern> <rule> @dots{})
  <module-pattern> : @r{a symbol module name, or a symbol containing glob pattern}
  <rule>         : @r{procedure} | @r{symbol} | @r{regexp}
                 | (and <rule> @dots{})
                 | (or  <rule> @dots{})
                 | (not <rule>)
@end example

@c EN
@code{<module-rules>} is the global rule to determine per-module
rules.  @code{<module-pattern>} is either a symbol module name
or a symbol that contains glob pattern (e.g. @code{mylib.*}).
If @code{<rule>} is a procedure, it is used as a predicate
and the bindings whose value satisfies the predicate are kept from
redefinition.   If @code{<rule>} is a symbol, the binding of
the variable whose name is the symbol is kept.  If @code{<rule>}
is a regexp, the bindings of the variable whose name matches the
regexp are kept.

Note that the mechanism to prevent redefinition is kind of ad-hoc
hack and semantically unclean.  Especially, the right-hand expressions
of @code{define}s are still evaluated, so any side effects they have
will be in effect (e.g. @code{define-class} would still redefine a class).
It's just for your convenience.
Take a look at the code if you want to know the exact behavior.
@c JP
@code{<module-rules>} はモジュールごとのルールをきめるグローバルルール
です。@code{<module-pattern>} はモジュール名シンボルまたは(@code{mylib.*}
のような)グロブパターンを含むシンボルのどちらかです。@code{<rule>} が
手続きであれば、述語として使われ、この述語を満す値の束縛は再定義から
保護されます。@code{<rule>} がシンボルであれば、それと同じ名前の
変数の束縛は保護されます。@code{<rule>} が正規表現の場合、この正規表現に
マッチする名前の変数は保護されます。

再定義からの保護機構は、場当たり的なもので、セマンティクスとしても
不透明なものであることに注意してください。特に@code{define}の右辺式は
評価されてしまうので、そこで起きる副作用は効果を持ちます (例えば
@code{define-class}はクラスの再定義を行ってしまいます)。
これは利便のためだけのものだと考えて下さい。
正確な振舞いを知りたければ、コードを見てください。
@c COMMON
@end deftp

@defun reload module-name :optional rule @dots{}
@c MOD gauche.reload
@c EN
Reloads the specified module.   You can optionally specify
redefinition rules by @var{rule} @dots{},
where each @var{rule} is the term @code{<rule>} defined above.
@c JP
指定されたモジュールを再ロードします。オプションで
@var{rule} @dots{} をつかって再定義ルールを指定することができます。
ここで、それぞれの @var{rule} は上の @code{<rule>} で定義されたものです。
@c COMMON
@end defun

@defun reload-modified-modules :optional module-rules
@c MOD gauche.reload
@c EN
Reloads module(s) that have been modified since they are loaded
last time.  If optional @var{module-rules} is given, it is
used to determine the redefinition rules for reloaded modules.
If @var{module-rules} is omitted, the current rules are used.
The default of current rules is empty.   You can set the current
rules by @code{module-reload-rules}.
@c JP
前回ロードしたときより変更のあったモジュールを再ロードします。
オプション引数 @var{module-rules} が与えられていれば、再ロードした
モジュールに適用する再定義ルールを決定するために使います。
@var{module-rules}が省略された場合、現在のルールが適用されます。
デフォルトの現在のルールは空です。現在のルールは
@code{module-reload-rules}をつかって設定できます。

@c COMMON
@end defun

@defun module-reload-rules :optional module-rules
@c MOD gauche.reload
@c EN
This is a parameter (@pxref{Parameters}) that keeps
the default module rules for @code{reload-modified-modules}.
If called without arguments, returns the current module rules.
If called with @var{module-rules}, sets the argument to the
current module rules.
@c JP
これは一種の「パラメータ」(@ref{Parameters}参照)で、
@code{reload-modified-modules}に対応するデフォルトのモジュールルールを
保持しています。引数なしで呼ばれたときには、現在のモジュールルールを
返します。@var{module-rules}とともに呼ばれたきにはその引数を
現在のモジュールルールにします。
@c COMMON
@end defun

@defun reload-verbose :optional flag
@c MOD gauche.reload
@c EN
This is a parameter to control verbosity of the reloading procedures.
If called without arguments, returns the current verbosity flag.
If called with @var{flag}, it is set to the current verbosity flag.
@c JP
これは再ロード手続きのメッセージ出力レベルを制御するパラメータです。
引数なしで呼ばれると現在の出力レベルフラグを返します。@var{flag}と
ともに呼ばれると現在の出力レベルをこれに設定します。
@c COMMON
@end defun

@c ----------------------------------------------------------------------
@node Simple dispatcher, Sequence framework, Reloading modules, Library modules - Gauche extensions
@section @code{gauche.selector} - Simple dispatcher
@c NODE 簡単なディスパッチャ, @code{gauche.selector} - 簡単なディスパッチャ

@deftp {Module} gauche.selector
@mdindex gauche.selector
@c EN
This module provides a simple interface to dispatch I/O events to
registered handlers, based on @code{sys-select} (@pxref{I/O multiplexing}).
@c JP
このモジュールは、@code{sys-select} (@ref{I/Oの多重化}参照)に基づき、
登録されたハンドラにI/Oイベントをディスパッチするためのシンプルな
インタフェースを提供します。
@c COMMON
@end deftp

@deftp {Class} <selector>
@clindex selector
@c MOD gauche.selector
@c EN
A dispatcher instance that keeps watching I/O ports with associated
handlers.  A new instance can be created by @code{make} method.
@c JP
ディスパッチャのインスタンスで、ハンドラを携えてI/Oポートを監視します。
@code{make}メソッドで新しいインスタンスを作れます。
@c COMMON
@end deftp


@deffn {Method} selector-add! (self <selector>) port-or-fd proc flags
@c MOD gauche.selector
@c EN
Add a handler @var{proc} to the selector.  @var{proc} is called
when @var{port-or-fd}, which should be a port object or an integer
that specifies a system file descriptor,  meets a certain condition
specified by @var{flags}.
@var{flags} must be a list of one or more of the following symbols.
@c JP
セレクタにハンドラ@var{proc}を追加します。@var{proc}は、@var{port-or-fd}
(ポートオブジェクトかシステムのファイルディスクリプタを表す整数)が
@var{flags}で指定された条件に合致した場合に呼ばれます。
@var{flags}は、以下のシンボルの1つ以上のリストでなければなりません。
@c COMMON
@c EN
@table @code
@item r
Calls @var{proc} when data is available at @var{port-or-fd} to read.
@item w
Calls @var{proc} when @var{port-or-fd} is ready to be written.
@item x
Calls @var{proc} when an exceptional condition occurs on @var{port-or-fd}.
@end table
@c JP
@table @code
@item r
@var{port-or-fd}が読み取り可能になった時点で@var{proc}が呼ばれます。
@item w
@var{port-or-fd}が書き込み可能になった時点で@var{proc}が呼ばれます。
@item x
@var{port-or-fd}で例外的な状況が発生した場合に@var{proc}が呼ばれます。
@end table
@c COMMON

@c EN
@var{proc} is called with two arguments.  The first one is @var{port-or-fd}
itself, and the second one is a symbol @code{r}, @code{w} or @code{x},
indicating the condition.
@c JP
@var{proc}は、2引数で呼ばれます。1つ目は@var{port-or-fd}そのもので、
2つ目は条件を表すシンボル、@code{r}、@code{w}あるいは@code{x}です。
@c COMMON

@c EN
If a handler is already associated with @var{port-or-fd} under the
same condition, the previous handler is replaced by @var{proc}.
@c JP
同じ条件の下ですでに@var{port-or-fd}にハンドラが関連付けられていた場合は、
以前のハンドラが@var{proc}で置き換えられます。
@c COMMON
@end deffn

@deffn {Method} selector-delete! (self <selector>) port-or-fd proc flags
@c MOD gauche.selector
@c EN
Deletes the handler entries that matches @var{port-or-fd}, @var{proc}
and @var{flags}.   One or more of the arguments may be @code{#f},
meaning ``don't care''.  For example,
@c JP
@var{port-or-fd}、@var{proc}、@var{flags}にマッチするハンドラエントリを
削除します。引数のいずれかが@code{#f}である場合は、それが何でも良いことを
意味します。例えば、
@c COMMON
@example
(selector-delete! selector the-port #f #f)
@end example
@c EN
deletes all the handlers associated to @var{the-port}, and
@c JP
@var{the-port}に関連付けられた全てのハンドラを削除します。
@c COMMON
@example
(selector-delete! selector #f #f '(w))
@end example
@c EN
deletes all the handlers waiting for writable condition.
@c JP
書き込み可能になるのを待っている全てのハンドラを削除します。
@c COMMON
@end deffn


@deffn {Method} selector-select (self <selector>) :optional (timeout #f)
@c MOD gauche.selector
@c EN
Dispatcher body.  Waits for the conditions registered in @var{self},
and when it occurs, calls the associated handler.
@c JP
ディスパッチャのボディです。@var{self}に登録された条件を待ち、条件が合致すると
それに関連付けられたハンドラを呼びます。
@c COMMON
@c EN
If the @var{timeout} argument is omitted or false, this method waits
indefinitely.  Alternatively you can give a timeout value, that can
be a real number in microseconds, or a list of two integers that
represents seconds and microseconds.
@c JP
@var{timeout}引数が省略されるか偽の場合、このメソッドは永久に待ちます。
タイムアウトの値を与える場合は、マイクロ秒を表す実数か、秒とマイクロ秒を
表す2つの整数のリストを与えます。
@c COMMON

@c EN
Returns the number of handlers called.  Zero means the selector has been
timed out.
@c JP
戻り値は、ハンドラが呼ばれた回数です。0(ゼロ)は、セレクタがタイムアウト
したことを意味します。
@c COMMON

@c EN
It is safe to modify @var{self} inside handler.  The change will be
effective from the next call of @code{selector-select}
@c JP
ハンドラの中で@var{self}を変更することは安全です。その変更は、次回の
@code{selector-select}の呼び出し以降に反映されます。
@c COMMON
@end deffn

@c EN
This is a simple example of "echo" server:
@c JP
echoサーバのシンプルな例を示します。
@c COMMON

@example
(use gauche.net)
(use gauche.selector)
(use gauche.uvector)

(define (echo-server port)
  (let ((selector (make <selector>))
        (server   (make-server-socket 'inet port :reuse-addr? #t)))

    (define (accept-handler sock flag)
      (let* ((client (socket-accept server))
             (output (socket-output-port client)))
        (selector-add! selector
                       (socket-input-port client :buffering #f)
                       (lambda (input flag)
                         (echo client input output))
                       '(r))))

    (define (echo client input output)
      (let ((str (read-uvector <u8vector> 4096 input)))
        (if (eof-object? str)
            (begin (selector-delete! selector input #f #f)
                   (socket-close client))
            (begin (write-uvector str output)
                   (flush output)))))

    (selector-add! selector
                   (socket-fd server)
                   accept-handler
                   '(r))
    (do () (#f) (selector-select selector))))
@end example

@c ----------------------------------------------------------------------
@node Sequence framework, Syslog, Simple dispatcher, Library modules - Gauche extensions
@section @code{gauche.sequence} - Sequence framework
@c NODE シーケンスフレームワーク, @code{gauche.sequence} - シーケンスフレームワーク

@deftp {Module} gauche.sequence
@mdindex gauche.sequence
@c EN
Provides a generic operations on @emph{sequences}.
A sequence is a collection with ordered elements.
Besides all the operations applicable on collections,
you can associate integer index to each element,
and apply order-aware operations on the elements.
@c JP
@emph{シーケンス}に関するジェネリックな操作を提供するモジュールです。
シーケンスとは、コレクションのうち要素の順序が規定されているものです。
コレクションの操作全てに加え、シーケンスに対しては、
各要素に整数のインデックスを関連づけること、
それから要素の順序が影響する操作を適用することができます。
@c COMMON

@c EN
This module inherits @code{gauche.collection} (@pxref{Collection framework}).
All the collection generic operations can be applied to a sequence as well.
@c JP
このモジュールは@code{gauche.collection}を継承しています
(@ref{Collection framework}参照)。
コレクションに使えるジェネリックな操作は全てシーケンスに対しても適用可能です。
@c COMMON

@c EN
Among Gauche builtin class, lists, vectors and strings are sequences
and the specialized methods are defined for them.   Other extension
types, such as uniform vectors, have the methods as well.
@c JP
Gauche組み込みクラスのうち、リスト、ベクター、そして文字列は
シーケンスであり、このモジュールでメソッドが定義されます。
また@code{gauche.uvector}のユニフォームベクタ等、
いくつかの拡張データタイプはシーケンスとなっています。
@c COMMON
@end deftp

@menu
* Fundamental sequence accessors::
* Slicing and filling sequences::
* Mapping over sequences::
* Other operations over sequences::
* Implementing sequences::
@end menu

@node Fundamental sequence accessors, Slicing and filling sequences, Sequence framework, Sequence framework
@subsection Fundamental sequence accessors
@c NODE 基本的なシーケンスのアクセサ

@deffn {Method} ref (seq <sequence>) index :optional fallback
@c MOD gauche.sequence
@c EN
Returns @var{index}-th element of the sequence @var{seq}.
This method enables uniform access for any sequence types.

When @var{index} is less than zero, or greater than or equal to the
size of the sequence, @var{fallback} is returned if provided, or
an error is signaled if not.
@c JP
シーケンス@var{seq}の@var{index}番目の要素を返します。
このメソッドによって、全てのシーケンスが統一的にアクセスできます。

@var{index}が負値だったりシーケンスのサイズ以上だった場合は、
@var{fallback}が与えられていればそれが返され、
そうでなければエラーとなります。
@c COMMON

@example
(ref '(a b c) 1)  @result{} b
(ref '#(a b c) 1) @result{} b
(ref "abc" 1)     @result{} #\b
@end example
@end deffn

@deffn {Method} {(setter ref)} (seq <sequence>) index value
@c MOD gauche.sequence
@c EN
Sets @var{value} to the @var{index}-th element of the sequence @var{seq}.
This is the uniform sequence modifier.

Note: Some sequences may not support arbitrary modification by index.
For example, if you have a sequence representing a set of sorted integers,
you cannot modify @var{i}-th element with arbitrary value.  Yet such
sequence may provide other means of modification, such as inserting
or deleting elements.
@c JP
統一的なシーケンスの変更メソッドです。
シーケンス@var{seq}の@var{index}番目の要素に@var{value}をセットします。

註: シーケンスによってはインデックスによる変更をサポートしていない
場合があります。例えば「ソートされた整数」を表すシーケンスがあった場合、
@code{i}番目の要素を適当な整数で置き換えることはできないでしょう。
そのようなシーケンスでも、要素の挿入や削除など、別の方法でシーケンスを
変更する手段が与えられるかもしれません。
@c COMMON

@example
(let ((x (list 'a 'b 'c)))
  (set! (ref x 1) 'z)
  x) @result{} (a z c)

(let ((x (vector 'a 'b 'c)))
  (set! (ref x 1) 'z)
  x) @result{} #(a z c)

(let ((x (string #\a #\b #\c)))
  (set! (ref x 1) #\z)
  x) @result{} "azc"
@end example
@end deffn

@deffn {Method} referencer (seq <sequence>)
@c MOD gauche.sequence
@c EN
Returns a procedure @var{p} that can be invoked
as @code{(@var{p} @var{s} @var{i})} or
@code{(@var{p} @var{s} @var{i} @var{fallback})}.
@var{s} is a sequence of the same class as @var{seq}, and
@var{i} is an exact integer.  @var{p} must return the @var{i}-th
element of @var{s}.  If @var{i} is out of bounds,
it should return @var{fallback} if provided, or signals an error.

For example, applying @code{referencer} to any list returns
a procedure equivalent to @code{list-ref}.

This is useful when you need to invoke a lot of @code{ref} method or
@code{~} procedure on sequence objects;
@code{ref} method needs runtime dispatch for every
invocation, but if you take @code{referencer} once and use the
returned procedure, you can avoid runtime dispatch.
@c JP
@code{(@var{p} @var{s} @var{i})}もしくは
@code{(@var{p} @var{s} @var{i} @var{fallback})}と呼び出せる手続き@var{p}を
返します。ここで、@var{s}は@var{seq}と同じクラスのシーケンス、
@var{i}は正確な整数です。@var{p}は@var{s}の@var{i}番目の要素を返します。
@var{i}が範囲外の場合、@var{fallback}が与えられればそれを返し、
そうでなければエラーを投げます。

例えば、リストに@code{referencer}を適用すると、
@code{list-ref}相当の手続きが返されます。

これは、シーケンスオブジェクトに@code{ref}メソッドや@code{~}手続きを
頻繁に適用する場合に便利です。@code{ref}は一回の呼び出し毎に
実行時ディスパッチのコストがかかります。一度@code{referencer}を取れば、
返された手続きは実行時ディスパッチを行いません。
@c COMMON
@end deffn

@deffn {Method} modifier (seq <sequence>)
@c MOD gauche.sequence
@c EN
Returns a procedure @var{p} that can be invoked
as @code{(@var{p} @var{s} @var{i} @var{obj})}, which sets @var{obj} to the
@var{i}-th element of a sequence @var{s} of the same class of @var{seq}.
If @var{i} is out of bounds, or @var{obj} is not suitable as an element
of @var{s}, or @var{s} is immutable, an error is thrown.

For example, applying @code{modifier} to any list returns
a procedure equivalent to @code{list-set!}.

This is useful when you need to set lots of places of sequence
objects.  @code{(set! (ref s i) obj)} needs runtime dispatch,
and calling a procedure returned by @code{modifier} avoid it.
@c JP
@code{(@var{p} @var{s} @var{i} @var{obj})}と呼び出せる手続き@var{p}を
返します。ここで、@var{s}は@var{seq}と同じクラスのシーケンス、
@var{i}は正確な整数で、@var{p}は@var{obj}を@var{s}の@var{i}番目の要素にセットします。
@var{i}が範囲外の場合、@var{s}が変更不可の場合、
あるいは@var{obj}が@var{s}の要素としてふさわしくない場合はエラーが投げられます。

例えば、リストに@code{modifier}を適用すると、
@code{list-set!}相当の手続きが返されます。

シーケンスオブジェクトの多くの箇所を変更したい場合、
@code{(set! (ref s i) obj)} で行うと呼び出しの度に実行時ディスパッチの
オーバヘッドがありますが、@code{modifier}を呼んで返された手続きを使うと
それを避けられます。
@c COMMON
@end deffn

@node Slicing and filling sequences, Mapping over sequences, Fundamental sequence accessors, Sequence framework
@subsection Slicing and filling sequences
@c NODE シーケンスのスライス、フィル

@deffn {Method} subseq (seq <sequence>) :optional start end
@c MOD gauche.sequence
@c EN
Retrieve a subsequence of the sequence @var{seq}, from
@var{start}-th element (inclusive) to @var{end}-th element (exclusive).
If @var{end} is omitted, up to the end of sequence is taken.
The type of the returned sequence is the same as @var{seq}.
@c JP
シーケンス@var{seq}の、@var{start}番目の要素から@var{end}番目の要素の直前
までの部分シーケンスを返します。@var{end}が省略された場合はシーケンスの
最後までが取られます。返されるシーケンスの型は@var{seq}と同じになります。
@c COMMON

@example
(subseq '(a b c d e) 1 4)   @result{} (b c d)
(subseq '#(a b c d e) 1 4)  @result{} #(b c d)
(subseq "abcde" 1 4)        @result{} "bcd"

(subseq '(a b c d e) 3)     @result{} (d e)
@end example
@end deffn

@deffn {Method} {(setter subseq)} (seq <sequence>) start end value-seq
@deffnx {Method} {(setter subseq)} (seq <sequence>) start value-seq
@c MOD gauche.sequence
@c EN
Sets the elements of @var{value-seq} from the @var{start}-th element
(inclusive) to the @var{end}-th element (exclusive) of the sequence @var{seq}.
@var{Value-seq} can be any sequence, but its size
must be larger than (@var{end} - @var{start}).

In the second form, @var{end} is figured out by the length of @var{value-seq}.
@c JP
@var{value-seq}の各要素を、シーケンス@var{seq}の@var{start}番目から
@var{end}番目の直前まで順にセットします。
@var{value-seq}はどんなシーケンスでも構いませんが、
(@var{end} - @var{start}) よりは長くなくてはなりません。

2番目の形式では、@var{end}が@var{value-seq}の長さから算出されます。
@c COMMON

@example
(define s (vector 'a 'b 'c 'd 'e))
(set! (subseq s 1 4) '(4 5 6))
s @result{} #(a 4 5 6 e)
(set! (subseq s 0)   "ab")
s @result{} #(#\a #\b 5 6 e)
@end example
@end deffn

@deffn {Method} sequence-copy! (dst <sequence>) dstart (src <sequence>) :optional sstart send
@c MOD gauche.sequence
@c EN
A generic version of @code{vector-copy!}, @code{string-copy!} etc.
Copy the contents of @var{src} between @var{sstart} and @var{send}
into a mutable sequence @var{dst} starting from @var{dstart}.
The classes of @var{src} and @var{dst} can differ.
The return value is undefined.

If @var{sstart} and/or @var{send} are omitted, 0 and the length of @var{src}
are assumed, respectively.

If @var{dst} isn't large enough to hold the copied portion, or
@var{dst} is immutable, an error is signaled.
@c JP
@code{vector-copy!}や@code{string-copy!}のジェネリック版です。
@var{src}の@var{sstart}から@var{send}までを、@var{dst}の@var{dstart}位置へと
コピーします。@var{src}と@var{dst}のクラスは異なっていても構いません。
戻り値は未定義です。

@var{ssart}、@var{send}が省略された場合はそれぞれ0と@var{src}の長さが使われます。

@var{dst}の長さが必要な要素を書き込むのに足りなかったり、
@var{dst}が変更不可の場合はエラーが投げられます。
@c COMMON

@example
(rlet1 v (list 'a 'b 'c 'd 'e)
  (sequence-copy! v 1 "pqr")) @result{} (a #\p #\q #\r e)
@end example
@end deffn

@deffn {Method} sequence-fill! (dst <sequence>) elt :optional start end
@c MOD gauche.sequence
@c EN
A generic version of @code{vector-fill!} etc.
Fill @var{dst} with @var{elt}.  If the optional @var{start} and/or @var{end}
indexes are given, they limit the portion of @var{dst} to be filled.
@var{dst} must be a mutable sequence.
@c JP
@code{vector-fill!}等のジェネリック版です。
@var{dst}を要素@var{elt}で埋めます。省略可能な@var{start}や@var{end}は
変更対象となる@var{dst}の範囲を制限します。
@var{dst}は変更可能でなければなりません。
@c COMMON

@example
(rlet1 v (list 'a 'b 'c 'd 'e)
  (sequence-fill! v 'Z 2)) @result{} (a b Z Z Z)
@end example
@end deffn


@node Mapping over sequences, Other operations over sequences, Slicing and filling sequences, Sequence framework
@subsection Mapping over sequences
@c NODE シーケンス上のマップ

@c EN
You can use extended @code{fold}, @code{map}, @code{for-each} and other
generic functions on sequences, since a sequence is also a collection.
However, sometimes you want to have index as well as the element itself
during iteration.   There are several generic functions for it.
@c JP
シーケンスはまたコレクションでもあるので、シーケンスについて
@code{fold}、@code{map}、@code{for-each}や他のジェネリック関数を
拡張することができます。しかし、時にはイテレーション中に要素そのものと
そのインデックスを知りたいことでしょう。そのためのジェネリック関数が
いくつかあります。
@c COMMON

@deffn {Method} fold-with-index kons knil (seq <sequence>) @dots{}
@c MOD gauche.sequence
@c EN
Like generic @code{fold}, except @var{kons} is given
the index within @var{seq}, as the first argument,
as well as each element from @var{seq}s and the accrued value.
@c JP
ジェネリックな@code{fold}と似ていますが、@var{kons}には@var{seq}の
インデックス内から、第1引数として@var{seq}の要素と増加する値が渡る
点が異なります。
@c COMMON

@example
(fold-with-index acons '() '(a b c))
  @result{} ((2 . c) (1 . b) (0 . a))
@end example
@end deffn

@deffn {Method} map-with-index proc (seq <sequence>) @dots{}
@deffnx {Method} map-to-with-index class proc (seq <sequence>) @dots{}
@deffnx {Method} for-each-with-index proc (seq <sequence>) @dots{}
@c MOD gauche.sequence
@c EN
Like @code{map}, @code{map-to} and @code{for-each}, except @var{proc}
receives the index as the first argument.
@c JP
@code{map}、@code{map-to}、@code{for-each}と似ていますが、@var{proc}が
第1引数としてインデックスを受け取る点が違います。
@c COMMON

@example
(map-with-index list '(a b c d) '(e f g h))
  @result{} ((0 a e) (1 b f) (2 c g) (3 d h))

(map-to-with-index <vector> cons '(a b c d))
  @result{} #((0 . a) (1 . b) (2 . c) (3 . d))
@end example
@end deffn

@deffn {Method} find-with-index pred (seq <sequence>)
@c MOD gauche.sequence
@c EN
Finds the first element in @var{seq} that satisfies @var{pred}
like @code{find}, but returns two values, the index of the element
and the element itself.   If no element satisfies @var{pred},
two @code{#f}'s are returned.
@c JP
@code{find}のように、@var{seq}の中で@var{pred}を満足する最初の要素を
探しますが、2つの値、要素のインデックスと要素自身を返します。
@var{pred}を満足する要素がなかったら、2つの@code{#f}が返ります。
@c COMMON

@example
(find-with-index char-upper-case? "abraCadabra")
  @result{} 4 and #\C

(find-with-index char-numeric? "abraCadabra")
  @result{} #f and #f
@end example
@end deffn

@deffn {Method} find-index pred (seq <sequence>)
@c MOD gauche.sequence
@c EN
Like @code{find}, but returns the index of the first element
that satisfies @var{pred} in @var{seq}, instead of the element itself.
If no element in @var{seq} satisfies @var{pred}, @code{#f} is returned.
@c JP
@code{find}に似ていますが、@var{seq}の中で@var{pred}を満足する最初の、
要素自身ではなくインデックスを返す点が異なります。
@var{seq}の中に@var{pred}を満足する要素がなかったら、@code{#f}が返ります。
@c COMMON

@example
(find-index char-upper-case? "abraCadabra")
  @result{} 4

(find-index char-numeric? "abraCadabra")
  @result{} #f
@end example

@c EN
See also @code{list-index} in @code{scheme.list}
(@pxref{R7RS lists}).
@c JP
@code{scheme.list} (@ref{R7RS lists}参照)の@code{list-index}も見て下さい。
@c COMMON
@end deffn

@deffn {Method} fold-right kons knil (seq <sequence>) @dots{}
@deffnx {Method} fold-left kons knil (seq <sequence>) @dots{}
@c MOD gauche.sequence
@c EN
Generalization of @code{fold-right}/@code{fold-left} on lists.
Like @code{fold}, this method applies a higher-order function
@var{kons} over given sequence(s), passing the "seed" value
whose default is @var{knil}.  The difference between @code{fold}
and @code{fold-right} is the associative order of elements on
which @var{kons} is applied.

When we have one sequence, @code{[E0, E1, ..., En]},
@code{fold-right} and @code{fold-left} work compared to @code{fold}
as follows, respectively.
@c JP
リストに対する@code{fold-right}の総称関数版です。
@code{fold}と同じように、このメソッドは種となる値 (初期値は@var{knil})
を受渡しながら、高階関数@var{kons}を与えられたシーケンスの各要素に
適用してゆきます。@code{fold}と@code{fold-right}の違いは
要素間の結合の順序にあります。

ひとつだけのシーケンス@code{[E0, E1, ..., En]}に適用する場合、
@code{fold}に対して@code{fold-right}と@code{fold-left}はそれぞれ以下のように動作します。
@c COMMON

@example
fold:
  (kons En (kons En-1 (kons ... (kons E1 (kons E1 knil)) ...)))

fold-right
  (kons E0 (kons E1 (kons ... (kons En-1 (kons En knil)) ...)))

fold-left:
  (kons (kons ... (kons (kons knil E1)  E2) ... En-2) En-1)
@end example

@c EN
This method isn't defined on @code{<collection>}, since
collections don't care the order of elements.
@c JP
このメソッドは@code{<collection>}に対しては提供されていません。
コレクションは要素の順序を規定しないからです。
@c COMMON
@end deffn


@node Other operations over sequences, Implementing sequences, Mapping over sequences, Sequence framework
@subsection Other operations over sequences
@c NODE その他のシーケンス上の操作

@c EN
@subsubheading Selection and searching
@c JP
@subsubheading 選択と検索
@c COMMON

@deffn {Generic function} sequence-contains haystack needle :key test
@c MOD gauche.sequence
@c EN
Both @var{needle} and @var{haystack} must be sequences.
Searches @var{needle} from @var{haystack} from the beginning of @var{haystack}.
If @var{needle} is found, the index in @var{haystack} where it begins is
returned.  Otherwise @code{#f} is returned.  The keyword argument
@var{test} is used to compare elements; its default is @code{eqv?}.
@c JP
@var{needle}と@var{haystack}はシーケンスです。
@var{haystack}の中で、@var{needle}に一致するシーケンスを左から探します。
もし見つかれば、@var{haystack}中の@var{needle}が始まる場所のインデックスを、
見つからなければ@code{#f}を返します。キーワード引数@var{test}は
要素を比較するのに使われます。デフォルトは@code{eqv?}です。
@c COMMON

@example
(sequence-contains '#(a b r a c a d a b r a) '#(b r a))
  @result{} 1

(sequence-contains '#(a b r a c a d a b r a) '#(c r a))
  @result{} #f
@end example

@c EN
This can be regarded as generalization of @code{string-contains} in SRFI-13
(@pxref{SRFI-13 String searching}).
@c JP
これは、SRFI-13の@code{string-contains}を一般化したものとみることもできます
(@ref{SRFI-13 String searching}参照)。
@c COMMON
@end deffn

@defun break-list-by-sequence list needle :key test
@defunx break-list-by-sequence! list needle :key test
@c MOD gauche.sequence
@c EN
Searches a sequence @var{needle} from @var{list},
and if found, breaks @var{list}
to two parts---the prefix of @var{list} up to right before @var{needle}
begins, and the rest---and returns them.
@var{List} must be a list, but @var{needle} can be any sequence.
Elements are compared by @var{test}, defaulted to @code{eqv?}.
@c JP
シーケンス@var{needle}を@var{list}から探し、見つかれば@var{list}を
@var{needle}の直前までとそれ以降に分割して二つの値として返します。
@var{list}はリストでなければなりませんが、
@var{needle}には任意のシーケンスを渡せます。
各要素は@var{test}手続きで比較されます。デフォルトは@code{eqv?}です。
@c COMMON

@example
(break-list-by-sequence '(a b r a c a d a b r a) '(c a d))
  @result{} (a b r a) @r{and} (c a d a b r a)
@end example

@c EN
If @var{needle} isn't found in @var{list}, it returns @var{list} itself
and @code{()}.  This behavior is aligned to @code{span} and @code{break}
(@pxref{R7RS lists}), which split a list by predicate but
returns the whole list if split condition isn't met.
@c JP
@var{needle}が@var{list}中に見つからなかった場合は、
@var{list}そのものと@code{()}が返されます。
これは@code{span}や@code{break}の動作に合わせてあります
(@ref{R7RS lists}参照)。
これらの手続きは要素に対する述語でもってリストを分割しますが、
分割条件が満たされなかった場合はリスト全体を返します。
@c COMMON

@example
(break-list-by-sequence '(a b r a c a d a b r c a) '(c a z))
  @result{} (a b r a c a d a b r c a) @r{and} ()
@end example

@c EN
The linear update version @code{break-list-by-sequence!}
modifies @var{list} to create the return value if necessary,
so @var{list} must be mutable.  The caller must use the return
value instead of relying on side-effects, though,
for @var{list} may not be modified.
@c JP
@code{break-list-by-sequence!}はその場で更新するバージョンで、
必要なら@var{list}を破壊的に変更して返り値を生成します。渡すリストは変更可能で
なければなりません。@var{list}が変更されない場合もあるので、
呼出側は副作用に頼らず常に返り値を利用する必要があります。
@c COMMON
@end defun

@defun sequence->kmp-stepper needle :key test
@c MOD gauche.sequence
@c EN
This is an internal routine to search subsequence (@var{needle}) inside
larger sequence, using Knuth-Morris-Pratt (KMP) algorithm.
It is used in @code{sequence-contains},
@code{break-list-by-sequence} and @code{break-list-by-sequence!}.
@c JP
これは、KMPアルゴリズムを使って大きなシーケンス中から
部分シーケンス@var{needle}を探すための内部ルーチンです。
@code{sequence-contains}、
@code{break-list-by-sequence}、
@code{break-list-by-sequence!}の中で使われています。
@c COMMON

@c EN
Returns a procedure that performs one step of KMP search.
The procedure takes two arguments, an element @var{elt}
and an index @var{k}.  It compares @var{elt} with
@code{(~ needle k)}, and returns two values---the next index and
a flag indicating the match is completed.  When the match is
completed, the next index is equal to the length of @var{needle}.
@c JP
KMPアルゴリズムの1ステップを行う手続きを返します。
返される手続きは二つの引数、要素@var{elt}とインデックス@var{k}を取り、
@var{elt}と@code{(~ needle k)}を比較します。二つの値を返します：
次に比較すべきインデックスと、マッチが終了したかどうかのフラグです。
マッチが終了した場合、次のインデックスとして返される値は@var{needle}の
長さと等しいです。
@c COMMON

@c EN
As an edge case, if @var{needle} is an empty sequence,
@code{sequence->kmp-stepper} returns @code{#f}.
@c JP
エッジケースとして、@var{needle}が空のシーケンスの場合、
@code{sequence->kmp-stepper}は@code{#f}を返します。
@c COMMON

@c EN
Elements are compared using @var{test}, which is defaulted to @code{eqv?}.
@c JP
要素は@var{test}で比較されます。デフォルトは@code{eqv?}です。
@c COMMON

@c EN
The following is a skeleton of searcher using
@code{sequence->kmp-stepper}.  Here we assume @var{haystack}
is a list, and we just return whether the needle is
found or not, or needle is empty; you might want to carry
around other info in the loop (e.g. @code{sequence-contains}
tracks the current index of @var{haystack} in order to
return the found index.)
@c JP
以下に、@code{sequence->kmp-stepper}を使った探索コードの骨格を示します。
この例では@var{haystack}はリストで、単に@var{needle}が見つかったかどうか
(あるいは@var{needle}が空か)だけを返しています。
実際の応用では、他の情報をループで持ち回ることになるでしょう
(例えば@code{sequence-contains}では@var{haystack}中の
インデックスをトラックして、見つかった場所を返しています。)
@c COMMON

@example
(if-let1 stepper (sequence->kmp-stepper needle)
  (let loop ([haystack haystack]
             [k 0])
    (if (null? haystack)
      'not-found
      (receive (k found) (stepper (car haystack) k) ; KMP step
        (if found
          'found
          (loop (cdr haystack) k)))))
  'needle-is-empty)
@end example
@end defun

@c EN
Note that selection and searching methods for collections
can also be applied to sequences.
See @ref{Selection and searching in collection}.
@c JP
コレクションに対する選択と探索はシーケンスにも使えます。
@ref{Selection and searching in collection}を参照して下さい。
@c COMMON

@c EN
@subsubheading Grouping
@c JP
@subsubheading グループ化
@c COMMON

@deffn {Generic function} group-sequence seq :key key test
@c MOD gauche.sequence
@c EN
Groups consecutive elements in a sequence @var{seq} which
have the common key value.  A key value of an element is
obtained by applying the procedure @var{key} to the element;
the default procedure is @code{identity}.
For each element in @var{seq}, @var{key} is applied exactly once.
The equal-ness of keys are compared by @var{test} procedure,
whose default is @code{eqv?}.
@c JP
シーケンス@var{seq}の連続する要素で、同じキー値を持つもの同士を
グループ化します。
キーの値は要素に手続き@var{key}を適用することで得られます。@var{key}の
デフォルト値は@code{identity}です。@var{sedq}の各要素に対して、
@var{key}は正確に一回だけ呼ばれます。
キーの等価性判定には手続き@var{test}が使われます。デフォルト値は@code{eqv?}です。
@c COMMON

@example
(group-sequence '(1 1 1 2 3 4 4 2 2 3 1 1 3))
  @result{} ((1 1 1) (2) (3) (4 4) (2 2) (3) (1 1) (3))

(group-sequence '(1 1 1 2 3 4 4 2 2 3 1 1 3)
                :key (cut modulo <> 2)))
  @result{} ((1 1 1) (2) (3) (4 4 2 2) (3 1 1 3))

(group-sequence '#("a" "a" "b" "b" "c" "d" "d")
                :test string=?)
  @result{} (("a" "a") ("b" "b") ("c") ("d" "d"))

(group-sequence "aabbcdd"
                :test char=?)
  @result{} ((#\a #\a) (#\b #\b) (#\c) (#\d #\d))
@end example

@c EN
This method is similar to Haskell's @code{group}.
If you want to group elements that are not adjacent,
use @code{group-collection}
(@pxref{Selection and searching in collection}).
@c JP
このメソッドはHaskellの@code{group}と似ています。
隣り合っていない要素もグループ化したい場合は、
@code{group-collection}
(@ref{Selection and searching in collection}参照)を使って下さい。
@c COMMON

@c EN
If you simply need to reduce each group for one instance,
that is, removing adjacent duplicated elements,
you can use @code{delete-neighbor-dups} below.
@c JP
もし、単にそれぞれのグループあたり一つづとつの要素だけを残したい、
つまり、隣り合う重複する要素を除きたい場合は、
下の@code{delete-neighbor-dups}が使えます。
@c COMMON
@end deffn

@deffn {Generic function} group-contiguous-sequence seq :key key next test squeeze
@c MOD gauche.sequence
@c EN
Group contiguous elements in @var{seq}.
@c JP
@var{seq}中の連続する要素をまとめます。
@c COMMON

@example
(group-contiguous-sequence '(1 2 3 4 7 8 9 11 13 14 16))
  @result{} ((1 2 3 4) (7 8 9) (11) (13 14) (16))
@end example

@c EN
If the keyword argument @var{squeeze} is true, each subsequence is
represented with its first and last elements, except when the subsequence
has only one element.
@c JP
キーワード引数@var{squeeze}に真の値が与えられた場合は、
まとめた後の部分列を、その最初と最後の要素のみに置き換えます。部分列が要素ひとつだけの
場合はそのままです。
@c COMMON

@example
(group-contiguous-sequence '(1 2 3 4 7 8 9 11 13 14 16) :squeeze #t)
  @result{} ((1 4) (7 9) (11) (13 14) (16))
@end example

@c EN
The keyword argument @var{key} must be a procedure taking one argument,
and it is applied to every element in the sequence once, to construct
the result.  Its default is @code{identity}.

The keyword argument @var{next} must be a procedure
taking one argument, which is the key value (whatever @var{key} procedure
returns) and must return the ``next'' key value.
Its default is @code{(^n (+ n 1))}.

The @var{test} argument must be a procedure taking two argument
and used to compare two key values.  Its default is @code{eqv?}.
@c JP
キーワード引数@var{key}はひとつの引数を取る手続きでなければならず、
シーケンスの各要素に一回だけ適用され、その戻り値が結果を作るのに使われます。
デフォルトは@code{identity}です。

キーワード引数@var{next}はひとつの引数を取る手続きでなければならず、
キーの値(@var{key}手続きが返すもの)を受け取って、その「次」にあたるキーの値を返します。
デフォルトは@code{(^n (+ n 1))}です。

キーワード引数@var{test}はふたつの引数を取る手続きでなければならず、
ふたつのキー値が等しいかどうかを判定します。デフォルトは@code{eqv?}です。
@c COMMON

@example
(group-contiguous-sequence "AbCdFgH"
  :key char-upcase :next (^c (integer->char (+ 1 (char->integer c)))))
  @result{} ((#\A #\B #\C #\D) (#\F #\G #\H))
@end example
@end deffn

@deffn {Generic function} delete-neighbor-dups seq :key key test start end
@c MOD gauche.sequence
@c EN
Returns a sequence of the same type as @var{seq}, in which
elements in @var{seq} are included in the original order, except
duplicate adjacent elements.
The type of @var{seq} must has a builder.
@c JP
@var{seq}中で、隣り合う重複する要素を取り除いたものを
@var{seq}と同じ型のシーケンスとして返します。
@var{seq}の型はビルダーを持っていなければなりません。
@c COMMON

@example
(delete-neighbor-dups '(1 1 1 2 3 4 4 2 2 3 1 1 3))
  @result{} (1 2 3 4 2 3 1 3)

(delete-neighbor-dups '#(1 1 1 2 3 4 4 2 2 3 1 1 3))
  @result{} #(1 2 3 4 2 3 1 3)

(delete-neighbor-dups "1112344223113")
  @result{} "12342313"
@end example

@c EN
Elements are compared with @code{eqv?} by default.  You can pass
alternative procedure to @var{test} keyword argument; it is always
called as @code{(@var{test} @var{x} @var{y})},
where @var{x} and @var{y} are the contiguous elements in @var{seq}.
If elements are compared equal, the first one is kept:
@c JP
要素同士はデフォルトでは@code{eqv?}で比較されます。
@var{test}キーワード引数に代わりの比較手続きを渡すこともできます。
@var{seq}中に要素@var{x}と@var{y}がこの順で隣り合っているとすると、
比較手続きは常に@code{(@var{test} @var{x} @var{y})}として呼ばれます。
要素が等しかった場合、最初に出現する要素が残ります。
@c COMMON

@example
(delete-neighbor-dups "AaaAbBBbCCcc" :test char-ci=?)
  @result{} "AbC"
@end example

@c EN
If @var{key} is provided, it must be a procedure that takes one arguments.
It is applied to each element of @var{seq} at most once, and each resulting
value is used for the comparison instead of elements themselves.
@c JP
@var{key}キーワード引数が与えられた場合、それは1引数の手続きでなければなりません。
@var{seq}の各要素に対してその手続きは1回だけ適用され、結果が比較に使われます。
@c COMMON

@example
(delete-neighbor-dups
  '((1 . "a") (1 . "b") (2 . "c") (2 . "d"))
  :key car)
  @result{} ((1 . "a") (2 . "c"))
@end example

@c EN
The @var{start} and @var{end} arguments specify indexes in the @var{seq}
to limit the range to look at.  Where @var{start} is inclusive, @var{end}
is exclusive.
@c JP
@var{start}と@var{end}引数は@var{seq}へのインデックスで、
調べる範囲を限定します。@var{start}番目の要素から、
@var{end}番目の要素の一つ手前までが対象となります。
@c COMMON

@example
(delete-neighbor-dups "1112344223113" :start 3 :end 9)
  @result{} "2342"
@end example
@end deffn

@deffn {Generic function} delete-neighbor-dups! seq :key key test start end
@c MOD gauche.sequence
@c EN
Scan @var{seq} from left to right, dropping consecutive duplicated
elements.  The result is stored into @var{seq}, packed to left.
Note @var{seq} must be modifiable by index, i.e. @code{modifier} method
must be defined.  The rest of @var{seq} will be untouched.
Returns the next index after the last modified entry.
@c JP
@var{seq}を左から右にスキャンし、重複する要素を除いた結果を左に詰めて@var{seq}に
格納してゆきます。@var{seq}はインデックス指定で変更可能でなければなりません。
つまり、@var{modifier}メソッドが定義されてなければなりません。
詰め終わった残りの部分は変更せずに残されます。
最後に変更された場所の次のインデックスを返します。
@c COMMON

@example
(let1 v (vector 1 1 2 2 3 3 2 2 4 4)
  (list (delete-neighbor-dups! v)
        v))
  @result{} (5 #(1 2 3 2 4 3 2 2 4 4))
@end example

@c EN
The semantics of keyword arguments @var{key}, @var{test},
@var{start} and @var{end} are the same as
@code{delete-neighbor-dups}.
@c JP
キーワード引数@var{key}、@var{test}、@var{start}、@var{end}の意味は
@code{delete-neighbor-dups}と同じです。
@c COMMON

@example
(let1 v (vector 1 1 2 2 3 3 2 2 4 4)
  (list (delete-neighbor-dups! v :start 2)
        v))
  @result{} (6 #(1 1 2 3 2 4 2 2 4 4))
@end example

@c EN
Note: This method works on any sequence with @code{modifier}
method, but it's not necessarily more efficient than
@code{delete-neighbor-dups}, which creates a new sequence.
If @var{seq} is a list or a string, each modification by index takes O(n)
time (for a string even it costs O(n) extra storage), so the
total cost is O(n^2), whereas @code{delete-neighbor-dups}
needs O(n) time and storage.
This works best for vectors and alike,
with which it doesn't cost extra allocation and runs in O(n) time.
@c JP
註: このメソッドは@code{modifier}が定義されているシーケンスなら何でも
使えますが、新たなシーケンスをアロケートする@code{delete-neighbor-dups}より
効率的であるとは限りません。@var{seq}がリストや文字列であれば、
一ヶ所の変更にO(n)の時間がかかります(文字列の場合はさらにO(n)のメモリも使います)から
トータルのコストはO(n^2)になります。@code{delete-neighbor-dups}なら
時間空間ともにO(n)です。
このメソッドはベクタとその仲間で最も効率よく動作します。
余分なメモリを必要とせず、O(n)時間で済みます。
@c COMMON
@end deffn

@deffn {Generic function} delete-neighbor-dups-squeeze! seq :key key test start end
@c MOD gauche.sequence
@c EN
Operates like @code{delete-neighbor-dups} but reuses storage of @var{seq},
which will be resized by dropping duplicated elements.
Returns the sequence after dupes are removed.
@c JP
@code{delete-neighbor-dups}と同じように動作しますが、
@var{seq}の格納領域を再利用します。
@var{seq}内の重複する要素は消去され、全体の長さが短くなります。
変更後の@var{seq}を返します。
@c COMMON

@c EN
Not all sequences are resizable, so this method won't be defined
for such sequences.  The @code{gauche.sequence} module only
provides this method for @code{<list>}, in which dropping the
middle of the sequence is very efficient as it is just a
single @code{set-cdr!}.
@c JP
シーケンスは長さを変更できるとは限らないので、
このメソッドはそういったシーケンスに対しては定義されません。
@code{gauche.sequence}モジュールでは、
@code{<list>}に対してのメソッドだけが提供されます。
リストは@code{set-cdr!}を用いることで効率よく中間の要素を削除できます。
@c COMMON

@example
(delete-neighbor-dups-squeeze! (list 1 1 1 2 2 2 3 3 3))
  @result{} (1 2 3)

(delete-neighbor-dups-squeeze! (list 1 1 1 2 2 2 3 3 3 4 4)
                               :start 3 :end 9)
  @result{} (2 3)
@end example

@c EN
The semantics of keyword arguments @var{key}, @var{test},
@var{start} and @var{end} are the same as
@code{delete-neighbor-dups}.
@c JP
キーワード引数@var{key}、@var{test}、@var{start}、@var{end}の意味は
@code{delete-neighbor-dups}と同じです。
@c COMMON
@end deffn

@c EN
@subsubheading Prefix
@c JP
@subsubheading プレフィクス
@c COMMON

@deffn {Generic function} common-prefix (a <sequence>) (b <sequence>) :key key test
@c MOD gauche.sequence
@c EN
Returns a new sequence of the same type of @var{a} which contains
the common prefix of sequences @var{a} and @var{b}.  The types of
@var{a} and @var{b} doesn't need to match.
The type of @var{a} must have a builder.

For each corresponding element in @var{a} and @var{b}, the @var{key}
procedure is applied (default @code{identity}), then compared with
@var{test} procedure (default @code{eqv?}).
@c JP
シーケンス@var{a}と@var{b}に共通するプレフィクスを、@var{a}と同じ型の
新たなシーケンスで返します。@var{a}と@var{b}の型は異なっていても構いません。
@var{a}の型はビルダーを持っている必要があります。

@var{a}と@var{b}のそれぞれ対応する要素について、まず@var{key}手続きが
呼ばれ、その結果が@var{test}手続きで比較されます。省略時にはそれぞれ
@code{identity}および@code{eqv?}が使われます。
@c COMMON

@example
(common-prefix '(a b c d e) '(a b c e f))
  @result{} (a b c)

(common-prefix "abcef" '#(#\a #\b #\c #\d #\e))
  @result{} "abc"
@end example

@c EN
For strings, SRFI-13 has a specific function with
related feature: @code{string-prefix-length}
(@pxref{SRFI-13 String prefixes & suffixes}).
@c JP
文字列については、SRFI-13に似た機能を持つ手続き
@code{string-prefix-length}があります。
(@ref{SRFI-13 String prefixes & suffixes}参照)。
@c COMMON
@end deffn

@deffn {Generic function} common-prefix-to (class <class>) (a <sequence>) (b <sequence>) :key key test
@c MOD gauche.sequence
@c EN
Returns a new sequence of the type @var{class} which contains
the common prefix of sequences @var{a} and @var{b}.  The types of
@var{a} and @var{b} doesn't need to match, and neither
needs to have a builder.  The @var{class} must be a sequence class
with a builder.

The meanings of keyword arguments are the same as @code{common-prefix}.
@c JP
シーケンス@var{a}と@var{b}に共通するプレフィクスを、@var{class}の
インスタンスとして返します。@var{a}と@var{b}の型は異なっていても構わず、
ビルダーを持っていなくても構いません。@var{class}はビルダーを備えた
シーケンスのクラスである必要があります。

キーワード引数については@code{common-prefix}と同じです。
@c COMMON

@example
(common-prefix-to <list> "abcde" "ABCEF" :test char-ci=?)
  @result{} '(#\a #\b #\c)
@end example
@end deffn

@c EN
@subsubheading Permutation and shuffling
@c JP
@subsubheading 置換とシャッフル
@c COMMON

@deffn {Generic function} permute (src <sequence>) (permuter <sequence>) :optional fallback
@c MOD gauche.sequence
@c EN
Returns a newly created sequence of the same type as @var{src}, in which
the elements are permuted from @var{src} according to @var{permuter}.

@var{Permuter} is a sequence of exact integers.  When the @var{k}-th element
of @var{permuter} is @var{i}, the @var{k}-th element of the result
is @code{(ref @var{src} @var{i})}.   Therefore, the size of the result
sequence is the same as the size of @var{permuter}.  @var{Permuter}
can be any kind of sequence, unrelated to the type of @var{src}.

It is allowed that the same index @var{i} can appear more than once
in @var{permuter}.
@c JP
シーケンス@var{src}の要素を@var{permuter}に従って並べ替えた、新たなシーケンスを
作って返します。返されるシーケンスは@var{src}と同じ型です。

@var{permuter}は正確な整数のシーケンスです。@var{pertmuter}の@var{k}番目の
要素が@var{i}であれば、結果の@var{k}番目の要素が@code{(ref @var{src} @var{i})}
になります。従って結果のシーケンスの長さは@var{permuter}と長さと同じになります。
@var{permuter}の型は@var{src}の型と違っていて構いません。

同じインデックス@var{i}が複数回@var{permuter}に現れても構いません。
@c COMMON

@example
(permute '(a b c d) '(3 2 0 1))     @result{} (d c a b)
(permute '(a b c d) '(0 2))         @result{} (a c)
(permute '(a b c d) '(0 0 1 1 2 2)) @result{} (a a b b c c)
@end example

@c EN
If an integer in @var{permuter} is out of the valid range as the index
of @var{src}, then an error is signaled unless @var{fallback} is given.
If @var{fallback} is given, what value is used depends on the result of
@code{(ref @var{src} @var{i} @var{fallback})}---which usually returns
@var{fallback} for the out-of-range index @var{i}.
@c JP
@var{permuter}の要素の整数が@var{src}の有効なインデックスの範囲外であった場合、
デフォルトではエラーが通知されます。しかし@var{fallback}が与えられた場合は、
@var{src}の要素の読み出しが@code{(ref @var{src} @var{i} @var{fallback})}
として行われます。これは通常、@var{i}が範囲外であった場合に@var{fallback}を
返します。
@c COMMON

@example
(permute '#(a b c) '(3 2 1 0) 'foo) @result{} #(foo c b a)

(permute "!,HWdelor" #(2 5 6 6 7 1 -1 3 7 8 6 4 0) #\space)
  @result{} "Hello, World!"
@end example
@end deffn

@deffn {Generic function} permute-to (class <class>) (src <sequence>) (permuter <sequence>) :optional fallback
@c MOD gauche.sequence
@c EN
Like @code{permute}, but the result will be an instance of the given @var{class}
instead of the class of @var{src}.
@c JP
結果のシーケンスが@var{src}の型でなく@var{class}になること以外は、
@code{permute}と同じです。
@c COMMON

@example
(permute-to <string> '(#\a #\b #\c #\d #\r)
            '(0 1 4 0 2 0 3 0 1 4 0))
  @result{} "abracadabra"
@end example
@end deffn

@deffn {Generic function} permute! (src <sequence>) (permuter <sequence>) :optional fallback
@c MOD gauche.sequence
@c EN
Also like @code{permute}, but the result is stored back to @var{src}.
@var{Src} must be a mutable sequence, and @var{permuter} must be equal length
to or shorter than @var{src}.
@c JP
これも@code{permute}と似ていますが、結果は新たに作られるシーケンスではなく
@var{src}を破壊的変更して格納されます。@var{src}は変更可能でなければならず、
@var{permuter}は@var{src}と同じ長さかそれより短くなければなりません。
@c COMMON

@c EN
If @var{permuter} is shorter than @var{src}, the remaining elements
of @var{src} is left alone if @var{fallback} isn't provided,
or filled with @var{fallback} if provided.
@c JP
@var{permuter}が@var{src}より短い場合、@var{fallback}が与えられなければ
@var{src}の残りの部分は変更されず、@var{fallback}が与えられた場合は
それで埋められます。
@c COMMON

@example
(rlet1 v (list 'a 'b 'c 'd 'e)
  (permute! v '(2 1 0 4 3))) @result{} (c b a e d)

(rlet1 v (list 'a 'b 'c 'd 'e)
  (permute! v '(2 2 0))) @result{} (c c a d e)

(rlet1 v (list 'a 'b 'c 'd 'e)
  (permute! v '(2 2 0) 'z)) @result{} (c c a z z)
@end example

@c EN
If @var{permuter} contains index outside of the valid range of @var{src},
@var{fallback} must be provided, and it is set to the corresponding element.
@c JP
@var{permuter}が@var{src}の有効な範囲外のインデックスを含んでいた場合は
@var{fallback}が与えられなければならず、対応する要素が@var{fallback}で
埋められます。
@c COMMON

@example
(rlet1 v (list 'a 'b 'c 'd 'e)
  (permute! v '(5 4 3 -1 1) 'z)) @result{} (z e d z b)
@end example
@end deffn

@deffn {Generic Function} inverse-permuter (permuter <sequence>) :optional fallback
@c MOD gauche.sequence
@c EN
Computes and returns the inverse of
@var{permuter}, which is a sequence of exact nonnegative integers,
@code{[X_0 X_1 ... X_i ... X_n]},
specifying the @code{i}-th element of the original sequence to be mapped to
@code{X_i}.
The inverse permuter is a sequence of exact integers of the same
type as @code{permuter}, in which
@code{X_i}-th index contains @code{i}.
The sequence type of @var{permuter} must have a builder.
@c JP
@var{permuter}の逆写像を計算して返します。
@var{permuter}は整数のシーケンス@code{[X_0 X_1 ... X_i ... X_n]}で、
@code{i}番目の要素が@code{X_i}番目に写像されることを示します。
その逆写像は、@code{X_i}番目の要素が@code{i}番目に写される写像です。
返されるシーケンスは@var{permuter}と同じクラスになります。
@var{permuter}のクラスはビルダーを実装していなければなりません。
@c COMMON

@example
(inverse-permuter '#(3 0 1 4 2))
 @result{} #(1 2 4 0 3)
@end example

@c EN
@var{Permuter} must be injective, that is, every element in it
must be unique; otherwise, an error is signaled.
If @var{permuter} is not bijective, that is, there can be
elements in the codomain that not eleemnts in the domain is mapped,
the inverse permutation maps such codomain's elements to @var{fallback}
if provided, or an error is signaled.
@c JP
@var{permuter}は単射、つまり定義域の要素の各々は終域の別の要素に写像されなければ
なりません。そうでなければエラーが投げられます。
@var{permuter}が全射でない場合、つまり終域の要素のうち定義域から写像されない
ものがあった場合、@var{fallback}が与えられていれば逆写像はそのインデックスを使い、
与えられていなければエラーが投げられます。
@c COMMON

@example
(inverse-permuter '#s8(5 3 0) -1))
  @result{} #s8(2 -1 -1 1 -1 0)
@end example
@end deffn

@deffn {Generic function} unpermute (src <sequence>) (permuter <sequence>) :optional fallback
@deffnx {Generic function} unpermute-to (class <class>) (src <sequence>) (permuter <sequence>) :optional fallback
@deffnx {Generic function} unpermute! (src <sequence>) (permuter <sequence>) :optional fallback
@c MOD gauche.sequence
@c EN
Inverse of @code{permute} etc. if the permutation is bijective.
@c JP
置換が全単射であれば、これらは@code{permute}の逆関数です。
@c COMMON

@example
(permute '(a b c d) '(3 1 2 0)) @result{} (d b c a)
(unpermute '(d b c a) '(3 1 2 0)) @result{} (a b c d)
@end example

@c EN
If the permutation isn't surjective (but injective),
those procedures try to fill the undeterminable element with @var{fallback}
if provided, or signal an error if @var{fallback} isn't provided.
Note that the length of result sequence of @code{unpermute}
is the maximum index in the @var{permuter} plus one.  It doesn't fill
the result beyond it.
@c JP
もし置換が全射でない(けれども単射ではある)場合、
@var{fallback}が与えられていれば決定できない要素がそれで埋められます。
@var{fallback}が与えられなければエラーが投げられます。
但し、戻り値の大きさは@code{permuter}内の最大のインデックス+1になるので、
それ以降の要素が埋められることはありません。
@c COMMON

@example
(permute '(a b c d e) '(4 0 2)) @result{} (e a c)
(unpermute '(e a c) '(4 0 2) 'Z) @result{} (a Z c Z e)

(permute '(a b c d e) '(3 2 1)) @result{} (d c b)
(unpermute '(d c b)) '(3 2 1) 'Z) @result{} (Z b c d)
@end example
@end deffn


@deffn {Generic function} shuffle (src <sequence>) :optional random-source
@c MOD gauche.sequence
@c EN
Returns a new sequence of the same type and size as @var{src},
in which elements are randomly permuted.
@c JP
@var{src}と同じ型、長さのシーケンスで、@var{src}の要素の順序がランダムに
置き換えられたものを返します。
@c COMMON

@example
(shuffle '(a b c d e))  @result{} (e b d c a)
(shuffle "abcde")       @result{} "bacde"
@end example

@c EN
This generic function uses SRFI-27 (@pxref{Sources of random bits}).
By default it uses @code{default-random-source}, but you can pass
an alternative random source by the optional argument.
@c JP
このジェネリックファンクションはSRFI-27 (@ref{Sources of random bits}参照)
を使っています。デフォルトでは乱数源として@code{default-random-source}が
使われますが、省略可能引数に乱数源を渡すこともできます。
@c COMMON
@end deffn

@deffn {Generic function} shuffle-to (class <class>) (src <sequence>) :optional random-source
@c MOD gauche.sequence
@c EN
Like @code{shuffle}, except that the result will be an instance of
@var{class} instead of the class of @var{src}.
@c JP
結果を@var{src}の型ではなく@var{class}のインスタンスとして返す@code{shuffle}です。
@c COMMON
@end deffn

@deffn {Generic function} shuffle! (src <sequence>) :optional random-source
@c MOD gauche.sequence
@c EN
Like @code{shuffle}, but the result is stored back to @var{src}.
@var{Src} must be a mutable sequence.
@c JP
結果を@var{src}を破壊的変更して格納する@code{shuffle}です。
@var{src}は変更可能でなければなりません。
@c COMMON
@end deffn


@node Implementing sequences,  , Other operations over sequences, Sequence framework
@subsection Implementing sequences
@c NODE シーケンスを実装する

@c EN
When you define your own aggregate class that holds ordered objects,
you can follow the sequence protocol below to make it sequence.
@c JP
複数のオブジェクトを順序づけて保持するクラスを定義した場合、
次のシーケンスプロトコルを実装することで、それをシーケンスにすることができます。
@c COMMON

@c EN
@strong{Inherit @code{<sequence>}}: You need to derive your class
from @code{<sequence>}, so that sequence-related methods can be uniformly
used.  Note that @code{<sequence>} inherits @code{<collection>}, so your
class will also be a collection.
@c JP
@strong{@code{<sequence>}を継承する}:
ユーザ定義クラスが@code{<sequence>}を継承することにより、
シーケンス関連のメソッドが一様に使えるようになります。なお、@code{<sequence>}は
@code{<collection>}を継承しているので、そのクラスはコレクションにもなります。
@c COMMON

@c EN
@strong{Implement collection protocol}: A sequence is also a collection,
and you need to implement a collection protocol
(@pxref{Implementing collections}).
For the very least, you need to have @code{call-with-iterator} method.
If you want your sequence to be buildable,
you also need to have @code{call-with-builder} method.
All other collection generic functions have
default method on top of these two, so they'll work; though
you can specialize other collection generic functions if it's
more efficient.  We strongly recommend to specialize @code{size-of},
for its default method walks over the entire sequence to find its size,
which can be very ineffient (O(N) time).
@c JP
@strong{コレクションプロトコルを実装する}: シーケンスはコレクションでもあるので、
コレクションプロトコルを実装しなければなりません
(@ref{Implementing collections})。
少なくとも@code{call-with-iterator}メソッドが必要で、ビルダブルにしたいなら
@code{call-with-builder}も必要です。
それ以外のコレクションジェネリックファンクションは、
デフォルトメソッドがこれら二つのプリミティブの上に作られているので、
他のメソッドを定義しなくてもコレクションAPIが使えます。
ただ、他のジェネリックファンクションも特定化することで、
ショートカットして性能が見込めるならそうするのが良いでしょう。
特に@code{size-of}は、デフォルトメソッドは
@code{call-with-iterator}で全要素を数え上げるO(N)時間を要するので、
可能なら専用メソッドを定義することを強くおすすめします。
@c COMMON

@c EN
@strong{Implement sequence protocol}: You need to define @code{referencer},
@code{modifier}, at least.
If your sequence is immutable, you can leave @code{modifier} undefined
(the default method raises an error).  Again, you may want to
specialize other generic functions if it's more efficient.
It is recommended to define @code{call-with-reverse-iterator} as well,
which is used for operations that walks the sequence in the reverse order
(e.g. @code{fold-right)}.  If @code{call-with-reverse-iterator} is not
specialized, the default method uses @code{call-with-iterator}
and keeps all the elements temporarily during execution, which
takes O(N) space.
@c JP
@strong{シーケンスプロトコルを実装する}: 少なくとも@code{referencer}と
@code{modifier}を実装する必要があります。
シーケンスが変更不可なら@code{modifier}は未定義のままにすることもできます。
デフォルトメソッドはエラーを投げます。
ここでも、性能向上が見込めるなら他のシーケンスAPIを特定化するのが良いでしょう。
可能なら、@code{call-with-reverse-iterator}も定義することをおすすめします。
シーケンスを逆順にたどるAPI (例: @code{fold-right}) は、このメソッドが定義されていれば
それを使います。定義されていなければ、@code{call-with-iterator}で一旦全要素を
取り出す必要があるのでO(N)空間を消費します。
@c COMMON

@c ----------------------------------------------------------------------
@c @node Serializer, Terminal control, Simple dispatcher, Library modules
@c @section @code{gauche.serializer} - Serializer

@c @deftp {Module} gauche.serializer
@c @mdindex gauche.serializer
@c @end deftp

@c ----------------------------------------------------------------------
@node  Syslog, Terminal control, Sequence framework, Library modules - Gauche extensions
@section @code{gauche.syslog} - Syslog
@c NODE Syslog, @code{gauche.syslog} - Syslog

@deftp {Module} gauche.syslog
@mdindex gauche.syslog
@c EN
This module provides syslog(3) system logger interface.

For the common applications, you might find @code{gauche.logger} module
easier to use (@pxref{User-level logging}).   For the portable code,
you might want to look at SRFI-215 (@pxref{Central log exchange}).
This module is for those who need direct access to the syslog API.

The procedures are only defined if the underlying system supports them.
@c JP
このモジュールは syslog(3) のシステムロガーのインタフェースを提供します。

一般的なアプリケーションについては、@code{gauche.logger} モジュールの
ほうが使いやすいでしょう(@ref{User-level logging}参照)。
また、ポータブルなコードを書く場合は、SRFI-215が使えます
(@ref{Central log exchange}参照)。
このモジュールは syslog の API に直接アクセスする必要のある人向きです。

手続き群は基盤になっているシステムで syslog がサポートされている場合に
のみ定義されます。
@c COMMON
@end deftp

@defun sys-openlog ident option facility
[POSIX]
@c MOD gauche.syslog
@c EN
Opens a connection to the system logger.  A string argument
@var{ident} is used for the prefix of the log, and usually is
the program name.  @var{Option} is an integer flag to control
the behavior of logging, and @var{facility} is an integer
that specify the type of the program.

The flag for @var{option} can be composed by @code{logior}-ing
one or more of the following integer constants:
@code{LOG_CONS}, @code{LOG_NDELAY}, @code{LOG_NOWAIT},
@code{LOG_ODELAY}, @code{LOG_PERROR} and @code{LOG_PID}.
(Some of the constants may not be defined if the underlying system
doesn't support them).

The @var{facility} argument can be one of the following integer
constants: @code{LOG_AUTH}, @code{LOG_AUTHPRIV}, @code{LOG_CRON},
@code{LOG_DAEMON}, @code{LOG_FTP}, @code{LOG_KERN}, @code{LOG_LOCAL0}
through @code{LOG_LOCAL7}, @code{LOG_LPR}, @code{LOG_MAIL}, @code{LOG_NEWS},
@code{LOG_SYSLOG}, @code{LOG_USER} and @code{LOG_UUCP}.
(Some of the constants may not be defined if the underlying system
doesn't support them).

See your system's manpage of openlog(3) for detail description about
these constants.
@c JP
システムロガーへのコネクションをオープンします。文字列の引数 @var{ident}
はログの接頭辞に使われます。通常はプログラムを名前にします。@var{option}
は整数のフラグで、ログの振舞いを制御します。@var{facility} はプログラムの
タイプを指定する整数です。

@var{option}のフラグは以下の整数定数の1つまたは複数を @code{logior} で
合成することができます：
@code{LOG_CONS}、@code{LOG_NDELAY}、@code{LOG_NOWAIT}、
@code{LOG_ODELAY}、@code{LOG_PERROR} および @code{LOG_PID} です
(これらの定数のいくつかは基盤となるシステムがサポートしていなければ
定義されません)。

@var{facility} 引数は以下の整数定数のどれかひとつです。
@code{LOG_AUTH}、@code{LOG_AUTHPRIV}、@code{LOG_CRON},
@code{LOG_DAEMON}、@code{LOG_FTP}、@code{LOG_KERN}、@code{LOG_LOCAL0}、
から @code{LOG_LOCAL7}、@code{LOG_LPR}、@code{LOG_MAIL}、@code{LOG_NEWS},
@code{LOG_SYSLOG}、@code{LOG_USER}、@code{LOG_UUCP} までです。
(これらの定数のいくつかは基盤となるシステムがサポートしていなければ
定義されません)。

これらの定数の詳しい説明については、システムの openlog(3) の
マニュアル・ページを見てください。
@c COMMON
@end defun

@defun sys-syslog priority message
[POSIX]
@c MOD gauche.syslog
@c EN
Log the string @var{message}.  Unlike syslog(3), this procedure doesn't
do formatting---you can use @code{format} (@pxref{Output}) to create
a formatted message, or use higher-level routine @code{log-format}
(@pxref{User-level logging}).

An integer argument @var{priority} can be composed by @code{logior}-ing
one of the @var{facility} constants described above and
the @var{level} constants: @code{LOG_EMERG}, @code{LOG_ALERT},
@code{LOG_CRIT}, @code{LOG_ERR}, @code{LOG_WARNING}, @code{LOG_NOTICE},
@code{LOG_INFO}, @code{LOG_DEBUG}.
@c JP
文字列 @var{message} をログに記録します。syslog(3) とは違って、この手続きは
フォーマットを行いません。フォーマットされた文字列を生成するなら
@code{format} (@ref{Output}参照)が使えます。あるいは、より高水準の
ルーチン @code{log-format} (@ref{User-level logging}参照)
を使うこともできます。

整数の引数 @var{priority} は上述の @var{facility} 定数のどれかひとつ
と、以下の@var{level}定数と@code{logior}して、合成することができます：
@code{LOG_EMERG}、@code{LOG_ALERT}、@code{LOG_CRIT}、@code{LOG_ERR}、
@code{LOG_WARNING}、@code{LOG_NOTICE}、@code{LOG_INFO}、@code{LOG_DEBUG}
@c COMMON

@end defun

@defun sys-closelog
[POSIX]
@c MOD gauche.syslog
@c EN
Closes the connection to the logging system.
@c JP
ロギングシステムとのコネクションをクローズします。
@c COMMON
@end defun

@defun sys-setlogmask mask
[POSIX]
@c MOD gauche.syslog
@c EN
Sets the process's log priority mask that determines which calls to
@code{sys-syslog} may be logged.
An priority @var{mask} can be composed by @code{logior}-ing
bitmasks corresponding to the @var{level} argument of @code{sys-syslog}.
You can use @code{sys-logmask} below to obtain a bitmask
from the level.
@c JP
どの @code{sys-syslog}への呼び出しを記録できるかを決める、プロセスのログ
優先度マスクを設定します。
優先度マスク@var{mask}は@code{sys-syslog}の@var{level}引数に
対応するビットマスクを@code{logior}することで作成できます。
レベルに対応するビットマスクは下の@code{sys-logmask}から
取得することができます。
@c COMMON
@end defun

@defun sys-logmask level
[POSIX]
@c MOD gauche.syslog
@c EN
Returns an integer bitmask for @code{sys-setlogmask} from
the log level @var{level}.
@c JP
ログレベル @var{level} から @code{sys-setlogmask} に対する
ビットマスク整数を返します。
@c COMMON
@end defun

@c ----------------------------------------------------------------------
@node Terminal control, Unit testing, Syslog, Library modules - Gauche extensions
@section @code{gauche.termios} - Terminal control
@c NODE 端末の制御, @code{gauche.termios} - 端末の制御

@deftp {Module} gauche.termios
@mdindex gauche.termios
@c EN
This module provides procedures to control terminals.
On Unix platforms, the low-level API provides POSIX termios interface
as the module name suggests.  This module also provides
pseudo tty interface, if the system supports it.
@c JP
このモジュールは端末の制御のための手続きを提供します。
Unix環境では、低レベルAPIはモジュール名からわかるように
POSIX termiosへのインタフェースを提供しています。
さらに、このモジュールでは、システムがサポートしている場合には
擬似 tty のインタフェースも提供しています。
@c COMMON

@c EN
On Windows native platforms, POSIX termios interface is not
available.  It is too different from Windows console API to
provide a meaningful emulation.  The low-level Windows console
API is available in the @code{os.windows} module
(@pxref{Windows support}).   You can still use high-level
terminal control procedures in this module.
@c JP
Windowsネイティブ環境ではPOSIX termiosインタフェースは使えません。
Windows console APIは大きく違っているので、意味のあるエミュレーションを
提供するのが難しいためです。低レベルのWindows console APIは
@code{os.windows}モジュールで使うことができます(@ref{Windows support}参照)。
ただし、このモジュールの高レベル端末制御手続きは、
Windowsネイティブ環境でも使うことができます。
@c COMMON
@end deftp

@menu
* Posix termios interface::
* Common high-level terminal control::
@end menu

@node Posix termios interface, Common high-level terminal control, Terminal control, Terminal control
@subsection Posix termios interface
@c NODE POSIX termiosインタフェース

@c EN
These procedures are available when the feature identifier
@code{gauche.os.windows} is @emph{not} defined.   See @code{cond-expand}
in @ref{Feature conditional} for how to switch code using
feature identifiers.
@c JP
ここに挙げる手続きは、機能シンボル@code{gauche.os.windows}が定義されて@emph{いない}
場合にのみ利用可能です。機能シンボルによってコードを切り替える方法は
@ref{Feature conditional}の@code{cond-expand}を参照してください。
@c COMMON

@deftp {Builtin Class} <sys-termios>
@clindex sys-termios
@c MOD gauche.termios
@c EN
POSIX termios(7) structure.
@c JP
POSIX termios(7) の構造体です。
@c COMMON

@defivar {<sys-termios>}  iflag
@end defivar
@defivar {<sys-termios>}  oflag
@end defivar
@defivar {<sys-termios>}  cflag
@end defivar
@defivar {<sys-termios>}  lflag
@end defivar
@defivar {<sys-termios>}  cc
@end defivar

@c EN
The slots @code{iflag}, @code{oflag}, @code{cflag} and @code{lflag}
contains non-negative integers representing bitmasks.

The slot @code{cc} contains a @emph{copy} of @code{c_cc} array
of @code{struct termios}, as an u8vector (see @ref{Uniform vectors}
for the details about u8vector).
Since @code{cc} slot is a copy of the internal structure, you have
to @code{set!} an u8vector to the slot explicitly to make
changes to the @code{c_cc} array.
@c JP
@code{iflag}、@code{oflag}、@code{cflag}、@code{lflag}の各スロットは、
対応するビットマスクを非負の整数で表現した値を保持しています。

また、@code{cc}スロットは@code{struct termios}の@code{c_cc}配列の
@emph{コピー}を返します。
@code{c_cc}配列の値を変えたい場合は、変更したu8vectorを明示的に
@code{cc}スロットに@code{set!}して下さい。
@c COMMON

@end deftp

@c EN
Throughout this section, argument @var{port-or-fd} refers to
either a port object or a small integer representing system's file
descriptor.  If @var{port} is not associated
to the system terminal, an error is signaled.  (You can check if @var{port}
has an associated terminal by @code{sys-isatty?}.
@pxref{Other file operations}).
@c JP
このセクションを通じて、引数 @var{port-or-fd} はポートオブジェクトか
システムのファイルディスクリプタを表現する小さい整数かのどちらかです。
@var{port}がシステム端末に結びついていないければ、エラーになります。
(@code{sys-isatty?}を使えば@var{port}が端末と結びついているか
どうかチェックできます。 @ref{Other file operations}参照)
@c COMMON

@defun sys-tcgetattr port-or-fd
@c MOD gauche.termios
@c EN
Returns terminal parameters in a @code{<sys-termios>} object,
associated to @var{port-or-fd}.
@c JP
@var{port-or-fd} と結びついている @code{<sys-termios>}オブジェクトの
端末パラメータを返します。
@c COMMON
@end defun

@defun sys-tcsetattr port-or-fd when termios
@c MOD gauche.termios
@c EN
Sets terminal parameters associated to @var{port-or-fd} by @var{termios},
which must be an instance of @code{<sys-termios>}.

An integer argument @var{when} specifies when the changes take effect.
Three variables are pre-defined for the argument:
@c JP
@var{port-or-fd}と結びついている端末のパラメータを @var{termios} に設定します。
@var{termios} は @code{<sys-termios>} のインスタンスでなければなりません。

整数の引数@var{when}はいつ変更を有効にするかを指定します。
この引数用に3つの変数があらかじめ定義されています。
@c COMMON
@table @code
@item TCSANOW
@vindex TCSANOW
@c EN
The change is reflected immediately.
@c JP
変更を直ちに反映します。
@c COMMON
@item TCSADRAIN
@vindex TCSADRAIN
@c EN
The change is reflected after all pending output is flushed.
@c JP
変更を、すべてのペンディングになっている出力がフラッシュされた後に反映します。
@c COMMON
@item TCSAFLUSH
@vindex TCSAFLUSH
@c EN
The change is reflected after all pending output is flushed,
and all pending input is discarded.
@c JP
変更を、すべてのペンディングになっている出力がフラッシュされ、かつ、
すべてのペンディングになっている入力が破棄されたあとに反映します。
@c COMMON
@end table
@end defun

@defun sys-tcsendbreak port-or-fd duration
@c MOD gauche.termios
@c EN
Transmits a zero stream for the specified duration
to the terminal associated to @var{port-or-fd}.
The unit of duration depends on the system; see man tcsendbreak(3) of
your system for details.
@c JP
ゼロストリームを指定した時間、@var{port-or-fd}と結びついている端末に
送出します。時間の単位はシステム依存です。詳しくは、お使いの
システムのマニュアルページ tcsendbreak(3)を参照してください。
@c COMMON
@end defun

@defun sys-tcdrain port-or-fd
@c MOD gauche.termios
@c EN
Waits until all output written to @var{port-or-fd} is transmitted.
@c JP
@var{port-or-fd}へのすべての出力が送出されるまで待ちます。
@c COMMON
@end defun

@defun sys-tcflush port-or-fd queue
@c MOD gauche.termios
@c EN
Discards data in the buffer of @var{port-or-fd}, specified by
@var{queue}, which may be one of the following values.
@c JP
@var{port-or-fd}のバッファ内のデータを破棄します。@var{queue}には以下の値の
どれかを指定します。
@c COMMON
@table @code
@item TCIFLUSH
@vindex TCIFLUSH
@c EN
Discards data received but not read.
@c JP
受信データしたが読み込んではいないデータを破棄します。
@c COMMON
@item TCOFLUSH
@vindex TCOFLUSH
@c EN
Discards data written but not transmitted.
@c JP
書き出したが送出していないデータを破棄します。
@c COMMON
@item TCIOFLUSH
@vindex TCIOFLUSH
@c EN
Do both @code{TCIFLUSH} and @code{TCOFLUSH} action.
@c JP
@code{TCIFLUSH} と @code{TCOFLUSH} の両方の動作をします。
@c COMMON
@end table
@end defun

@defun sys-tcflow port-or-fd action
@c MOD gauche.termios
@c EN
Controls data flow of @var{port-or-fd} by @var{action}, which may be
one of the following values:
@c JP
@var{port-or-fd}のデータフローを@var{action}で制御します。@var{action}は
以下の値のうちどれかです。
@c COMMON
@table @code
@item TCOOFF
@vindex TCOOFF
@c EN
Suspends output transmission.
@c JP
出力の送出をサスペンドします。
@c COMMON
@item TCOON
@vindex TCOON
@c EN
Restarts output transmission.
@c JP
出力の送出を再開します。
@c COMMON
@item TCIOFF
@vindex TCIOFF
@c EN
Transmits a STOP character to make the terminal device stop transmitting
data to the system.
@c JP
端末デバイスがシステムへの送出を止めるよう STOP 文字を送出する。
@c COMMON
@item TCION
@vindex TCION
@c EN
Transmits a START character to make the terminal device resume transmitting
data to the system.
@c JP
端末デバイスがシステムへの送出を再開するよう START 文字を送出する。
@c COMMON
@end table
@end defun

@defun sys-tcgetpgrp port-or-fd
@c MOD gauche.termios
@c EN
Returns process group ID of the terminal associated to @var{port-or-fd}.
@c JP
@var{port-or-fd}の結びついている端末のプロセスのグループIDを返します。
@c COMMON
@end defun

@defun sys-tcsetpgrp port-or-fd pgrp
@c MOD gauche.termios
@c EN
Sets process group ID of the terminal associated to @var{port-or-fd}
to @var{pgrp}.
@c JP
@var{port-or-fd}の結びついている端末のプロセスのグループIDを@var{pgrp}に
設定します。
@c COMMON
@end defun

@defun sys-cfgetispeed termios
@defunx sys-cfsetispeed termios speed
@defunx sys-cfgetospeed termios
@defunx sys-cfsetospeed termios speed
@c MOD gauche.termios
@c EN
Gets/sets input/output speed (baud rate) parameter stored in @var{termios}
object.   Speed is represented by the following predefined numbers:
@code{B0}, @code{B50}, @code{B75}, @code{B110}, @code{B134},
@code{B150}, @code{B200}, @code{B300}, @code{B600}, @code{B1200},
@code{B1800}, @code{B2400}, @code{B4800}, @code{B9600},
@code{B19200}, @code{B38400}.
@c JP
@var{termios}内の入出力スピード(ボーレート)を取得/設定します。スピードは
以下の定義ずみの数値で表現されてます：
@code{B0}、@code{B50}、@code{B75}、@code{B110}、@code{B134}、
@code{B150}、@code{B200}、@code{B300}、@code{B600}、@code{B1200}、
@code{B1800}、@code{B2400}、@code{B4800}、@code{B9600}、
@code{B19200}、@code{B38400}。
@c COMMON

@c EN
Some system may support higher baud rate, such as @code{B57600},
@code{B115200} or @code{B230400}.  You can use @code{symbol-bound?}
to check these options are defined.  @code{B0} is used to
terminate the connection.
@c JP
もっと速いボーレート、たとえば、@code{B57600}、
@code{B115200} あるいは @code{B230400} をサポートしている
システムもあります。@code{symbol-bound?}をつかえば、これらの
オプションが定義されているかどうかをチェックできます。@code{B0}
はコネクションを終了するのに使われます。
@c COMMON
@end defun

@defun sys-openpty :optional term
@c MOD gauche.termios
@c EN
Opens a pair of pseudo ttys, one for master and the other for slave,
then returns two integers which are their file descriptors.
An optional argument @var{term} must be, if passed, a @code{<sys-termios>}
object; it sets the slave pty's parameters.

You can use @code{open-input-fd-port} and/or @code{open-output-fd-port}
to create a port around the returned file descriptor (@pxref{File ports}).
To obtain pseudo tty's name, use @code{sys-ttyname}
(@pxref{Other file operations}).

This function is available only if the system supports @code{openpty(3)}.
@c JP
擬似 tty のペア、マスターとスレーブをオープンし、2つの
ファイルディスクリプタの整数を返します。オプション引数 @var{term}
が渡される場合は、@code{<sys-termios>}オブジェクトでなければなりません。
これは、pty パラメータを設定します。

@code{open-input-fd-port}と@code{open-output-fd-port}の両方またはどちらか
を返されたファイルディスクリプタに対するポートを生成するために使うことが
できます(@ref{File ports}参照)。擬似端末の名前を得るには @code{sys-ttyname}
を使います(@ref{Other file operations}参照)。

この関数はシステムが @code{openpty(3)} をサポートしている場合にのみ利用
可能です。
@c COMMON
@end defun

@defun sys-forkpty :optional term
@c MOD gauche.termios
@c EN
Opens a pair of pseudo ttys, one for master and the other for slave,
sets the slave pty suitable for login terminal, then fork(2).

Returns two integers; the first value is a child pid for the parent process,
and 0 for the child process.  The second value is a file descriptor
of the master pty.

An optional argument @var{term} must be, if passed, a @code{<sys-termios>}
object; it sets the slave pty's parameters.

This function is available only if the system supports @code{forkpty(3)}.
@c JP
擬似 ttyのペア、マスターとスレーブをオープンし、スレーブ sty を
ログイン端末になるよう設定し、fork(2) します。

二つの整数、最初の値は親プロセスに対しては子の pid の値で、0ならば
子プロセスです。ふたつ目の値はマスター pty のファイルディスクリプタの
値です。

オプション引数 @var{term}が渡される場合は、それは@code{<sys-termios>}オブジェクト
でなければなりません。これはスレーブ pty のパラメータを設定します。

この関数はシステムが @code{forkpty(3)} をサポートしている場合にのみ利用
可能です。
@c COMMON

@c EN
Note: @code{sys-forkpty} has the same MT hazard as @code{sys-fork}
(see @ref{Process management}, for details).  If you're
running multiple threads, use @code{sys-forkpty-and-exec} below.
@c JP
注意: @code{sys-forkpty}には@code{sys-fork}と同様のマルチスレッドハザー
ドの危険性があります。(詳細については@ref{Process management}参照
してください)。マルチスレッドプログラムでは後述の
@code{sys-forkpty-and-exec}を利用してください。
@c COMMON
@end defun

@defun sys-forkpty-and-exec command args :key iomap term sigmask
@c MOD gauche.termios
@c EN
Does @code{sys-forkpty}, and lets the child process
immediately @code{exec}s the specified @var{command}
with arguments @var{args}.   This function doesn't have
the hazard in multi-thread environment.
@c JP
@code{sys-forkpty}して、ただちに指定した@var{command}を引数
@var{args}で子プロセスで@code{exec}します。この関数にはマルチスレッド
環境でもハザードを起こしません。
@c COMMON

@c EN
The meanings of arguments @var{command}, @var{args}, @var{iomap} and
@var{sigmask}
are the same as @code{sys-exec} (see @ref{Process management}).
If the keyword argument @var{term} is given, it is used to initialize
the slave pty.
@c JP
引数@var{command}、@var{args}、@var{iomap}、@var{sigmask}の意味は
@code{sys-exec}のものと同じです。(@ref{Process management}を見て
ください)。キーワード引数@var{term}が与えられれば、スレーブptyの初期化
に使われます。
@c COMMON
@end defun

@node Common high-level terminal control,  , Posix termios interface, Terminal control
@subsection Common high-level terminal control
@c NODE 共通の高レベル端末制御

@defun without-echoing iport proc
@c MOD gauche.termios
@c EN
If @var{iport} is an input port connected to a terminal,
sets the terminal mode non-echoing and call @var{proc} with
@var{iport} as an argument.  Before returning from
@code{without-echoing}, or throwing an error,
the terminal mode is reset to the original state when this
procedure is called.  The procedure returns whatever value(s)
@var{proc} returns.
@c JP
@var{iport}が端末につながった入力ポートである場合、
端末をエコーしないモードにして@var{proc}を呼びます。@var{proc}には
@var{iport}が引数として渡されます。
@var{proc}から戻るか、@var{proc}がエラーを投げた場合に、
端末は元のモードに戻されます。@var{proc}からの戻り値が@code{without-echoing}の
戻り値となります。
@c COMMON

@c EN
You can also pass @code{#f} to @var{iport}.  In that case,
this procedure tries to open a console (@code{/dev/tty} on Unix,
@code{CON} on Windows) and set the console mode, then calls
@var{proc} with the opened input port.  An error is thrown
if the procedure can not open a console.
@c JP
@var{port}に@code{#f}を渡すこともできます。その場合、
この手続きは標準の端末 (Unixでは@code{/dev/tty}、Windowsでは@code{CON})を
オープンし、そにこつながった入力ポートを引数に@var{proc}を呼び出します。
標準の端末がオープンできない場合はエラーが投げられます。
@c COMMON

@c EN
If @var{iport} is other than above, this procedure
simply calls @var{proc} with @var{iport}.  This allows
the caller to read password from redirected input,
for example.
@c JP
@var{iport}が上記のいずれにも該当しない場合は、単に@var{proc}を@var{iport}を引数にして
呼び出し結果を返します。
例えば、端末からエコーなしでパスワードを読むのと、
リダイレクトでパスワードが流し込まれるのとを、区別せずに処理できます。
@c COMMON

@c EN
Note: Because of an implementation issue, on Windows native
platforms this procedure always changes console mode
of the standard input handle when @code{iport} is either
@code{#f} or a terminal input port.
@c JP
註: 実装上の問題から、Windowsでは、@var{iport}が@code{#f}もしくは
端末につながっている場合、常に標準入力ハンドルのモードが変更されます。
@c COMMON
@end defun

@defun has-windows-console?
@c MOD gauche.termios
@c EN
Returns @code{#t} iff the running Gauche is Windows-native and
the process has attached console.  On Unix platforms this
procedure always returns @code{#f}.
@c JP
走っているGaucheがWindowsネイティブで、プロセスが端末を持っている場合に@code{#t}を
返します。Unixプラットフォームでは常に@code{#f}が返されます。
@c COMMON

@c EN
The reason that @code{cond-expand} isn't enough is that on Windows
the program may start without console, but you can attach console
afterwards.  @xref{Windows console API}, for the details.
@c JP
この用途に@code{cond-expand}は不適です。というのも、Windowsプログラムは
端末なしで起動した後に端末をアタッチする、といったことができるからです。
詳しくは@ref{Windows console API}参照。
@c COMMON
@end defun


@c ----------------------------------------------------------------------
@node Unit testing, Threads, Terminal control, Library modules - Gauche extensions
@section @code{gauche.test} - Unit Testing
@c NODE 単体テスト, @code{gauche.test} - 単体テスト

@deftp {Module} gauche.test
@mdindex gauche.test
@c EN
Defines a set of functions to write test scripts.
A test script will look like this:
@c JP
テストスクリプトを書くための手続きを提供します。
テストスクリプトは次のような形になります。
@c COMMON

@lisp
(use gauche.test)
(test-start "my feature")
@c EN
(load "my-feature")  ; @r{load your program}
(import my-feature)  ; @r{if your program defines a module.}

(test-module 'my-feature) ; @r{tests consistency in your module.}
@c JP
(load "my-feature")  ; @r{テストすべきプログラムをロード}
(import my-feature)  ; @r{モジュールを定義している場合はインポート}

(test-module 'my-feature) ; @r{モジュールの一貫性チェック}
@c COMMON

(test-section "feature group 1")
(test "feature 1-1" EXPECT (lambda () TEST-BODY))
(test "feature 1-2" EXPECT (lambda () TEST-BODY))
 @dots{}

(test-section "feature group 2")
(define test-data ...)
(test "feature 2-1" EXPECT (lambda () TEST-BODY))
(test "feature 2-2" (test-error) (lambda () TEST-THAT-SIGNALS-ERROR))
 @dots{}

(test-end :exit-on-failure #t)
@end lisp

@c EN
With this convention, you can run test both interactively or
in batch.   To run a test interactively, just load the file
and it reports a result of each test, as well as the summary
of failed test at the end.  To run a test in batch, it is
convenient to redirect the stdout to some file
If stdout is redirected to other than tty, all the verbose logs will go
there, and only a small amount of messages go to stderr.
@c JP
このテストスクリプトは、バッチ処理でもインタラクティブセッションからでも
実行できます。インタラクティブセッションの場合はこのテストスクリプトを
ただロードすれば、各テストの結果とサマリーが報告されます。
バッチテストの場合は、標準出力を別のファイルにリダイレクトしておくと良いでしょう。
標準出力が端末でない場合、テスト手続きは詳しい結果をstdoutに出力し、簡単な
メッセージを標準エラー出力に書き出します。
@c COMMON

@c EN
It is recommended to have a "check" target always in Makefile
of your module/program, so that the user of your program can run a
test easily.  The rule may look like this:
@c JP
モジュールやプログラムを書いたら、Makefileに"check"ターゲットを作ることを
お薦めします。ルールはこんな感じになるでしょう：
@c COMMON

@example
check :
        gosh my-feature-test.scm > test.log
@end example

@c EN
For the portable programs, there are a couple of srfis that provide testing
frameworks (@pxref{Lightweight testing},
and @pxref{A Scheme API for test suites}).
In Gauche, when you can use these srfis with @code{gauche.test},
srfi's tests work as a part of Gauche's tests.
@c JP
ポータブルなコードでは、テストフレームワークを定めたsrfiがあります
(@ref{Lightweight testing}、および@ref{A Scheme API for test suites}参照)。
Gaucheでは、これらのsrfiを@code{gauche.test}と一緒に使うと、
srfiのテストがGaucheのテストとして走るようになっています。
@c COMMON
@end deftp


@menu
* Structuring a test file::
* Individual test::
* Incorporating external tests::
* Better test failure reporting::
* Quasi-static checks::
@end menu

@node Structuring a test file, Individual test, Unit testing, Unit testing
@subsection Structuring a test file
@c NODE テストファイルの構造

@defun test-start module-name
@c MOD gauche.test
@c EN
Initializes internal state and prints a log header.
This should be called before any tests.
@var{Module-name} is used only for logging purpose.
@c JP
テストの状態を初期化して、ヘッダをログに書き出します。テストを呼ぶ前に呼んで下さい。
@var{module-name}はログのために使われる文字列です。
@c COMMON

@c EN
If a test is already running, this procedure just emits a log message
and update internal test nesting level.  It allows a test script
to include another test script with @code{test-start}/@code{test-end}
pair.

With this feature, you can split a lengthy test script into several
sub test scripts, each of which is a stand-alone test script, and include
them into the main test script.   By doing so, you can run a single
sub test script while developing, and run the main test script for
full tests.
@c JP
テストが既に走っている場合は、
この手続きはログメッセージを出して内部のテストネストレベルを更新するだけです。
これにより、@code{test-start}/@code{test-end}のペアを持つスクリプトを
別のテストスクリプトからincludeすることができます。

この機能は、例えば長大なテストスクリプトをいくつかのサブテストスクリプトに
分割するのに役立ちます。各サブテストスクリプトはそれぞれ独立に走れるように
しておいて、元のテストスクリプトはそれらをincludeします。
これによって、開発中は必要なサブテストスクリプトだけを走らせ、フルテストでは
全てのテストを走らせる、といった運用ができます。
@c COMMON
@end defun

@defun test-end :key exit-on-failure
@c MOD gauche.test
@c EN
Prints out list of failed tests.  If @var{exit-on-failure} is @code{#f} or
omitted, this procedure returns the number of failed tests.

Otherwise, this function terminates the @code{gosh}
process by @code{exit}.  If a fixnum is given to @code{exit-on-failure}
it becomes the process's exit status; if other true value is given,
the exit status will be 1.
@c JP
失敗したテストのリストを報告します。@var{exit-on-failure}が@code{#f}か
省略された場合は、この手続きは失敗したテストの数を返します。

そうでなければ、この手続きは@code{exit}を呼んで@code{gosh}を
終了させます。@code{exit-on-failure}にfixnumが渡された場合は、
それがプロセスの終了ステータスとして使われます。@code{exit-on-failure}が
他の真となる値であった場合は、終了ステータスは1となります。
@c COMMON

@c EN
If test is nested, that is, this @code{test-end} corresponds
to inner @code{test-start} while outer test is ongoing, this procedure
only emits a log message and adjust internal test nesting level.
@c JP
テストがネストしている場合、つまりこの@code{test-end}と対応する@code{test-start}
が、既にテストが走っている状況で実行されていた場合は、この手続きは単にログメッセージを
出力して内部のテストネストレベルを調整します。
@c COMMON
@end defun

@defun test-running?
@c MOD gauche.test
@c EN
Returns @code{#t} if test is running, that is, you're between outermost
@code{test-start} and @code{test-end}.  Returns @code{#f} otherwise.
@c JP
テストが実行中、つまり、一番外側の@code{test-start}と@code{test-end}の間に
いるならば@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun


@defun test-section section-name
@c MOD gauche.test
@c EN
Marks beginning of the group of tests.  This is just for logging.
@c JP
一群のテストの開始をマークします。単にログに使われるだけです。
@c COMMON
@end defun

@defun test-log fmtstr args @dots{}
@c MOD gauche.test
@c EN
This is also just for logging.  Creates a formatted string
with @var{fmrstr} and @var{args} just like @code{format},
then write it to the current output port, with prefix @code{;; }
and newline at the end.

With the typical Makefile settings, where you redirect
stdout of test scripts to a log file, the message only goes to
the log file.

Using this, you can dump information that can't be automatically
tested but may be useful for troubleshooting.    For example,
you get a mysterious test failure reports you can't reproduce
on your machine, and suspect
some aspects of the running systems may unpredictably
affect the test result.
You can put @code{test-log} in the test code to dump such parameters,
and ask the reporter to run the test again and analyze the log.
@c JP
この手続きも単なるログのためのものです。
@code{format}と同じように@var{fmtstr}と@var{args}からフォーマット済み文字列を
作り、@code{;; }を前に、改行文字を後につけて現在の出力ポートへと出力します。

典型的なMakefileでのテスト起動では、テストスクリプトの標準出力をログに流すので、
このメッセージもログにのみ記録されることになります。

この手続きは、自動化テストで検査することは出来ないけれどトラブルシューティングに
役に立つかもしれない情報をダンプしておくのに使えます。
例えば、謎のテスト失敗報告が来て、でも手元ではどうしても再現できず、
実行システムに固有のある側面が影響しているのではないかと推測できたとしましょう。
その場合、@code{test-log}でそういった情報をダンプするコードをテストスクリプトに
仕込んでおいて、もう一度報告者のマシンでテストを走らせてもらい、そのログを解析する
ことができるでしょう。
@c COMMON
@end defun

@defun test-record-file file
@c MOD gauche.test
@c EN
Suppose you have several test scripts.  Normally you run them
as a group and what you want to know is a concise summary of
the whole results, instead of each result of individual test files.

A @emph{test record file} is an auxiliary file used to
gather summary of the result.   It holds a one-line summary
of tests like this:
@c JP
テストスクリプトがいくつかある場合を考えます。通常は、それらのテストスクリプト
をひとつづつ走らせて結果を確かめるのではなく、全部を一気に走らせて
簡単な結果のまとめだけを知りたいと思うでしょう。

@emph{test record file}はテスト結果を集積するための補助ファイルです。
その内容は次のような一行のサマリになっています。
@c COMMON

@example
Total:  9939 tests,  9939 passed,     0 failed,     0 aborted.
@end example

@c EN
When a test record file exists,
@code{test-start} reads and parses it, and remembers the numbers.
Then @code{test-end} adds the count of the results and
writes them back to the same test record file.
@c JP
test record fileが既に存在していると、@code{test-start}は
それを読みこんで数字を覚えておきます。そして@code{test-end}が
そのスクリプト中のテスト結果の数字を加算して、同じtest record fileに書き戻します。
@c COMMON

@c EN
If you write the @code{check} target in your makefile as follows,
you will get the final one-line summary every time you run
@code{make check}, assuming that @file{test1.scm}, @file{test2.scm},
and @file{test3.scm} all has @code{(test-record-file "test.record")}
before a call to @code{test-start}.
@c JP
makefileの@code{check}ターゲットを次のように書いておけば、
@code{make check}を実行するたびにテスト結果の一行サマリを
得ることができます。
ただし、@file{test1.scm}、@file{test2.scm}、@file{test3.scm}はいずれも
@code{test-start}呼び出し前に@code{(test-record-file "test.record")}を
評価しているものとします。
@c COMMON

@example
check:
        @@rm -f test.record test.log
        gosh test1.scm >> test.log
        gosh test2.scm >> test.log
        gosh test3.scm >> test.log
        @@cat test.record
@end example

@c EN
Note that to make @code{test-record-file} work, it must be placed
before the call to @code{test-start}.

Alternatively, you can use the environment variable
@code{GAUCHE_TEST_RECORD_FILE} to specify the test record file.
@c JP
@code{test-record-file}手続きがうまく動作するためには、それが
@code{test-start}より前に呼ばれなければならないことに注意してください。

この手続きのかわりに、環境変数@code{GAUCHE_TEST_RECORD_FILE}を使って
test record fileを指定することもできます。
@c COMMON
@end defun

@deftp {Environment Variable} GAUCHE_TEST_RECORD_FILE
@c EN
If this environment variable is set when the test script is run,
its value is used as the name of the test record file.

If the test script calls @code{test-record-file}, it takes precedence
and this environment variable is ignored.
@c JP
テストスクリプトが走る時にこの環境変数が指定されていれば、
その値がtest record fileの名前として使われます。

ただしテストスクリプト中に@code{test-record-file}の呼び出しがあると
そちらが優先され、この環境変数は無視されます。
@c COMMON
@end deftp

@defun test-summary-check
@c MOD gauche.test
@c EN
If the test record file is set (either by @code{test-record-file} or
the environment variable @code{GAUCHE_TEST_RECORD_FILE}), read it,
and then exit with status 1 if the record has nonzero failure
count and/or nonzero abort count.  If the test record file isn't
set, this procedure does nothing.
@c JP
テストレコードファイルが(@code{test-record-file}もしくは環境変数
@code{GAUCHE_TEST_RECORD_FILE}によって)設定されていた場合、
それを読み込んで、失敗カウントとアボートカウントがともに0でなければ
終了ステータス1でexitします。テストレコードファイルが設定されていなければ
何もしません。
@c COMMON

@c EN
This is useful when you have multiple test scripts and you want
to let @code{make} fail if any of tests fails, but not before all
test script is run.  If you make every test script use
@code{:exit-on-failure} of @code{test-end}, then @code{make}
stops immediately after the script that fails.  Instead, you
avoid using @code{:exit-on-failure}, but use the test record file
and for the last thing you can call this function:
@c JP
これは、複数のテストスクリプトを持っていて、どれかが失敗したら@code{make}に
それを伝えたいけれども、テストスクリプト自体はすべて走らせたい、という場合に便利です。
各テストスクリプトで@code{test-end}に@code{:exit-on-failure}を
使ってしまうと、@code{make}は失敗したテストスクリプトのところで処理を打ち切って
しまいます。そこで@code{:exit-on-failure}を使うのを避け、
テストレコードファイルを使い、ビルドの最後にこの関数を呼ぶようにします:
@c COMMON

@example
check:
   rm -f $GAUCHE_TEST_RECORD_FILE test.log
   gosh test1.scm >> test.log
   gosh test2.scm >> test.log
   cat $GAUCHE_TEST_RECORD_FILE /dev/null
   gosh -ugauche.test -Etest-summary-check -Eexit
@end example

@c EN
By this, @code{make} will run all the test script no matter how
many of them fails (since @code{gosh} exits with status 0), but
detect an error since the last line of @code{gosh} call exits
with status 1 if there has been any failure.
@c JP
こうしておくと@code{make}は失敗があろうともすべてのテストスクリプトを
実行し (@code{gosh}は常に終了ステータス0で終了するので)、
最後の行でテストレコードファイルを参照して、失敗があった場合に
@code{make}にそれを伝えることができます。
@c COMMON
@end defun

@node Individual test, Incorporating external tests, Structuring a test file, Unit testing
@subsection Individual test
@c NODE 個々のテスト

@c EN
Most test frameworks have various test procedures such as @code{test-assert},
@code{test-equal}, etc., depending on what you want to test.
We have only one, @code{test}, and its thin wrapper
@code{test*}.  It takes a thunk (or an expression) to run, the expected
result, and an optional check predicate to compare the expected result against
the actual result.  Various conditions, such as testing the actual
result is a true value,
or testing the expression raising a specific error, can be handled
by the check predicate.  The default check predicate handles typical cases:
@c JP
多くのテストフレームワークでは、何をテストするかによって@code{test-assert}や
@code{test-equal}などの様々なテスト手続きを提供しています。
Gaucheではテスト手続きは@code{test} (およびそのラッパーである@code{test*}) だけです。
@code{test}はテストする式(のサンク)、期待される結果、そして省略可能な検査述語を取り、
式の実際の結果と期待される結果を検査述語で比較します。
単純に値を比較する、エラーが投げられることを確認する、など様々なテストは
検査述語によって処理されます。デフォルトの検査述語でも、
以下のような色々なテストに対応できます。
@c COMMON

@itemize @bullet
@item
@c EN
Compare the expected result with the actual result.
@c JP
期待される結果と実際の結果を比較する。
@c COMMON
@example
(test* "one plus one equals two"
       2
       (+ 1 1))
@end example
@item
@c EN
Assert the expression returns true value (i.e. not @code{#f}).
@c JP
式が真となる値(@code{#f}でない値)を返すことを確認する。
@c COMMON
@example
(test* "'any' returns non-false value"
       (test-truthy)
       (any integer? '(1.2 3/4 5)))
@end example
@item
@c EN
Check if the actual result is one of possible values.
@c JP
実際の結果が可能ないくつかの結果のうちのひとつであることを確認する。
@c COMMON
@example
(test* "get random ineteger between 0 and 5"
       (test-one-of 0 1 2 3 4 5)
       (random-integer 6))
@end example

@item
@c EN
Check if the expression raises an expected error.
@c JP
式が期待するエラーを投げることを確認する。
@c COMMON
@example
(test* "expects read error"
       (test-error <read-error>)
       (read-from-string "(a .)"))
@end example
@end itemize

@c EN
With this way, it is easier to parameterize tests, e.g.
loop over a list of expected result and test thunks.
@c JP
このようにしておくと、例えば期待される結果とテストサンクのリストを用意して
ループするような、テストのパラメタライズが容易にできます。
@c COMMON


@defmac test* name expected expr :optional check report hook
@c MOD gauche.test
@c EN
A convenience macro that wraps @var{expr} by lambda.
@c JP
@var{expr}をlambdaでくるんでくれる便利なマクロです。
@c COMMON

@example
(test* name expected expr opt ...)
  @equiv{} (test name expected (lambda () expr) opt ...)
@end example
@end defmac

@defun test name expected thunk :optional check report hook
@c MOD gauche.test
@c EN
Calls @var{thunk}, and checks its result fits @var{expected}
using a procedure @var{check}, which
is called as follows:
@example
(@var{check} @var{expected} @var{result-of-thunk})
@end example
It should return @code{#t} if the given result agrees with the
expected value, or @code{#f} otherwise.
The default check procedure is @code{test-check}, explained
below.  It compares @var{expected} and @var{result-of-thunk}
with @code{equal?}, except when @var{expected} is some
of special case test objects.  (See ``testing ambiguous results''
and ``testing abnormal cases''
paragraphs below for this special treatment.)

One typical usage of the custom check
procedure is to compare inexact numbers tolerating small error.
@c JP
@var{thunk}を呼び、その結果が@var{expected}に沿っているかを
@var{check}を次のとおり呼び出すことで確認します。
@example
(@var{check} @var{expected} @var{result-of-thunk})
@end example
この手続きは、渡された結果が期待する値と合致する場合に@code{#t}を、
そうでなければ@code{#f}を返さなければなりません。
デフォルトの@var{check}手続きは下で述べる@code{test-check}です。
これは、@var{expected}がいくつかの特殊なテストオブジェクトである場合をのぞき、
@var{expected}と@var{result-of-thunk}が@code{equal?}
である場合に@code{#t}を返します。すなわち、通常はテスト式の結果が
期待するものと@code{equal?}であればテストは成功である、ということです。
(特別な場合については下の ``曖昧な結果をテストする'' および
``異常系をテストする'' の項を見てください)。

特別な比較手続きのひとつの用法は、非正確な数値を、多少の誤差を許して
比較するような場合です。
@c COMMON

@example
(test "test 1" (/ 3.141592653589 4)
      (lambda () (atan 1))
      (lambda (expected result)
        (< (abs (- expected result)) 1.0e-10)))
@end example

@c EN
@var{Name} is a name of the test, for the logging purpose.
@c JP
@var{name}はログに残すためのテストの名前です。
@c COMMON

@c EN
When @var{thunk} signals an uncaptured error, it is caught and
yields a special error object @code{<test-error>}.
You can check it with another error object created by
@code{test-error} function to see if it is an expected type
of error.  See the entry of @code{test-error} below for the details.
@c JP
@var{thunk}内で捕捉されないエラーが発生した場合、それは捕捉され、
特別なエラーオブジェクト@code{<test-error>}に置き換えられます。
その結果を、下で説明する@code{test-error}手続きで作った@code{<test-error>}
オブジェクトと比較することにより、エラーが期待されたものであるか、
また適切な例外が上がっているかをテストすることができます。
@c COMMON

@c EN
The @var{report} optional argument must be an @code{#f} or a
procedure that takes three arguments.  If it is a procedure, it is called
after @var{check} returns false (but before @var{hook} is called).
The first argument is @var{name},
the seond argument is @var{expected}, and the third argument
is either the result of @var{thunk}, or a @code{<test-error>} object
when @var{thunk} raises an error.
The default is @code{test-report-failure} procedure, which simply
uses @code{write} to display the result of @var{thunk}
or a @code{<test-error>} object.
By passing your own procedure, you can customize
the message to be printed when the test is failed.
@c JP
省略可能引数@var{report}は@code{#f}か、引数を3つ取る手続きです。
@var{check}が偽を返した場合に呼ばれます (ただし、@var{hook}が呼ばれる前です)。
最初の引数は@var{name}、次の引数は@var{expeced}、最後の引数は@var{thunk}が
返した値か、@var{thunk}がエラーを投げた場合は@code{<test-error>}オブジェクトです。
デフォルトは@code{test-report-failure}手続きで、これは単に@code{write}を使って
最後の引数(実際の結果、あるいは@code{<test-error>}オブジェクト)を出力するだけです。
別の手続きを与えることにより、テスト失敗時の出力をカスタマイズできます。
@c COMMON

@c EN
Finally, the @var{hook} optional argument must be an @code{#f} or a procedure
that takes four arguments.  If it is a procedure, it is called after
the @code{test} procedure finishes the test.  The first argument
is a symbol either @code{pass} or @code{fail}, the second argument
is @var{name}, the third argument is @var{expected}, and the fourth argument
is either the result of @var{thunk}, or a @code{<test-error>} object
when @var{thunk} raises an error.  The return value of @var{hook} is
ignored.

It is mainly for libraries that wrap @code{gauche.test} and wants to
do its own bookkeeping.
@c JP
最後に、省略可能引数@var{hook}は、@code{#f}か4引数の手続きでなければなりません。
それが手続きの場合、@code{test}がテストを終えた後で次の引数で呼び出されます:
第1引数はシンボル@code{pass}か@code{fail}、第2引数は@var{name}、
第3引数は@var{expected}、そして第4引数は、@var{thunk}の返り値か、
@var{thunk}がエラーを投げた場合は@code{<test-error>}オブジェクト。
@var{hook}の戻り値は無視されます。

これは、@code{gauche.test}をラップしたライブラリが独自にテスト結果を記録したい
場合に便利です。
@c COMMON

@c EN
Note: In 0.9.10, we didn't have @var{report} argument.  Instead of
adding @var{report} to the last optional argument, we made it the second
and shifted @var{hook}, for @var{hook} arugment will rarely be used.
To keep the backward compatibility, we recognize if
4-argument procedure is passed to a @var{report} argument we treat it
as @var{hook}, with warning.  This compatibility feature will be removed
in future releases.
@c JP
註: 0.9.10では@var{report}引数がありませんでした。@var{report}引数を追加するに
当たって、それを最後の省略可能引数ではなく、2番目の省略可能引数として
@var{hook}引数をずらすことにしました。
@var{hook}引数は滅多に使われないだろうという判断です。
互換性のため、@var{report}引数に4引数の手続きが渡された場合は
警告を出したうえでそれを@var{hook}として扱うコードが今は入っています。
将来のリリースではこの互換性コードは取り除かれます。
@c COMMON
@end defun

@defun test-check expected actual :optional equal
@c MOD gauche.test
@c EN
The default procedure @code{test} and @code{test*} use
to check the result of the test expression conforms the
expected value.  By default, @code{test-check} just compares
@var{expected} and @var{actual} with a procedure @var{equal},
which is defaulted to @code{equal?}.   @code{test-check} behaves
differently if @var{expected} is one of special test objects
described below.
@c JP
テスト式の結果が期待された値に合致していることをチェックするために
@code{test}と@code{test*}が使うデフォルトの手続きです。
基本的に、@code{test-check}は@var{expected}と@var{actual}を
@var{equal}に渡された手続きで比較するだけです。@var{equal}の
デフォルト値は@code{equal?}です。
ただし、以下に述べるとおり、@var{expected}が特殊なテストオブジェクト
だった場合には特別な振る舞いをします。
@c COMMON
@end defun

@defun test-report-failure name expected actual
@c MOD gauche.test
@c EN
The default procedure to report test failure.  It just
writes @var{actual} with @code{write}.
You can customize the failure report by passing your reporting procedure
to @var{report} argument to @code{test} and @var{test*}.
See @code{test-report-failure-diff} below, for example.
@c JP
テスト失敗をレポートする手続きのデフォルトです。これは単に
@var{actual-result}を@code{write}で書き出すだけです。
@code{test}や@code{test*}の@var{report}引数に独自の手続きを渡すことにより、
テスト失敗時の表示をカスタマイズできます。
例えば下の@code{test-report-failure-diff}を参照してください。
@c COMMON
@end defun

@c EN
@subsubheading Testing ambiguous results
@c JP
@subsubheading 曖昧な結果をテストする
@c COMMON

@defun test-one-of choice @dots{}
@c MOD gauche.test
@c EN
Sometimes the result of test expression depends on various
external environment, and you cannot put an exact expected value.
This procedure supports to write such tests conveniently.
@c JP
時々、テスト式@var{expr}の結果が外部の環境に左右されるため、
ひとつの確定した値を期待値@code{expected}として書いておけない場合があります。
この手続きはそのようなテストを簡単に書けるようにします。
@c COMMON

@c EN
Returns a special object representing @emph{either one of the choices}.
The default check procedure, @code{test-check}, recognizes the object
when it is passed in the @var{expected} argument, and returns true
if any one of @var{choice} @dots{} passes the check against the result.

For example, the following test passes if @code{proc} returns either
1 or 2.
@c JP
@emph{@var{choice} @dots{} のいずれか} を表現する特別なオブジェクトを返します。
デフォルトの検査手続きである@code{test-check}は、@var{expected}引数に
そのオブジェクトが渡ってきた場合には、テスト結果と@var{choice} @dots{}を
ひとつづつ照合し、どれかがマッチすれば真を返します。

例えば次のテストは、@code{proc}が1か2を返せば成功となります。
@c COMMON

@example
(test* "proc returns either 1 or 2" (test-one-of 1 2) (proc))
@end example

@c EN
Note that @code{test-check} compares the actual result against each of
@var{choice}s by @code{test-check} itself, that is:
@c JP
@code{test-check}は各@var{choice}に対して@code{test-check}を再帰的に
呼びます。すなわち:
@c COMMON

@example
(test-check (test-one-of choice @dots{}) result equal)
 @equiv{} (or (test-check choice result equal) @dots{})
@end example

@c EN
This, if you want to compare each choice
with customized equivalence procedure, pass @code{test-check}
with a specialized equivalence procedure as the check procedure.
The following example compares each @var{choice} and the result
case-insensitively:
@c JP
従って、各選択肢を比較する手続きをカスタマイズしたい場合は、
それを与えた@code{test-check}手続きをチェック手続きとして渡してください。
例えば次の例は、各選択肢と結果を@code{string-ci=?}で比較します:
@c COMMON

@example
(test* "Using one-of with case insensitive comparison"
       (test-one-of "abc" "def")
       "Abc"
       (cut test-check <> <> string-ci=?))
@end example
@end defun


@defun test-none-of choice @dots{}
@c MOD gauche.test
@c EN
Similar to @code{test-one-of}, but creates a special object
representing @emph{none of the choices}.
The test suceeds if the test expression evaluates to a value that
don't match any of @var{choice}s.
@c JP
@emph{@var{choice} @dots{} のいずれでもない} を表現する特別なオブジェクトを返します。
テストは、テスト結果が@var{choice}のどれにもマッチしなかった時に成功となります。
@c COMMON
@end defun

@c EN
Note: If you want to compare inexact numeric result,
you can use @code{approx=?} (@pxref{Numerical comparison}).
@c JP
註: 非正確な数値の結果を比較したい場合は、
@code{approx=?}が使えます (@ref{Numerical comparison}参照)。
@c COMMON


@defun test-truthy
@c MOD gauche.test
@c EN
Returns a special object that expects a true value, i.e. anything
but @code{#f}.　Use it to assert the test expression returns a true value
but not necessarily @code{#t}.
@c JP
真の値、つまり@code{#f}以外のあらゆる値を期待するオブジェクトを返します。
テストする式が真の値を返す(が、@code{#t}とは限らない)場合に便利です。
@c COMMON
@end defun


@c EN
@subsubheading Testing abnormal cases
@c JP
@subsubheading 異常系をテストする
@c COMMON

@defun test-error :optional (condition-type <error>) (message #f)
@c MOD gauche.test
@c EN
Returns a new @code{<test-error>} object that matches with
other @code{<test-error>} object with the given @var{condition-type}.
@c JP
与えられた@var{condition-type}と適合する@code{<test-error>}オブジェクト
とマッチするような、新たな@code{<test-error>}オブジェクトを作成して返します。
@c COMMON

@c EN
The @code{test-check} procedure treats @code{<test-error>} objects
specially.  When @code{err-expected} and @code{err-actual}
are @code{<test-error>} objects,
@code{(test-check err-expected err-actual)} returns @code{#t}
if @code{err-expected}'s
condition type is the same as or supertype of @code{err-actual}'s.
@c JP
テスト結果をチェックする@code{test-check}手続きは@code{<test-error>}オブジェクトを
特別に扱います。@code{err-expected}と@code{err-actual}が
ともに@code{<test-error>}のインスタンスであるとき、
@code{(test-check err-expected err-actual)}は
@code{err-expected}の持つcondition typeが@code{err-actual}の
それと同じであるか、スーパータイプである場合に@code{#t}を返します。
@c COMMON

@c EN
For example, if you want to test a call to @code{foo} raises
an @code{<io-error>} (or its condition subtype), you can write
as the following example:
@c JP
例えば@code{foo}の呼び出しが@code{<io-error>} (もしくはそのサブタイプ) の
コンディションを投げるかどうかをテストしたければ、次のように書くことができます。
@c COMMON

@example
(test "see if foo raises <io-error>" (test-error <io-error>) (foo))
@end example

@c EN
Another optional argument @var{message} can be used to check if
the raised error has a message of expected pattern.  The argument
may be a string, a regexp, or @code{#f} (default).
If it is a string, @code{test-check}
checks if the message of the raised error exactly match the
string.  If it is a regexp, @code{test-check} checks
the message of the raised error matches that regexp.
If it is @code{#f}, the message is not checked.
@c JP
もう一つの省略可能引数@var{message}は、テスト中に投げられたエラーの
メッセージが期待するパターンを満たしているかどうかをチェックするのに使います。
この引数は文字列、正規表現、@code{#f}のいずれかでなければなりません。
この引数が文字列の場合、@code{test-check}は投げられたエラーのメッセージが
その文字列と完全に一致するかどうかをチェックします。
この引数が正規表現の場合、@code{test-check}は投げられたエラーのメッセージが
その正規表現にマッチするかをチェックします。
デフォルトは@code{#f}で、その場合はメッセージのチェックは行われません。
@c COMMON
@end defun

@defvar *test-error*
@c MOD gauche.test
@c DEPRECATED
@c EN
Bounded to an instance of @code{<test-error>} with
condition type @code{<error>}.  This is only provided for the
backward compatibility; new code should use @code{test-error}
procedure above.
@c JP
condition typeとして@code{<error>}を持つ@code{<test-error>}
オブジェクトに束縛されています。この変数は互換性のためにのみ残されています。
新しいコードは上に述べた@code{test-error}手続きを使ってください。
@c COMMON
@end defvar

@defvar *test-report-error*
@c MOD gauche.test
@c EN
If this variable is true, the @code{test} routine prints stack trace
to the current error port when it captures an error.  It is useful
when you got an unexpected test-error object and want to check out
where the error is occurring.

This variable is initialized by the environment variable
@code{GAUCHE_TEST_REPORT_ERROR} when the @code{gauche.test} module
is loaded.  For example, you can use the environment variable to check out
an unexpected error from your test script as follows (the value
of the environment variable doesn't matter).
@c JP
この変数が真であれば、@code{test}ルーチンはエラーを捕捉した際に
スタックトレースをカレントエラーポートに出力します。
期待しない状況でtest-errorオブジェクトが返された際に、そのエラーが
どこで起こったかを知るのに役立つでしょう。

この変数は@code{gauche.test}モジュールが読み込まれた時点で
環境変数@code{GAUCHE_TEST_REPORT_ERROR}の値により初期化されます。
例えば、テストスクリプト中の予期せぬエラーを調べるのに、
次のようにすることができるでしょう (環境変数がセットされていれば、値は関係ありません)。
@c COMMON

@example
env GAUCHE_TEST_REPORT_ERROR=1 gosh mytest.scm
@end example
@end defvar

@node Incorporating external tests, Better test failure reporting, Individual test, Unit testing
@subsection Incorporating external tests
@c NODE 外部のテストの取り込み

@c EN
Sometimes you implment an existing specification that comes with tests.
If tests are written in R7RS Scheme, you can run it by itself;
however, you might want to run it as a part of larger test suite
managed by @code{gauche.test}.  By doing so, you can get consolidated
test result reports, for Gauche integrates SRFI test frameworks
such as @code{srfi.64} and @code{srfi.78}.
@c JP
しばしば、既存の仕様を実装していて、テストコードがその仕様に付属していることがあります。
テストがR7RSで書かれていればそれ自体をGaucheで実行することはできますが、
@code{gauche.test}で管理されるより大きなテストスイートの一部として
与えられたテストを実行したい場合もあるでしょう。
Gaucheではテスト用SRFIである@code{srfi.64}や@code{srfi.78}が@code{gauche.test}
と連携するようになっているので、テスト結果がまとめて報告されます。
@c COMMON

@c EN
If the test file is written in R7RS format, however, you may
not be able to simply @code{include} the test file into Gauche's
test suite.  As R7RS @code{import} differs from Gauche's, we have
some black magic to switch R7RS/Gauche namespace based on
whether the first form in the file is R7RS @code{import} form
or not (@pxref{Three forms of import}).  If you include R7RS program into
Gauche's program, the @code{import} in the R7RS code is interpreted
as Gauche's and doesn't work.  The macro @code{test-include-r7} can
be used instead.
@c JP
ただ、テストがR7RS形式で書かれている場合、それをGaucheのテストスイートに
単純に@code{include}するだけではうまくいかないことがあります。
Gaucheにもともとあった@code{import}とR7RSの@code{import}は異なっているので、
Gaucheは実行時に、
プログラム中で最初に出会う@code{import}でどちらかを切り替える黒魔術を使っています
(@ref{Three forms of import}参照)。
Gaucheプログラム中にR7RSプログラムをインクルードした場合、R7RSプログラム中の
@code{import}がGaucheの@code{import}と解釈されてしまうのでうまくありません。
かわりに、下のマクロ@code{test-include-r7}が使えます。
@c COMMON

@c EN
NB: If the external test is written for Chibi Scheme,
you can use @code{chibi-test} instead (@pxref{Running Chibi-scheme test suite}).
@c JP
註: 外部テストがChibi Scheme向けに書かれている場合、
@code{chibi-test}が使えます(@ref{Running Chibi-scheme test suite}参照)。
@c COMMON

@defmac test-include-r7 path [exclude-clause]
@c MOD gauche.test
@c EN
Like @code{include} form (@pxref{Inclusions}), expands the content of
the file specified by @var{path} in place of this form.
If @var{path} is relative, it is relative from the includer.
@c JP
@code{include}フォーム (@ref{Inclusions}参照) と同じように、
@var{path}で指定されるファイルの内容をこのマクロの位置に挿入します。
@var{path}が相対パスの場合は、インクルードしているファイルからの相対になります。
@c COMMON

@c EN
The code is included in the environment where @code{import} is bound
to R7RS's, so that a test script written for R7RS can be included as is.
@c JP
ファイル中のコードは、@code{import}がR7RSの@code{import}に束縛された
環境で挿入されます。したがってR7RSで書かれたテストスクリプトがそのまま実行できます。
@c COMMON

@c EN
A recommended usage is to create a submodule in Gauche's test script:
@c JP
推奨される使い方は、Gaucheのテストスクリプト中に別のモジュールを作ってその中で
インクルードする方法です。
@c COMMON

@example
(use gauche.test)
(test-start ...)
     :
(test-section "xxx-tests")
(define-module xxx-tests
  (use gauche.test)
  (test-include-r7 "xxx-tests"))
@end example

@c EN
Sometimes the external script refers to a library that's not
corresponds to what Gauche provides (e.g.
@file{tests/include/srfi-222-tests.scm}
imports @code{(compounds)} library, but Gauche provides it as @code{srfi.222}.)
You can list such libraries to @code{exclude clause} so that import won't
load it:
@c JP
しばしば、与えられたテストスクリプトが、Gaucheにない名前でライブラリを参照
していることがあります (例えば@file{tests/include/srfi-222-tests.scm}
は@code{(compounds)}というライブラリをインポートしていますが、
Gaucheではそのライブラリは@code{srfi.222}という名前で提供されています)
その場合、Gaucheに無いモジュールを@var{exclude-clause}に列挙することで、
@code{import}がそのモジュールを無視するようにできます:
@c COMMON

@example
(define-module srfi-222-tests
  (use gauche.test)
  (use srfi.222)
  (test-include-r7 "include/srfi-222-tests" (exclude (compounds))))
@end example

@c EN
The format of @var{exclude-clause} is as follows:
@c JP
@var{exclude-clause}は次の形式を取ります:
@c COMMON

@example
<exclude-clause> : (exclude @var{r7rs-library-name} @dots{})
@end example
@end defmac

@node Better test failure reporting, Quasi-static checks, Incorporating external tests, Unit testing
@subsection Better test failure reporting
@c NODE 見やすいテスト失敗の報告
@c COMMON

@c EN
As described in @code{test} entry above, you can customize
how the failure is reported by passing the optional @var{report} argument
to @code{test} and @code{test*}.  One of useful customizations is
to show the difference between multi-line text.  It's such a useful tool
so we provide a report procedure.
@c JP
上記@code{test}の項で説明したように、@code{test}手続きや@code{test*}マクロの
@var{report}引数に手続きを渡すことで、失敗の報告をカスタマイズできます。
便利なカスタマイズのひとつは、複数行に渡るテキストの差分を示すことです。
これはとても便利なので、それ用の手続きを用意しました。
@c COMMON

@c EN
Here's a contrived example.  We pass @code{test-report-failure-diff}
as a report procedure (and @code{test-check-diff} for check procedure,
which we'll explain later).  Expected text is given as a list of lines,
while the actual result is a single string;
Both @code{test-report-failure-diff} and @code{test-check-diff}
procedures canonicalize expected
and actual result into a single multi-line string, so you can give
them in whichever ways that's convenient for you.
@c JP
これはちょっとわざとらしいテストです。
@code{test-report-failure-diff}を@var{report}引数に渡しています
(それと、@var{check}引数に@code{test-check-diff}を渡しています。後で説明します。)
期待される結果は行のリストで、実際の結果は単一の文字列になっています。
@code{test-report-failure-diff}と@code{test-check-diff}手続きは、
@var{expected}と@var{actual}に渡されるものを単一の文字列へと正規化するので、
渡しやすいような形式で引数を渡すことができます。
@c COMMON

@example
(test* "Beatrice"
       ;; expected
        '("What fire is in mine ears?  Can this be true?"
          "Stand I condemned for pride and scorn so much?"
          "Contempt, farewell, and maiden pride, adieu!"
          "No glory lives behind the back of such.")
       ;; actual
       "What fire is in mine ears?  Can this be true?\n\
        Stand I condemn'd for pride and scorn so much?\n\
        Contempt, farewell! and maiden pride, adieu!\n\
        No glory lives behind the back of such.\n"
       test-check-diff           ; check
       test-report-failure-diff) ; report

 @result{} @r{Reports:}
ERROR: GOT diffs:
--- expected
+++ actual
@@@@ -1,4 +1,4 @@@@
 What fire is in mine ears?  Can this be true?
-Stand I condemned for pride and scorn so much?
-Contempt, farewell, and maiden pride, adieu!
+Stand I condemn'd for pride and scorn so much?
+Contempt, farewell! and maiden pride, adieu!
 No glory lives behind the back of such.
@end example

@c EN
As you see, the result is reported in a unified diff format
(@pxref{Calculate difference of text streams}) so that you can
spot the difference easily.
@c JP
このとおり、結果がunified diffフォーマットで報告されるので、どこが違っているのか
見つけやすくなります
(unified diffフォーマットについては@ref{Calculate difference of text streams}参照)。
@c COMMON

@defun test-check-diff expected actual :optional equal
@c MOD gauche.test
@c EN
An alternative check procedure you can pass into @var{check} argument
of @code{test} procedure / @code{test*} macro.
@c JP
@code{test}手続き/@code{test*}マクロの@var{check}引数に渡せる
チェック手続きです。
@c COMMON

@c EN
Before comparing @var{expected} and @var{actual}, it performs the
following operations on each of @var{expected} and @var{actual}:
@c JP
まず、@var{expected}と@var{actual}を次の規則によって正規化します。
@c COMMON
@itemize @bullet
@item
@c EN
If it is a list of strings, join them with @code{\n} (with @code{suffix}
syntax, so the last line is also appended with @code{\n}).
@c JP
文字列のリストであれば、@code{\n}を糊としてひとつの文字列へとjoinします
(@code{suffix}シンタックスを使います。つまり、最後の行の末尾にも@code{\n}は付きます)。
@c COMMON
@item
@c EN
If it is a form @code{(content-of <string>)}, then @code{<string>}
is taken as a filename and the content of the file is used as
a string.  If the filename is relative, it is relative to the
current loading file.  If named file doesn't exist, an empty string
is used.
@c JP
@code{(content-of <string>)}という形であれば、
@code{<string>}をファイル名と解釈し、そのファイルを読み込んだ文字列を使います。
ファイル名が相対パスの場合、現在ロードしているファイルからの相対と解釈されます。
ファイルが無ければ空文字列になります。
@c COMMON
@item
@c EN
If it is a string or other object, it is used as is.
@c JP
文字列や他のオブジェクトの場合は、それがそのまま使われます。
@c COMMON
@end itemize

@c EN
Then the two arguments are compared using @var{equal}, which is defaulted
to @code{equal?}.
@c JP
正規化後、二つの引数が@var{equal}手続きによって比較されます。デフォルトは@code{equal?}です。
@c COMMON
@end defun

@defun test-report-failure-diff msg expected actual
@c MOD gauche.test
@c EN
An alternative failure report procedure you can pass into @var{report}
argument of @code{test} procedure / @code{test*} macro.
@c JP
@code{test}手続き/@code{test*}マクロの@var{report}引数に渡せる
チェック手続きです。
@c COMMON

@c EN
The @var{expected} and @var{actual} arguments are converted in the same
way as @code{test-check-diff}; that is, if it is a list of strings (lines)
or a form @code{(content-of <filename>)}, it is converted to
a single string.
@c JP
まず@var{expected}と@var{actual}引数が@code{test-check-diff}と同様に
正規化されます。つまり、文字列のリストか@code{(content-of <filename>)}ならば
単一の文字列に変換されます。
@c COMMON

@c EN
Then the difference of the two is reported in a unified diff format
(using @code{diff-report/unified}. @xref{Calculate difference of text streams}).
@c JP
それから、両者の差異をunified diff形式で表示します
(@code{diff-report/unified}が使われます。
@ref{Calculate difference of text streams}参照)。
@c COMMON

@c EN
If either @var{expected} or @var{actual} is not convertable to a single
string, the result is reported in the same way as the standard
@code{test-report-failure}.
@c JP
@var{expected}と@var{actual}の少なくとも一方が文字列に変換されなかった場合は、
標準の@code{test-report-failure}と同じ表示になります。
@c COMMON

@c EN
Note: This procedure is called twice, once when the test is failed,
and again from @code{test-end} to report the summary of discrepancy.
If you pass @code{(content-of <filename>)} form, you have to make sure
the named file exists until @code{test-end} returns.  This is tricky
if you generate text into a temporary file during a single test.
In general, @code{(content-of <filename>)} form is useful in the
@var{expected} argument, where you can specify the prepared file.
@c JP
註: この手続きは、テストが失敗した時だけでなく、@code{test-end}がテスト結果の
まとめを表示する時にも呼ばれます。
従って、@code{(content-of <filename>)}の形式を使う場合は、
@code{test-end}が戻るまで@code{<filename>}が存在するようにしてください。
例えばテスト内で一時ファイルを作って結果をそこに出し、そのテスト後にクリアする、
という場合はこの形式は使い辛いでしょう。
一般的に、@code{(content-of <filename>)}形式は、@var{expected}に
あらかじめ用意してあるファイルを指定するのに使うのが良いでしょう。
@c COMMON
@end defun

@defmac test*/diff name expected expr
@c MOD gauche.test
@c EN
This is a convenience version of @code{test*}, using
@code{test-check-diff} and @code{test-report-failure-diff} as
check and report procedures, respectively.
@c JP
@code{test*}マクロで@code{test-check-diff}と@code{test-report-failure-diff}を
@var{check}と@var{report}引数に指定したもので、簡便のために用意されています。
@c COMMON

@example
(test*/diff name expected expr)
 @equiv{}
 (test* name expected expr test-check-diff test-report-failure-diff)
@end example
@end defmac

@node Quasi-static checks,  , Better test failure reporting, Unit testing
@subsection Quasi-static checks
@c NODE 準静的検査

@c EN
Scheme is dynamically typed, which is convenient for incremental
and experimental development on REPL, but it tends to delay error detection
until the code is actually run.  It is very annoying that you run your
program for a while only to see it barfs on simple typo of variable name.
@c JP
Schemeは動的型付けで、これはREPLでインクリメンタルあるいは実験的な開発を
するには便利なのですが、コードが実際に走るまでエラーに気づかないということになりがちです。
しばらく走らせた後で変数名のタイポで止まってしまうと腹立ちますよね。
@c COMMON

@c EN
Gauche addresses this issue by checking certain types of errors
at the test phase.  It isn't purely a static check (we need to load
a module or a script, which evaluates toplevel expressions), nor
exhaustive (we can't catch inconsistencies that span over multiple
modules or about information that can be added at runtime).  Nevertheless
it can often catch some common mistakes, such as incorrect variable names
or calling procedures with wrong number of arguments.
@c JP
Gaucheでは、こういった種類のエラーをテスト時に検査する方法を用意しています。
これは完全に静的な検査ではありません(対象のモジュールやスクリプトをロードするので、
トップレベル式は実行されてしまいます)し、網羅的でもありません
(複数のモジュールを見たり、実行時に追加される情報に依存するものは検査できません)。
それでも、変数名の間違いや引数の個数の誤りなどよくあるミスはこの検査で大抵見つけることが
できます。
@c COMMON

@c EN
The two procedures, @code{test-module} and @code{test-script},
load the named module and the script files respectively (which compiles
the Scheme code to VM instructions), then scan the compiled VM code
to perform the following tests:
@c JP
@code{test-module}と@code{test-script}手続きはそれぞれ、
指定されたモジュールもしくはスクリプトをロードし (その過程でSchemeコードは
VM命令列へとコンパイルされます)、次にコンパイルされたVMコードを走査して
以下のテストを行います。
@c COMMON

@enumerate
@item
@c EN
See if the global variables referenced within functions are all defined
(either in the module, or in one of imported modules).
@c JP
関数内から参照されているグローバル変数は(該当モジュール内、もしくはインポートしたモジュールで)
全て定義されているか
@c COMMON

@item
@c EN
If a global variable is used as a function, see if the number of arguments
given to it is consistent to the actual function.
@c JP
グローバル変数が関数として使われているなら、その引数の数が
関数の定義と合致しているか。
@c COMMON

@item
@c EN
See if the symbols set as autoload in the code can be resolved.
@c JP
autoloadに設定されている変数が実際にロードできるか。
@c COMMON

@item
@c EN
While testing module, see if the symbols declared in the export list
are actually defined.
@c JP
モジュールをテストしている場合、exportされているシンボルが
定義されているか。
@c COMMON
@end enumerate

@c EN
The check is somewhat heuristic and we may miss some errors and/or
can have false positives.  For false positives, you can enumerate
symbols to be excluded from the test.
@c JP
今のところ検査はヒューリスティックで、エラーを見逃すこともあれば、
エラーでないものをエラーと報告してしまう可能性もあります。後者については、
偽陽性となるシンボルを列挙して検査から外すようにできます。
@c COMMON

@defun test-module module :key allow-undefined bypass-arity-check
@c MOD gauche.test
@c EN
Loads the module and runs the quasi-static consistency check.
@var{Module} must be a symbol module name or a module.
@c JP
モジュールをロードし、準静的な一貫性チェックを行います。
@var{Module}はモジュール名のシンボルかモジュールでなければなりません。
@c COMMON

@c EN
Sometimes you have a global variable that may not be
defined depending on compiler options or platforms, and
you check its existence at runtime before using it.
The undefined variable reference check by @code{test-module}
doesn't follow such logic, and reports an error whenever
it finds your code referring to undefined variable.  In such case,
you can give a list of symbols to the @var{allow-undefined}
keyword argument; the test will excludes them from the check.
(Note: @var{allow-undefined} does not allow variables exported
but not defined in the module.)
@c JP
しばしば、プラットフォームやコンパイルオプションによって
グローバル変数が定義されるかどうかが異なる場合があります。
コード中では実行時にその変数の存在を確認してから使うように
コーディングしてあったとしても、@code{test-module}は
そのようなロジックを追わないため、未定義変数の参照を報告して
しまいます。そのような場合は、チェックから外す変数名のリストを
@var{allow-undefined}キーワード引数に渡して下さい。
(註: @var{allow-undefined}はエクスポートされているけれど
未定義の変数を許すことはしません。)
@c COMMON

@c EN
The arity check may also raise false positives, if the module
count on a behavior of global procedures that will be modified
after the module is loaded (e.g. a method with different number
of arguments can be added to a generic function after the module
is loaded, which would make the code valid.)  If you know
you're doing right thing and need to suppress the false positives,
pass a list of names of the functions to @code{bypass-arity-check}
keyword arguments.
@c JP
引数の個数のチェックも、偽陽性のエラーをあげる可能性があります。
モジュールがロードされた後のグローバルな関数の変更を当てにしている場合などです
(例えば、コード中であるジェネリックファンクションに渡されている引数の個数が、
モジュールのロード時点では不正なものだったとしても、そのコードが実行される
までに該当引数のメソッドが追加されれば、正しいコードとなるわけです)。
自分のコードは確かに正しく、チェックが誤りであるような場合は、
該当関数の名前のリストを@code{bypass-arity-check}キーワード引数に
渡してください。
@c COMMON
@end defun

@defun test-script filename :key allow-undefined bypass-arity-check compile-only
@c MOD gauche.test
@c EN
Loads the script named by @var{filename}
into a fresh anonymous module and runs the quasi-static
consistency check.
@var{Filename} must be a string that names the script file.
@c JP
@var{filename}で指定されるスクリプトを新しい無名モジュールにロードし、
準静的な一貫性チェックを行います。
@var{filename}はスクリプトファイル名を指定する文字列でなければなりません。
@c COMMON

@c EN
The meaning of keyword arguments is the same as @code{test-module}.
@c JP
キーワード引数の意味は@code{test-module}と同じです。
@c COMMON

@c EN
Note that the toplevel forms in @var{filename} are evaluated, so scripts that
relies on the actions of toplevel forms could cause unwanted side-effects.
This check works best for the scripts written in SRFI-22 convention,
that is, calling actions from @code{main} procedure instead of toplevel
forms.  R7RS scripts relies on actions in toplevel forms and can't be
tested with this procedure.
@c JP
@var{filename}中のトップレベルフォームは評価されるので、
トップレベルフォームのアクションに依存したスクリプトは望ましくない副作用を生じるでしょう。
この検査は、スクリプトがSRFI-22形式、
つまりアクションを@code{main}手続きから呼ぶようになっているとうまくいきます。
R7RSスクリプトはトップレベルフォームのアクションに頼らざるを得ないので
この手続きではうまく検査できません。
@c COMMON

@c EN
Scripts that relies on being loaded into @code{user} module also
won't work well with this check, which loads the forms into anonymous
module.
@c JP
スクリプトが@code{user}モジュールにロードされることに依存して書かれている場合も、
この手続きではうまくいきません。
@c COMMON

@c EN
If you need to test a script with toplevel side-effecting forms and
you can't change it, you may want to pass
true value to the @code{compile-only} keyword argument.  Then
@code{test-script} just compiles each toplevel form before running
static checking,
instead of @code{load}ing (which not only compiles but executes each
of toplevel forms).
@c JP
もしスクリプトに副作用があるトップレベルフォームが書かれていて、それを
変更することができないなら、@code{compile-only}キーワード引数に
真の値を渡してみてください。すると、@code{test-script}は
スクリプトのトップレベルフォームをコンパイルだけしてから静的検査を行います。
(デフォルトの@code{load}はコンパイルだけではなく実行も行います)。
@c COMMON
@end defun

@c ----------------------------------------------------------------------
@node Threads, Measure timings, Unit testing, Library modules - Gauche extensions
@section @code{gauche.threads} - Threads
@c NODE スレッド, @code{gauche.threads} - スレッド

@c EN
Gauche can use threads
built on top of either POSIX threads (pthreads) or Windows threads,
depending on the platform.
@c JP
Gaucheでは、POSIXスレッド(pthreads)か
Windowsスレッド上に構築されるスレッドを使うことができます
(どちらを使うかはプラットフォームによります)。
@c COMMON

@deftp {Module} gauche.threads
@mdindex gauche.threads
@c EN
Provides thread API.  The thread support is built-in, and this
module merely provides a separate namespace.
@c JP
スレッドを扱うAPIを提供します。スレッドサポートは組み込みで、
このモジュールは名前空間を提供しているだけです。
@c COMMON
@end deftp

@c EN
Although you hardly need to distinguish
the underlying thread subsystem (either pthreads or Windows threads)
in Scheme level, you may want to detect the difference if your code
depends on a particular subsystem-specific semantics.
There are feature identifiers @code{gauche.sys.pthreads}
or @code{gauche.sys.wthreads}, for pthreads platform and Windows thread
platform, respectively.  You can use @code{cond-expand}
to switch the platform-dependent code
(@pxref{Feature conditional}).
@c JP
Schemeレベルでは、スレッドサブシステムの違い(pthreadsかWindowsスレッドか)を
意識する必要はほどんど無いでしょう。ただ、特定のサブシステムのセマンティクスに
依存したコードを書きたい場合は、
pthreadプラットフォームとWindowsスレッドプラットフォームで
それぞれ、@code{gauche.sys.pthreads}と@code{gauche.sys.wthreads}
という機能識別子が用意されています。
@code{cond-expand}でプラットフォーム依存のコードを切り替えられます
(@ref{Feature conditional}参照)。
@c COMMON

@c EN
To check if threads are available at runtime,
instead of compile time, use the following procedure.
@c JP
コンパイル時ではなく実行時にスレッドが有効かどうかをチェックするためには、
次の手続きを使います。
@c COMMON

@defun gauche-thread-type
@c MOD gauche.threads
@c EN
Returns a symbol that indicates the supported thread type.
It returns @code{pthread} for POSIX pthreads,
and @code{wthread} for Windows threads.
@c JP
サポートされているスレッドのタイプを表すシンボルを返します。
POSIX pthreadsなら@code{pthread}、
Windowsスレッドなら@code{wthread}が返されます。
@c COMMON

@c EN
(Note: On pthreads platforms, it should return @code{pthreads} instead
of @code{pthread}; then the returned symbol would correspond to the
value given to @code{--enable-threads} option at configuration time.
It's a historical overlook, stuck for the backward compatibility.)
@c JP
(註：pthreadプラットフォームではシンボル@code{pthread}ではなく
@code{pthreads}を返すべきでした。そうすれば、
@code{gauche-thread-type}の返り値はコンフィグレーション時に
@code{--enable-threads}に与えた値と対応するものになっていたでしょう。
互換性のために、残念ながらこの見過ごしは修正されないでしょう。
@c COMMON
@end defun

@c EN
Scheme-level thread API conforms SRFI-18, "Multithreading support",
wrapped around Gauche's object interface.
@c JP
SchemeレベルのスレッドAPIはSRFI-18、``マルチスレッドサポート''を満たし、
Gaucheのオブジェクトのインターフェースでラップされます。
@c COMMON

@menu
* Thread programming tips::
* Thread procedures::
* Thread local storage::
* Synchronization primitives::
* Thread exceptions::
@end menu

@node Thread programming tips, Thread procedures, Threads, Threads
@subsection Thread programming tips
@c NODE スレッドプログラミングTips

@c EN
@subsubheading What's Gauche threads for
@c JP
@subsubheading Gaucheのスレッドをどう使うか
@c COMMON

@c EN
Although the surface API of threads looks simple and portable,
you need to know how the threads are implemented in order to utilize
the feature's potential.   Some languages support threads as
language's built-in construct and encourage programmers
to express the calculation in terms of threads.
However, it should be noted that in many cases there are
alternative ways than threads to implement the desired
algorithm, and you need to compare advantages and
disadvantages of using threads depending on how the threads
are realized in the underlying system.
@c JP
スレッドのAPIは外見上シンプルでポータブルに見えますが、
その機能の潜在的な力を活用するためには、スレッドがどのように
実装されているかを知る必要があります。
いくつかの言語では言語組み込みの機能としてスレッドをサポートし、
プログラマによるスレッドの利用を推奨しています。
しかし、多くの場合、実現したいアルゴリズムをスレッドを使わずに
実装する方法があります。
スレッドを使うことの利点と欠点を、そのスレッドがシステムによってどのように
実現されているかを考慮した上で比較する必要があります。
@c COMMON

@c EN
In Gauche, the primary purpose of threads is to write programs
that @emph{require} preemptive scheduling, therefore are
difficult to express in other ways.  Preemptive threads may
be required, for example, when you have to call a module that
does blocking I/O which you can't intercept, or may spend
nondeterministic amount of calculation time that you want
to interrupt.
@c JP
Gaucheでは、スレッドを使う一番の目的は、他の方法で表現することが
難しい、プリエンプティブなスケジューリングを@emph{必要}とする
プログラムを書くことです。プリエンプティブなスレッドは、
例えば、中断できないブロッキングI/Oを行うモジュールを
使わなければならないときや、実行時間の分からない計算に
割り込みを行いたいときなどに必要となります。
@c COMMON

@c EN
For each Gauche's thread, an individual VM is allocated
and it is run by the dedicated POSIX thread.  Thus the
cost of context switch is the same as the native
thread, but the creation of threads costs much higher than,
say, lightweight threads built on top of call/cc.
So Gauche's preemptive threads are @emph{not} designed for
applications that want to create thousands of threads
for fine-grained calculation.
@c JP
それぞれのGaucheのスレッドには、個別の仮想マシンが割り当てられ、
専用のPOSIXスレッドにより実行されます。したがって、コンテキスト
スイッチのオーバヘッドは、ネイティブスレッドと同等です。
しかし、スレッドの生成は、例えばcall/ccによる軽量スレッドよりは
ずっとコストのかかる処理です。
このように、Gaucheのプリエンプティブなスレッドは、
きめ細かい計算のために幾千ものスレッドを生成したいアプリケーション
向けでは@emph{ありません}。
@c COMMON

@c EN
The recommended usage is the technique so called "thread pool",
that you create a set of threads and keep them around for
long time and dispatch jobs to them as needed.  Gauche provides
a thread pool implementation in @code{control.thread-pool} module
(@pxref{Thread pools}).
@c JP
推奨される使用方法は、いわゆる``スレッドプール''と呼ばれる
テクニックです。つまり、スレッドの集合を作って長時間それを
保持し、必要になったときにジョブをそこへディスパッチする
というものです。Gaucheは@code{control.thread-pool}モジュール
(@ref{Thread pools}参照) でスレッドプールの実装を提供しています。
@c COMMON

@c EN
Preemptive threads have other difficulties,
and sometimes the alternatives may be a better fit
than the native preemptive threads
(e.g. see @uref{https://www-sop.inria.fr/mimosa/rp/FairThreads/html/FairThreads.html}).
@c JP
プリエンプティブなスレッドには他にも難しい点があり、
しばしばネイティブなプリエンプティブスレッドよりも
より良くフィットする代替策があります
(例えば@uref{https://www-sop.inria.fr/mimosa/rp/FairThreads/html/FairThreads.html}参照)。
@c COMMON

@itemize @bullet
@item
@c EN
If what you need is just a concurrent calculation, you
might be able to use cooperative thread technique built
on top of @code{call/cc}.   Creating call/cc-based threads
is much faster than creating native threads.
@c JP
単に並行実行が必要なだけなら、@code{call/cc}による協調スレッド
テクニックが使えるでしょう。call/ccベースのスレッドの生成は、
ネイティブスレッドを生成するよりも高速です。
@c COMMON

@item
@c EN
If what you need is to deal with blocking I/O, and you have
all your code at hand, it is sometimes easier to use good old
@code{select}-based dispatching (@xref{Simple dispatcher},
for example).
@c JP
ブロッキングI/Oを扱う必要があり、全てのコードが手元にある場合は、
古き良き@code{select}ベースのディスパッチ(@ref{Simple dispatcher}に
例があります)を使うほうが簡単なことがあります。
@c COMMON

@item
@c EN
If what you need is to control the resource consumption in the
subsystem, and the subsystem works fairly independently from
the main system, you may be able to use Unix processes instead of threads.
It may sound to go backward, but Unix process does provide
higher "shield" between the subsystem and the main system
(e.g. the main system can keep running even if subsystem segfaults).
@c JP
サブシステムにおけるリソースの消費をコントロールする必要がある場合で、
サブシステムがメインシステムとほとんど独立に動作する場合は、
スレッドの代わりにUnixプロセスが使えることでしょう。
時代に逆行するように聞こえますが、Unixプロセスはサブシステムと
メインシステムの間に高度な``防御壁''を提供します。
(例えば、サブシステムがセグメンテーション違反を起こしても、
メインシステムは実行しつづけられます。)
@c COMMON

@end itemize

@c EN
Of course, these technique are not mutually exclusive with
native threads.  You can use dispatcher with "thread pool" technique,
for example.   Just keep it in your mind that the native threads
are not only but one of the ways to realize those features.
@c JP
もちろん、これらのテクニックはネイティブスレッドとは相互排他ではありません。
例えば、``スレッドプール''テクニックと一緒にディスパッチャを使うこともできます。
それらの機能を実現するために、ネイティブスレッドが唯一の方法ではないということを
心に留め置いて下さい。
@c COMMON

@c EN
@subsubheading Uncaught errors in a thread body
@c JP
@subsubheading スレッドボディ内で捕捉されないエラー
@c COMMON

@c EN
When you run a single-thread program that raises an unexpected (unhandled)
error, Gauche prints an error message and a stack trace by default.
So sometimes it perplexes programmers when a thread doesn't print
anything when it dies because of an unhandled error.
@c JP
シングルスレッドのプログラムが予期せぬ(捕捉されない)エラーを起こした場合、
デフォルトではGaucheはエラーメッセージとスタックトレースを表示します。
ところが、スレッドで捕捉されないエラーが生じスレッドが終了しても、
何も表示されません。
@c COMMON

@c EN
What's happening is this: An unhandled error in a thread body would
cause the thread to terminate, and the error itself will propagate
to the thread who's expecting the result of the terminated thread.
So, you get the error (wrapped by @code{<uncaught-exception>})
when you call @code{thread-join!} on a thread which is terminated
because of an unhandled error.  The behavior is defined in SRFI-18.
@c JP
それはこういうわけです。スレッド本体でエラーが起き、それがスレッド中で処理されなければ、
スレッドは終了し、エラー自体はそのスレッドの終了を待つスレッドへと伝達される仕組みだからです。
エラーで終了したスレッドに対して@code{thread-join!}を呼んだ時点で、
元のエラーを@code{<uncaught-exception>}でラップしたエラーが投げられます。
この動作はSRFI-18で規定されています。
@c COMMON

@c EN
If you fire a thread for one-shot calculation, expecting to receive
the result by @code{thread-join!}, then this is reasonable---you can
handle the error situation in the ``parent'' thread.  However,
if you run a thread to loop indefinitely to process something and
not expect to retrieve its result via @code{thread-join!}, this becomes
a pitfall; the thread may die unexpectedly but you wouldn't know it.
(If such a thread is garbage-collected, a warning is printed.
However you wouldn't know when that happens so you can't count on it.)
@c JP
新たなスレッドを一時的な計算のために走らせて、その結果を@code{thread-join!}で
受け取るという使い方なら、この動作は便利です。「親スレッド」でまとめてエラーを
捕捉できるからです。けれどもスレッドをずっとループさせてジョブを次々と処理する、といった
用法では@code{thread-join!}は呼ばれるとは限らず、この仕様は落とし穴になり得ます。
スレッドがエラーで死んだのに気づかないかもしれないからです。
(エラーで終了したスレッドが@code{thread-join!}されることなくGC対象になった場合は
警告が出力されます。しかし、GCがどのタイミングで起きるかはわかりません。)
@c COMMON

@c EN
For such threads, you should always wrap the body of such thread
with @code{guard}, and handles the error explicitly.  You can call
@code{report-error} to display the default error message and a stack
trace.
@c JP
そういう使い方をするスレッドについては、本体を常に@code{guard}で包んで
エラーを明示的に処理すべきです。例えばエラーメッセージとスタックトレースを出したければ
@code{report-error}を呼びます。
@c COMMON

@example
(thread-start!
 (make-thread (^[] (guard (e [else (report-error e) #f])
                     ... thread body ...))))
@end example

@c EN
@xref{Thread exceptions}, for the details of thread exception handling.
@c JP
スレッドでの例外の処理について詳しくは@ref{Thread exceptions}を参照してください。
@c COMMON

@c EN
Note: As of 0.9.5, Gauche has a known bug that the tail call of
error handling clauses of @code{guard} doesn't become a proper
tail call.   So, the following code, which should run safely
in Scheme, could eat up a stack:
@c JP
註: 0.9.5の時点では、@code{guard}のエラーハンドラ節が
末尾コンテクストで呼ばれないというバグがあります。
例えば次のコードはSchemeでは本来スタックを消費せずにループするはずですが、
現在のGaucheではスタックを徐々に食いつぶしてしまいます。
@c COMMON

@example
(thread-start!
 (make-thread (^[] (let loop ()
                     (guard (e [else (report-error e) (loop)])
                       ... thread body ...)))))
@end example

@c EN
For the time being, you can lift the call to loop outside of
@code{guard} as workaround.
@c JP
当面は回避策として、@code{loop}の呼び出しを@code{guard}の外側に出してください。
@c COMMON

@example
(thread-start!
 (make-thread (^[] (let loop ()
                     (guard (e [else (report-error e)])
                       ... thread body ...)
                     (loop)))))
@end example

@c EN
@subsubheading Using high-level libraries
@c JP
@subsubheading 高レベルライブラリを使う
@c COMMON

@c EN
As we've seen above, there are lots of caveats to consider when you use threads.
In fact, for typical use cases, Gauche provides high-level utilities
that hides thireads under the hood.  For example,
Concurrent sequences implements producer-consumer type concurrency
by running the producer thread (@pxref{Concurrent sequences}),
and Parallel map provides a utility to run computation on a group of
data conucurrently (@pxref{Parallel map}.  Plumbing uses threads implicity
to construct a network of input/output ports(@pxref{Plumbing ports}).
@c JP
これまで見たように、スレッドを使う際には考慮すべき注意点が多々あります。
そこで、Gaucheでは典型的なユースケースに対して、スレッドをボンネットの下に隠す
高レベルライブラリを用意しています。
例えば並行シーケンスは生産者-消費者型の並列性を簡単に書けます
(@ref{Concurrent sequences}参照)し、並列mapはデータのセットに対して
スレッドを使って並行計算を行います(@ref{Parallel map}参照)。
配管(plumbing)を使うと複雑な入力/出力ポートのネットワークを組めますが、
裏ではスレッドが動いています(@ref{Plumbing ports}参照)。
@c COMMON

@c EN
Those high-level libraries hides cumbersome details around using threads.
Take a look at @code{control.*} modules to see if there's any that saves
you the trouple of using bare thread primitives.
(If you can't find a suitable library for your purpose but you think it is
a common thread use case, let us know!)
@c JP
これらの高レベルライブラリはスレッドを使うに当たっての煩雑な詳細を隠してくれます。
@code{control.*}モジュールを見てみてください。
自分でスレッドを直接使う手間を省けるライブラリがあるかもしれません。
(もし、やりたいことを実現してくれるライブラリがなく、
でもその目的がよくあるものなら、ぜひ教えてください!)
@c COMMON

@node Thread procedures, Thread local storage, Thread programming tips, Threads
@subsection Thread procedures
@c NODE スレッド手続き

@deftp {Builtin Class} <thread>
@clindex thread
@c EN
A thread.  Each thread has an associated thunk which is evaluated by
a POSIX thread.  When thunk returns normally, the result is stored
in the internal 'result' slot, and can be retrieved by @code{thread-join!}.
When thunk terminates abnormally, either by raising an exception or
terminated by @code{thread-terminate!}, the exception condition is
stored in their internal 'result exception' slot, and will be passed
to the thread calling @code{thread-join!} on the terminated thread.
@c JP
スレッドを表すクラスです。それぞれのスレッドは、POSIXスレッドにより
評価される関連付けられた手続きを持ちます。手続きが正常に戻ると、
その結果は内部的な``結果''スロットに格納され、@code{thread-join!}により
取得することができます。例外が投げられるか
@code{thread-terminate!}により終了されるかで、手続きが異常終了すると、
例外条件が内部的な``結果としての例外''スロットに格納され、
その例外条件は終了したスレッドに対して@code{thread-join!}を
呼ぶスレッドへと渡されます。
@c COMMON

@c EN
Each thread has its own dynamic environment and dynamic handler stack.
When a thread is created, its dynamic environment is initialized by
the creator's dynamic environment.  The thread's dynamic handler
stack is initially empty.
@c JP
それぞれのスレッドは独自の動的環境と動的なハンドラスタックを持っています。
あるスレッドが生成されると、その動的な環境は生成者の動的な環境によって
初期化されます。そのスレッドの動的なハンドラスタックは初期においては空です。
@c COMMON

@c EN
A thread is in one of the following four states at a time.
You can query the thread state by the @code{thread-state} procedure.
@c JP
スレッドは以下の4つの状態のうちのひとつを取ります。@code{thread-state}手続きで
スレッドの状態を調べることができます。
@c COMMON

@table @code
@item new
@c EN
A thread hasn't started yet.  A thread returned from @code{make-thread}
is in this state.
Once a thread is started it will never be in this state again.
At this point, no POSIX thread has been created; @code{thread-start!}
creates a POSIX thread to run the Gauche thread.
@c JP
まだ作られたばかりで起動されてない状態です。@code{make-thread}が返すスレッドは
この状態です。スレッドがひとたび起動されると、そのスレッドがこの状態に戻ることは
決してありません。
この時点ではPOSIXスレッドはまだ作られません。@code{thread-start!}によって
POSIXスレッドが作られ、Gaucheのスレッドを実行します。
@c COMMON
@item runnable
@c EN
When a thread is started by @code{thread-start!}, it becomes to this
state.   Note that a thread blocked by a system call is still in
@code{runnable} state.
@c JP
@code{thread-start!}によって起動されたスレッドはこの状態になります。
スレッドがシステムコールによるブロックされている時もその状態は@code{runnable}
であることに注意してください。
@c COMMON
@item stopped
@c EN
A thread becomes in this state when it is stopped by @code{thread-stop!}.
A thread in this state can go back to @code{runnable} state by
@code{thread-cont!}, resuming execution from the point when
it is stopped.
@c JP
スレッドが@code{thread-stop!}によって止められるとこの状態になります。
この状態のスレッドは@code{thread-cont!}によって再び@code{runnable}になり、
止められた時点から実行を再開することができます。
@c COMMON
@item terminated
@c EN
When the thread finished executing associated code, or
is terminated by @code{thread-terminate!}, it becomes in this state.
Once a thread is in this state, the state can no longer be changed.
@c JP
割り当てられたコードの実行が終了したり、@code{thread-terminate!}によって
強制的に終了させられた時に、スレッドはこの状態になります。
一度この状態になると他の状態に遷移することはありません。
@c COMMON
@end table

@c EN
Access to the resources shared by multiple threads must be protected
explicitly by synchronization primitives.
@xref{Synchronization primitives}.
@c JP
複数のスレッドで共有されるリソースへのアクセスは、同期化プリミティブにより
明示的に保護されなければなりません。@ref{Synchronization primitives}参照。
@c COMMON

@c EN
Access to ports are serialized by Gauche. If multiple threads attempt
to write to a port, their output may be interleaved but no output
will be lost, and the state of the port is kept consistent.
If multiple threads attempt to read from a port, a single read
primitive (e.g. @code{read}, @code{read-char} or @code{read-line})
works atomically.
@c JP
ポートへのアクセスはGaucheによりシリアライズされます。
複数のスレッドが1つのポートへの書き込みを試みた場合、それらの出力は
混じることもありますが、失われる出力はなく、そのポートのステータスは
一貫性が保たれます。複数のスレッドが1つのポートからの読み込みを試みた
場合、1つの読み込みプリミティブ(例えば、@code{read}や@code{read-char}、
@code{read-line}など)がアトミックに実行されます。
@c COMMON

@c EN
Signal handlers are shared by all threads, but each thread has
its own signal mask.  @xref{Signals and threads}, for details.
@c JP
シグナルハンドラは全てのスレッドで共有されますが、それぞれのスレッドは
独自のシグナルマスクを持ちます。詳細は、@ref{Signals and threads}を参照。
@c COMMON

@c EN
A thread object has the following external slots.
@c JP
スレッドオブジェクトは以下の外部スロットを持ちます。
@c COMMON

@defivar <thread> name
@c EN
A name can be associated to a thread.
This is just for the convenience of the application.
The primordial thread has the name "@code{root}".
@c JP
スレッドに関連付けられる名前。
これは単にアプリケーションにとっての便宜を図るためのものです。
原始となるスレッドは``@code{root}''という名前を持ちます。
@c COMMON
@end defivar

@defivar <thread> specific
@c EN
A thread-local slot for use of the application.
@c JP
アプリケーションが使うスレッドローカルなスロット。
@c COMMON
@end defivar
@end deftp

@defun current-thread
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns the current thread.
@c JP
現在のスレッドを返します。
@c COMMON
@end defun

@defun thread? obj
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is a thread, @code{#f} otherwise.
@c JP
@var{obj}がスレッドなら@code{#t}、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun make-thread thunk :optional name error-reporter
[SRFI-18+], [SRFI-21+]
@c MOD gauche.threads
@c EN
Creates and returns a new thread to execute @var{thunk}.
To run the thread, you need to call @code{thread-start!}.
The result of @var{thunk} may be retrieved by calling @var{thread-join!}.
@c JP
@var{thunk}を実行するための新しいスレッドを生成して返します。
そのスレッドの実行を開始するには、@code{thread-start!}を呼ぶ必要があります。
@var{thunk}の実行結果は、@var{thread-join!}を呼ぶことで回収できます。
@c COMMON

@c EN
You can provide the name of the thread by the optional argument @var{name}.
@c JP
オプション引数@var{name}を与えることで、そのスレッドに名前を与えることができます。
@c COMMON

@c EN
The created thread inherits the signal mask of the calling thread
(@pxref{Signals and threads}), and has a copy of
parameters of the calling thread at the time of creation
(@pxref{Parameters}).
@c JP
作成されたスレッドは、呼び出したスレッドのシグナルマスクを継承し
(@ref{Signals and threads}参照)、また呼び出したスレッドの持つ
その時点でのパラメータのコピーを受けとります。
@c COMMON

@c EN
Other than those initial setups, there will be no relationship between
the new thread and the calling thread; there's no parent-child
relationship like Unix process.   Any thread can call @code{thread-join!}
on any other thread to receive the result.  If nobody issues
@code{thread-join!} and nobody holds a
reference to the created thread, it will be garbage collected
after the execution of the thread terminates.
@c JP
これらの初期化操作以外に、作られるスレッドと呼び出したスレッド間の関係は
ありません。Unixのプロセスのような親子関係があるわけではないのです。
どのスレッドも、他のスレッドに対して@code{thread-join!}を発行
して結果を受け取ることができます。
もし誰も@code{thread-join!}を発行せず、また作られたスレッドに対する
参照を保持していなかった場合、スレッドは実行が終了した後にガベージコレクトされます。
@c COMMON

@c EN
If a thread execution is terminated because of uncaught exception,
it is saved in the thread object, and reraised
when @code{thread-join!} is called (wrapped by @code{<uncaught-exception>}
condition).

If @code{thread-join!} has never been called on the thread until
it is garbage-collected, a warning
will be printed to the standard error port notifying
``thread dies a lonely death'':  It usually indicates some coding
error.  If you don't collect the result of threads, you have to
make sure that all the exceptions are captured and handled within @var{thunk}.
@c JP
もしスレッドが捕捉されない例外のために実行を終了した場合、
その例外はスレッドオブジェクトに保管され、
@code{thread-join!}が呼ばれた時に@code{<uncaught-exception>}にラップされて
再び投げられます。

もし@code{thread-join!}がそのスレッドに対し一切呼ばれずに
スレッドがガベージコレクトされた場合、
標準エラーポートに``thread dies a lonely death'' という
警告メッセージが出力されます。そのようなケースは通常何らかのコーディングエラーで
あるからです。スレッドの結果を回収しない場合は、
@var{thunk}中ですべての例外を捕捉し処理しなければなりません。
@c COMMON

@c EN
The optional @var{error-reporter} argument is Gauche's extension.

Since the uncaught exception from @var{thunk} is reraised by @code{thread-join!},
the exception won't be reported as in the usual mannter by default
(otherwise, it will be reported twice, once when the exception occurs, and
again when @code{thread-join!} raises @code{<uncaught-exception>}.)
This is logical, but sometimes it causes an unexpected error
from the thread unnoticed, especially @code{thread-join!} isn't
called soon, or at all.  Although the ``right way'' is to always install
your own exception handler, it requires more repetitive, boilerplate code
for ``just in case''.
This argument provides a handy alternative.

The @var{error-reporter} argument can be @code{#f}, @code{#t}, or a
procedure taking one argument.  @code{#f} is the default behavior
(do not report the error immediately).  If it is @code{#t},
the error is reported as usual when it occurs.  If it is a procedure,
it is called with the thrown condition, and supposed to report
the error in some way (e.g. logging).   In any case, the condition
is saved in the thread object and reraised by @code{thread-join!} anyway.
Note that If @var{error-reporter} itself
raises an exception, Gauche process aborts by double fault.

If there's an exception handler installed when an error occurs,
@var{error-repoorter} is not consulted.  @var{error-reporter} is not
a substitution of exception handler, but merely set a fallback
mechanism for an unintentional leakage of exception.
@c JP
省略可能な@var{error-reporter}引数はGaucheの独自拡張です。

@var{thunk}からの捕捉されない例外は@code{thread-join!}から再び投げられるので、
デフォルトでは例外発生時にそのことは報告されません
(でないと、例外発生時と@code{thread-join!}から再び投げられた時で
重複報告されてしまいます)。
これは筋が通っていますが、@code{thread-join!}の呼ばれるタイミングが
ずっと後だったり全く呼ばれない場合に、予想していないエラーが気づかれないままに
なってしまう場合があります。「正しい方法」は常に独自の例外ハンドラを
設定することですが、「念の為」に似たようなコードを繰り返し書かねばならなくなります。
この引数はより手軽な代替です。

@var{error-reporter}引数は、@code{#f}、@code{#t}、あるいは1引数を取る
手続きでなければなりません。@code{#f}の場合はデフォルトの動作で、
例外は発生時には報告されません。@code{#t}の場合は例外発生時に
通常の報告が出されます。手続きの場合は、投げられたコンディションを
引数としてその手続きが呼ばれます。
手続きは何らかの例外報告(ログなど)をすることが期待されます。
いずれにせよ、コンディションはスレッドオブジェクトに保存され、
@code{thread-join!}で再び投げられることに変わりはありません。
@var{error-reporter}の中でエラーが起きた場合、ダブルフォールトとみなされ
Gaucheプロセスがabortするので注意してください。

エラーが起きた時点で例外ハンドラがインストールされていれば@var{error-reporter}
は無視されます。@var{error-reporter}は例外ハンドラの置き換えではなく、
意図せずに例外が漏れてきてしまった場合のフォールバックを指定するものです。
@c COMMON

@c EN
Internally, this procedure just allocates and initializes a Scheme
thread object; the POSIX thread is not created until @code{thread-start!}
is called.
@c JP
内部的に、この手続きは単にSchemeスレッドオブジェクトを割り当て初期化している
だけです。POSIXスレッドは@code{thread-start!}が呼ばれるまで生成されません。
@c COMMON
@end defun

@defun make-thread/loop proc ehandler :optional name
@c MOD gauche.threads
@c EN
This procedure creates a thread that loops, like a event loop.
There's a common pattern to avoid typical caveats, so we codify
it in this procedure.

@var{proc} is a procedure that takes one argument, @var{break}, an
escape procedure.  When @var{proc} returns, it is immediately
called again with the same argument.  If you want to exit the loop,
call @var{break}--then the thread terminates, and the argument
passed to @var{break} becomes the result of the thread, which can
be retrieved by @code{thread-join!}.

@var{ehandler} is a procedure that takes two arguments, and called
whenever an exception is raised during the loop.  The first argument
is the raised condition, and the second argument is the @var{break}
procedure the same as the one passed to @var{proc}.  The @var{ehandler}
processes the condition, and can take one of the following actions.

@enumerate
@item
Return.  In this case, the thread resumes the loop to call @var{proc}
repeatedly.
@item
Call @var{break}.  The thread terminates, and the argument passed
to @var{break} becoms the result of the thread.
@item
Raise the condition again, or a different condition.
The thread aborts, and the raised condition is reraised
(wrapped with @code{<uncaught-condition>}) when
@code{thread-join!} is called.
@end enumerate

The idea is that you want to keep looping unless the exception
is too serious to keep doing so.

Here's the typical pattern of event handling thread:
@c JP
この手続きは、イベントループのようなループするスレッドを作ります。
典型的な危険を避ける書き方には共通のパターンがあるので、
それをコード化したものがこの手続きです。

@var{proc}はひとつの引数、@var{break}を取る手続きです。
@var{proc}からリターンすると、直ちに再び@var{proc}が呼ばれます。
@var{break}を呼び出すことでループから抜け出し、スレッドが終了します。
@var{break}に渡した引数がスレッドの結果 (@code{thread-join!}の戻り値となります。

@var{ehandler}は2つの引数を取る手続きで、ループ中で例外が起きた時に
呼び出されます。最初の引数は投げられたコンディション、
次の引数は@var{proc}に渡される@var{break}と同じものです。
@var{ehandler}はコンディションを処理し、次の3つのうちのいずれかの
帰結を取ります。

@enumerate
@item
リターンする。この場合、スレッドは@var{proc}を呼ぶループを再開します。
@item
@var{break}を呼ぶ。スレッドは終了し、@var{break}に渡した引数が
スレッドの結果となります。
@item
渡されたコンディションを再び投げるか、新たなコンディションを投げる。
スレッドの実行は中断され、@var{thread-join!}が呼ばれると
投げられたコンディションが(@code{<uncaught-condition>}にラップされて)
再び投げられます。
@end enumerate

基本的な考え方は、例外が重大でこれ以上処理を続けられない場合以外は
ループを続ける、というものです。

次の例は典型的なパターンを示します:
@c COMMON

@example
(thread-start!
 (make-thread/loop
  (^[break] (let event (read-event)
              (cond [(termination? event)  (break 'done)]
                    ... handle other event types ...
                    )))
  (^[e break] (if (fatal-condition? e)
                 (break 'something-bad-happened)]
                 (log-format "Error in event loop: ~S" e))))
@end example
@end defun

@defun thread-state thread
@c MOD gauche.threads
@c EN
Returns one of symbols @code{new}, @code{runnable}, @code{stopped}
or @code{terminated}, indicating the state of @var{thread}.
@c JP
@var{thread}の状態を示す、@code{new}、@code{runnable}、@code{stopped}、
@code{terminated}のいずれかのシンボルを返します。
@c COMMON
@end defun

@defun thread-name thread
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns the value of @var{name} slot of @var{thread}.
@c JP
@var{thread}のスロット@var{name}の値を返します。
@c COMMON
@end defun

@defun thread-specific thread
@defunx thread-specific-set! thread value
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Gets/sets the value of the @var{thread}'s specific slot.
@c JP
@var{thread}の指定したスレッドの値を取得/設定します。
@c COMMON
@end defun

@defun thread-start! thread
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Starts the @var{thread}.  An error is thrown if @var{thread} is not in
``new'' state.
Returns @var{thread}.
@c JP
@var{thread}を開始します。@var{thread}が ``new'' 状態でなければエラーが投げられます。
@var{thread}を返します。
@c COMMON
@end defun

@defun thread-try-start! thread
@c MOD gauche.threads
@c EN
Starts and returns the @var{thread} if it is in ``new'' state.
Otherwise, returns @code{#f}.
@c JP
@var{thread}が ``new'' 状態であればそれを開始し、@var{thread}自身を返します。
そうでなければ@code{#f}を返します。
@c COMMON

@c EN
Note that a thread can become a ``terminated'' state even if it is never
started, if another thread calls @code{thread-terminate!} on it.
If that's the possibility, this procedure comes handy,
for @code{thread-start!} may raise an error if the thread is
termianted before started.
@c JP
スレッドは開始する前に ``terminated'' 状態になる場合があります。他のスレッドが
そのスレッドに対して@code{thread-terminate!}を呼んだ場合です。
開始する前に終了してしまったスレッドに対して@code{thread-start!}を呼ぶとエラーが
投げられますが、この手続きではエラーになりません。
@c COMMON
@end defun

@defun thread-join! thread :optional timeout timeout-val
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Waits termination of @var{thread}, or until the timeout is reached
if @var{timeout} is given.
@c JP
@var{thread}の終了、あるいは@var{timeout}が与えられていればtimeoutが
それに達するのを待ちます。
@c COMMON

@c EN
@var{Timeout} must be either a @code{<time>} object (@pxref{Time})
that specifies absolute point of time, or a real number that specifies
relative point of time from the time this procedure is called
in number of seconds, or @code{#f} that indicates no timeout (default).
@c JP
@var{Timeout}は絶対的な時間を表す@code{<time>}オブジェクト(@ref{Time}参照)か、
この手続きが呼ばれた時刻からの相対的な時間を秒数で表した実数でなければなりません。
タイムアウトが指定されていない(デフォルト)は@code{#f}です。
@c COMMON

@c EN
If @var{thread} terminates normally, @code{thread-join!} returns
a value which is stored in the result field of @var{thread}.
If @var{thread} terminates abnormally, @code{thread-join!} raises
an exception which is stored in the result exception field of @var{thread}.
It can be either a @code{<terminated-thread-exception>} or
@code{<uncaught-exception>}.
@c JP
@var{thread}が正常に終了したら、@code{thread-join!}は@var{thread}の
結果フィールドに格納されている値を返します。
@var{thread}が異常終了したら、@code{thread-join!}は@var{thread}の結果例外
フィールドに格納されている例外を投げます。それは
@code{<terminated-thread-exception>}か
@code{<uncaught-exception>}のどちらかです。
@c COMMON

@c EN
If the timeout is reached, @var{thread-join!} returns @var{timeout-val}
if given, or raises @code{<join-timeout-exception>}.
@c JP
タイムアウトに達すると、@var{timeout-val}が与えられていれば@var{timeout-val}を返し、
与えられていなければ@code{<join-timeout-exception>}を投げます。
@c COMMON

@c EN
@xref{Thread exceptions}, for the details of these exceptions.
@c JP
これらの例外の詳細については@ref{Thread exceptions}を参照してください。
@c COMMON
@end defun

@defun thread-yield!
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Suspends the execution of the calling thread and yields CPU to other
waiting runnable threads, if any.
@c JP
呼び出しているスレッドの実行を中断し、他に待機中の実行可能なスレッドがあれば、
CPUにそれを処理させます。
@c COMMON
@end defun

@defun thread-sleep! timeout
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Suspends the calling thread for the period specified by @var{timeout},
which must be either a @code{<time>} object (@pxref{Time}) that
specifies absolute point of time, or a real number that specifies
relative point of time from the time this procedure is called
in number of seconds.
@c JP
呼び出しているスレッドを@var{timeout}に指定した時間だけ中断します。
@var{timeout}は絶対的な時間を表す@code{<time>}オブジェクト(@ref{Time}参照)か、
この手続きが呼ばれた時刻からの相対的な秒数を表す実数でなければなりません。
@c COMMON

@c EN
After the specified time passes, @code{thread-sleep!} returns with
unspecified value.
@c JP
指定された時間が経過すると、@code{thread-sleep!}は未定義値を返します。
@c COMMON

@c EN
If @var{timeout} points a past time, @code{thread-sleep!} returns
immediately.
@c JP
@var{timeout}が過去の時間を指していたら、@code{thread-sleep!}はすぐに戻ります。
@c COMMON
@end defun

@defun thread-stop! thread :optional timeout timeout-val
@c MOD gauche.threads
@c EN
Stops execution of the target @var{thread} temporarily.
You can resume the execution of the @var{thread} by @code{thread-cont!}.
@c JP
対象となるスレッド@var{thread}の実行を一時的に停止します。
停止されたスレッドは@code{thread-cont!}により実行を再開させられます。
@c COMMON

@c EN
The stop request is handled synchronously; that is,
Gauche VM only checks the request at the ``safe'' point
of the VM and stops itself.  It means if the @var{thread} is
blocked by a system call, it won't become @code{stopped} state
until the system call returns.
@c JP
停止リクエストは同期的に処理されます。すなわち、GaucheのVMは実行ループ中の
「安全な」場所で停止リクエストをチェックし、それがあれば自分自身を停止するように
なっています。このことは、@var{thread}がシステムコールによりブロックされている場合、
それが戻ってくるまでスレッドが@code{stopped}状態にならないことを意味します。
@c COMMON

@c EN
By default, @code{thread-stop!} returns after the target
thread stops.  Since it may take indefinitely, you can give optional
@var{timeout} argument to specify timeout.   The @var{timeout}
argument can be @code{#f}, which means no timeout, or
a @code{<time>} object that specifies an absolute point of time,
or a real number specifying the number of seconds to wait.
@c JP
デフォルトでは、@code{thread-stop!}は対象スレッドが停止状態になってから
戻ってきます。しかしそうなるまでにどれだけ時間がかかるかわからないので、
省略可能引数@var{timeout}を与えて、タイムアウトすることができます。
@var{timeout}引数には@code{#f}(タイムアウトせず停止するまで待ち続ける)、
@code{<time>}オブジェクト(絶対的な時刻を指定)、もしくは
実数(現在からの秒数を指定)を与えられます。
@c COMMON

@c EN
The return value of @code{thread-stop!} is @var{thread} if
it could successfully stop the target, or @var{timeout-val}
if timeout reached.   When @var{timeout-val} is omitted, @code{#f}
is assumed.
@c JP
@code{thread-stop!}の戻り値は、対象スレッドを停止させられたなら
その@var{thread}オブジェクト、タイムアウトしたなら@var{timeout-val}です。
@var{timeout-val}が省略された場合は@code{#f}とみなされます。
@c COMMON

@c EN
If the target @var{thread} has already been stopped by the caller
thread, this procedure returns @var{thread} immediately.
@c JP
対象スレッドが既に呼び出しスレッドの要求によって停止していた場合は、
直ちに@var{thread}が返されます。
@c COMMON

@c EN
When @var{thread-stop!} is timed out, the request remains
effective even after @code{thread-stop!} returns.
That is, the target thread may stop at some point in future.
The caller thread is expected to call @code{thread-stop!}
again to complete the stop operation.
@c JP
@var{thread-stop!}がタイムアウトして@code{thread-stop!}から帰ってきた
場合でも、リクエストは有効なままになっており、未来のいつか@var{thread}を
停止させます。呼び出し側は、いずれ@code{thread-stop!}を再び呼び出して
停止を確認する必要があります。
@c COMMON

@c EN
An error is signaled if the target thread has already been
stopped by another thread (including the ``pending'' stop
request issued by other threads), or the target thread
is in neither @code{runnable} nor @code{stopped} state.
@c JP
対象スレッドが既に別のスレッドによって停止させられていた場合
(別のスレッドによって停止要求が出されて停止待ちに
なっている状態も含みます)や、
対象スレッドが@code{runnable}でも@code{stopped}でもない状態の場合は
エラーが報告されます。
@c COMMON
@end defun

@defun thread-cont! thread
@c MOD gauche.threads
@c EN
Resumes execution of @var{thread} which has been stopped by
@code{thread-stop!}.  An error is raised if @var{thread}
is not in stopped state, or it is stopped by another thread.
@c JP
@code{thread-stop!}で停止した@var{thread}の実行を再開します。
@var{thread}が停止状態でなかったり、@code{thread-cont!}を呼び出したのとは
別のスレッドによって停止させられていた場合はエラーが報告されます。
@c COMMON

@c EN
If the caller thread has already requested to stop the target
thread but timed out, calling @code{thread-cont!} cancels
the request.
@c JP
停止要求を既に出していて、タイムアウトしていた場合、@code{thread-cont!}は
その停止要求をキャンセルする役割を持ちます。
@c COMMON
@end defun

@defun thread-terminate! thread :key force
[SRFI-18+], [SRFI-21+]
@c MOD gauche.threads
@c EN
Terminates the specified thread @var{thread}.
The @var{thread} is terminated and an instance of
@code{<terminated-thread-exception>} is stored in the result exception
field of @var{thread}.
@c JP
指定されたスレッド@var{thread}を終了します。
@var{thread}は終了され、@code{<terminated-thread-exception>}のインスタンスが
@var{thread}の結果例外のフィールドに格納されます。
@c COMMON

@c EN
If @var{thread} is the same as the calling thread, this procedure
won't return.  Otherwise, this procedure returns unspecified value.
@c JP
@var{thread}が呼び出しているスレッドと同じ場合、この手続きは戻りません。
そうでなければ、この手続きは未定義値を返します。
@c COMMON

@c EN
If @var{thread} is already terminated, this procedure does nothing.
@c JP
@var{thread}が既に終了していた場合は、この手続きは何もしません。
@c COMMON

@c EN
By default, this procedure tries to termiante the thread in ``safe''
point, so that the thread can keep the process in consistent state.
The locked mutexes, however, may remain locked; they become
``abandoned'' state and when other thread tries to touch the mutex
it will raise @code{<abandoned-mutex-exception>}.
@c JP
デフォルトでは、この手続きは指定スレッドを「安全な」箇所で終了させます。
これは、プロセスの状態に最低限の一貫性を保証します。
ただし、指定スレッドがロックしていたmutexはロックされたまま「放棄された」状態になります。
他のスレッドがそのmutexに触ろうとすると@code{<abandoned-mutex-exception>}例外が
投げられます。
@c COMMON

@c EN
This strategy may, however, leave the system's thread unterminated,
if the thread is blocking in certain system calls, even in Scheme level
the thread is marked terminated.  The system thread will terminate itself
as soon as it resumes and return the control to Gauche runtime.
@c JP
この戦略では、スレッドがある種のシステムコールでブロックしていた場合、
Schemeレベルのスレッドが「terminated」とマークされた後でもシステムスレッドが
生きたまま残る可能性があります。このシステムスレッドが再開されてGaucheのランタイムに
制御が戻れば、その時点でシステムスレッドは自己終了します。
@c COMMON

@c EN
If, for some reason, you need to guarantee to terminate the system thread,
you can pass a true value to @code{force} keyword argument.  If you do so,
@code{thread-terminate!} will forcibly terminate the system thread
after the usual graceful termination fails.  It calls
@code{pthread_cancel} or @code{TerminateThread} as the last resort,
which can leave the process state inconsistent, so this mode should be
used in an absolute emergency.
@c JP
もし何らかの理由でシステムスレッドも確実に終了させたい場合は、
@code{force}キーワードに真の値を渡してください。その場合、
@code{thread-terminate!}は通常の穏やかな終了を試みて失敗したら、
強制的にシステムスレッドを終了させます。
これは最終的に@code{pthread_cancel}や@code{TerminateThread}コールによって
行われ、スレッドに後始末の余地を与えないため、プロセスの状態に一貫性が無くなる
可能性があります。緊急事態の時のみ用いてください。
@c COMMON
@end defun

@defun thread-schedule-terminate! thread
[SRFI-226]
@c MOD gauche.threads
@c EN
Triggers termination of a thread @var{thread}, but returns immediately
without confirming the termination.

This procedure does not attempt ``forcible'' termination as the @var{force}
argument of @code{thread-terminate!} does.  It just initiate the first
stage of termination, which just send an internal request to @var{thread}.
The thread will eventually terminate but there's no guarantee when it happens.

You can wait for @var{thread} to terminate later, using @code{thread-join!}.
@c JP
@var{thread}を終了させる仕組みを起動します。手続き自体はスレッドの終了を見届けることなく
直ちに返ります。

この手続きは@code{thread-terminate!}の@var{force}引数が行うような「強制的」な
終了も試みません。スレッド終了の最初のステージである、@var{thread}に内部的な
リクエストを送るところまでをやります。
@var{thread}はいずれ終了しますが、それがいつ起きるかについては何も保証はありません。

後で@code{thread-join!}を使って@var{thread}が終了するのを待つことはできます。
@c COMMON
@end defun

@node Thread local storage, Synchronization primitives, Thread procedures, Threads
@subsection Thread local storage
@c NODE スレッドローカル領域

@c EN
A thread local is an object that can hold per-thread value.
It is defined in SRFI-226.
@c JP
スレッドローカルはスレッドごとの値を格納できるオブジェクトです。
SRFI-226で規定されています。
@c COMMON

@c EN
Note: Parameters used to be the way to keep per-thread value, but
we've decided to split thread local storage from dyncamic binding
to conform SRFI-226.
Parameters should be used for dynamic binding, and thread locals should
be used for per-thread value.
If your existing code uses parameters for the per-thread value,
update it to use thread locals.
@xref{Transition to SRFI-226 parameters}, for the necessary changes.
@c JP
註: これまで、パラメータがスレッド毎の値を格納するためにも使われてきましたが、
SRFI-226に準拠するために、
動的束縛とスレッドローカル領域を切り離すことにしました。
パラメータは動的束縛のためだけに使われるべきで、スレッド毎の値を保持するには
スレッドローカルを使うようにしてください。
既存のコードで、スレッド毎の値を保持するためにパラメータを使っている場合は、
スレッドローカルを使うようにアップデートしてください。
必要な変更については@ref{Transition to SRFI-226 parameters}を参照してください。
@c COMMON


@defun make-thread-local init-value :optional inheritable? name
[SRFI-226]
@c MOD gauche.threads
@c EN
Returns a new thread local, with @var{init-value} as an initial value.
The optional @var{name} argument specifies thread local's name;
it is only used for debugging purpose.
@c JP
@var{init-value}を初期値とするあらたなスレッドローカルを作って返します。
省略可能な@var{name}引数は、スレッドローカルに名前を与えます。デバッグ時にのみ使われます。
@c COMMON

@c EN
A thread local is a handle to thread specific storage that can contain
single Scheme value.  You can retrieve its value with @code{tlref}
and set a new value with @code{tlset!}.
Once a thread local is created, it can be used from all existing
and future threads.
@c JP
スレッドローカルは一つのScheme値を格納できるスレッド毎の固有領域へのハンドルです。
@code{tlref}でその値を読み出し、@code{tlset!}で新たな値をセットできます。
一度スレッドローカルが作られると、それはその時点で存在する、あるいはこれから作られる
全てのスレッドで利用可能になります。
@c COMMON

@c EN
If @code{#f} is specified in @var{inheritable?} (default),
when a thread local is @code{tlref}-ed
first time in a thread, it returns @code{init-value}.
If a true value is specified in @var{inheritable?},
on the other hand, the initial value of the thread local
inherits the value of the creator thread at the moment
the thread is created.
@c JP
@var{inheritable?}引数が@code{#f}の場合(デフォルト)、
スレッドローカルが最初に@code{tlref}されると、@code{init-value}が返ります。
一方、@var{inheritable?}に真の値を指定すると、
スレッドが作られた時点で、それを作ったスレッドのスレッドローカルの値が初期値として使われます。
@c COMMON
@end defun

@defun thread-local? obj
[SRFI-226]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is a thread local, @code{#f} otherwise.
@c JP
@var{obj}がスレッドローカルなら@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun tlref tl
[SRFI-226]
@c MOD gauche.threads
@c EN
Returns the value of a thread local @var{tl}.
@c JP
スレッドローカル@var{tl}の呼び出しスレッドでの値を返します。
@c COMMON
@end defun

@defun tlset! tl val
[SRFI-226]
@c MOD gauche.threads
@c EN
Modifies the value of a thread local @var{tl} with @var{val}.
@c JP
スレッドローカル@var{tl}の呼び出しスレッドでの値を@var{val}に設定します。
@c COMMON

@c EN
As Gauche's extension, you can also use @code{set!} with @code{tlref}:
@c JP
Gaucheの拡張として、@code{tlref}と@code{set!}を使うこともできます:
@c COMMON

@example
(set! (tlref tl) obj) @equiv{} (tlset! tl obj)
@end example
@end defun


@node Synchronization primitives, Thread exceptions, Thread local storage, Threads
@subsection Synchronization primitives
@c NODE 同期プリミティブ

@c EN
Mutexes and condition variables are the low-level synchronization devices.
Defined in SRFI-18 and SRFI-21, they are portable across Scheme implementations
that supports one of those srfis.
(@xref{Mutex}, and @pxref{Condition variable}, for the details.)

However, in most cases you want to
use following higher-level synchronization utilities:
@c JP
mutexと条件変数が低レベルの同期デバイスとして提供されます。
これらはSRFI-18とSRFI-21で定義されているので、サポートしているScheme実装間では
ポータブルです。
(@ref{Mutex}、@ref{Condition variable}参照)。

しかし多くの場合、次のような高レベルの同期ユーティリティを使った方が良いです。
@c COMMON

@table @asis
@c EN
@item Atoms
An atom is a wrapper of arbitrary Scheme object, and allows synchronized
access to it somewhat like Java's @code{synchronized} blocks.
@c JP
@item アトム
アトムは任意のSchemeオブジェクトをラップして、Javaの@code{synchronized}ブロックに
似た形で同期アクセスを提供します。
@c COMMON
@c EN
@item Semaphores
A traditional synchronization primitive to share fixed number of resources.
@c JP
@item セマフォ
決まった数のリソースの利用を振り分けるのに使う、定番の同期プリミティブです。
@c COMMON
@c EN
@item Latch
Holds thread(s) until a set of operations is completed by
other thread(s).
@c JP
@item ラッチ
いくつかの操作が完了するまで、他のスレッドを待たせる同期プリミティブです。
@c COMMON
@c EN
@item Barrier
Wait until the preset number of thread reaches at the point.
@c JP
@item バリア
指定した個数のスレッドが指定ポイントに到達するまで全員で待ち合わせる同期プリミティブです。
@c COMMON
@c EN
@item MT-Queues
Thread-safe queues (@code{<mtqueue>}) are provided in @code{data.queue} module
(@pxref{Queue}), which works as a synchronized channel and
suitable to implement producer-consumer pattern.
@c JP
@item MT-Queue
スレッドセーフなキュー(@code{<mtqueue>})が@code{data.queue}モジュールで
提供されます(@ref{Queue}参照)。これは同期チャネルとして動作し、
生産者-消費者パターンを実装するのに適しています。
@c COMMON
@end table

@menu
* Mutex::
* Condition variable::
* Atom::
* Semaphore::
* Latch::
* Barrier::
@end menu

@node Mutex, Condition variable, Synchronization primitives, Synchronization primitives
@subsubsection Mutex
@c NODE Mutex

@deftp {Builtin Class} <mutex>
@clindex mutex
@c MOD gauche.threads
@c EN
A primitive synchronization device.  It can take one of four states:
locked/owned, locked/not-owned, unlocked/abandoned and unlocked/not-abandoned.
A mutex can be locked (by @code{mutex-lock!}) only if it is in unlocked state.
An 'owned' mutex keeps a thread that owns it.
Typically an owner thread is the one that locked the mutex,
but you can make a thread other than the locking thread own a mutex.
A mutex becomes unlocked either by @code{mutex-unlock!} or the owner
thread terminates.  In the former case, a mutex becomes unlocked/not-abandoned
state.  In the latter case, a mutex becomes unlocked/abandoned state.
@c JP
同期のためのプリミティブなデバイスです。次の4つの状態のいずれかを持ちます:
locked/owned、locked/not-owned、unlocked/abandoned、unlocked/not-abandoned。
Mutexは、それがunlocked(ロックされていない状態)であるときのみ、
(@code{mutex-lock!}により)ロックされます。
所有されている(owned) mutexは、そのmutexを所有しているスレッドを記憶しています。
通常、所有者となるスレッドはmutexをロックしたスレッドですが、
ロックしたのとは別のスレッドがmutexを所有するようにすることもできます。
ロックは@code{mutex-unlock!}によるか、所有するスレッドが終了すると解放されます。
前者の場合、mutexはunlocked/not-abandoned(ロックされておらず、放棄されていない状態)
になります。
後者の場合、mutexはunlocked/abandoned(ロックされておらず、放棄された状態)になります。
@c COMMON

@c EN
A mutex has the following external slots.
@c JP
Mutexは、以下の外部スロットを持ちます。
@c COMMON

@defivar <mutex> name
@c EN
The name of the mutex.
@c JP
Mutexの名前。
@c COMMON
@end defivar

@defivar <mutex> state
@c EN
The state of the mutex.  This is a read-only slot.
See the description of @code{mutex-state} below.
@c JP
Mutexの状態。これは読み取りのみ可能なスロットです。
下記の@code{mutex-state}の説明を参照して下さい。
@c COMMON
@end defivar

@defivar <mutex> specific
@c EN
A slot an application can keep arbitrary data.  For example, an application
can implement a 'recursive' mutex using the specific field.
@c JP
アプリケーションが任意のデータを保持することのできるスロットです。
例えば、アプリケーションはこの固有フィールドで'再帰的な' mutexを
実装することができます。
@c COMMON
@end defivar
@end deftp

@defun mutex? obj
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is a mutex, @code{#f} otherwise.
@c JP
@var{obj}がmutexであれば@code{#t}、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun make-mutex :optional name
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Creates and returns a new mutex object.
When created, the mutex is in unlocked/not-abandoned state.
Optionally, you can give a name to the mutex.
@c JP
新しいmutexオブジェクトを生成して返します。
生成時には、mutexの状態は、unlocked/not-abandoned(ロックされておらず、
放棄されていない状態)です。オプションで、このmutexに名前を付けることができます。
@c COMMON
@end defun

@defun mutex-name mutex
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns the name of the mutex.
@c JP
Mutexの名前を返します。
@c COMMON
@end defun

@defun mutex-specific mutex
@defunx mutex-specific-set! mutex value
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Gets/sets the specific value of the mutex.
@c JP
Mutexの固有の値を取得/セットできます。
@c COMMON
@end defun

@defun mutex-state mutex
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns the state of @var{mutex}, which may be one of the followings:
@c JP
@var{mutex}の状態を返します。状態は以下のうちの1つです。
@c COMMON

@table @asis
@c EN
@item a thread
The mutex is locked/owned, and the owner is the returned thread.
@item symbol @code{not-owned}
The mutex is locked/not-owned.
@item symbol @code{abandoned}
The mutex is unlocked/abandoned.
@item symbol @code{not-abandoned}
The mutex is unlocked/not-abandoned.
@c JP
@item あるスレッド
Mutexはlocked/owned(ロックされ所有されている)で、所有者は返されたスレッド。
@item シンボル @code{not-owned}
Mutexはlocked/not-owned(ロックされているが所有されていない)。
@item シンボル @code{abandoned}
Mutexはunlocked/abandoned(ロックされておらず、放棄されている)。
@item シンボル @code{not-abandoned}
Mutexはunlocked/not-abandoned(ロックされておらず、放棄されていない)。
@c COMMON
@end table
@end defun

@defun mutex-lock! mutex :optional timeout thread
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Locks @var{mutex}.  If @var{mutex} is in unlocked/not-abandoned
state, this procedure changes its state to locked state exclusively.
By default, @var{mutex} becomes locked/owned state, owned by the
calling thread.  You can give other owner thread as @var{thread} argument.
If @var{thread} argument is given and @code{#f}, the mutex becomes
locked/not-owned state.
@c JP
@var{mutex}をロックします。@var{mutex}がunlocked/not-abandoned(
ロックされておらず放棄されていない状態)なら、
この手続きはその状態を排他的なlocked(ロックされた状態)に変更します。
デフォルトでは、@var{mutex}はlocked/owned(ロックされ、所有された状態)になり、
所有者は呼び出したスレッドです。
他の所有しているスレッドを、引数@var{thread}を与えることもできます。
引数@var{thread}に@code{#f}が与えられると、mutexはlocked/not-owned
(ロックされ所有されていない状態)になります。
@c COMMON

@c EN
If @var{mutex} is in unlocked/abandoned state, that is, some other
thread has been terminated without unlocking it, this procedure
signals 'abandoned mutex exception' (@pxref{Thread exceptions})
after changing the state of @var{mutex}.
@c JP
@var{mutex}がunlocked/abandoned(ロックされておらず放棄された状態)ならば、それはつまり、
他の何らかのスレッドがそのロックを解放せずに終了した場合、
この手続きは@var{mutex}の状態を変更した後に、'abandoned mutex exception'
(@ref{Thread exceptions}参照)を通知します。
@c COMMON

@c EN
If @var{mutex} is in locked state and
@var{timeout} is omitted or @code{#f}, this procedure blocks until
@var{mutex} becomes unlocked.   If @var{timeout} is specified,
@code{mutex-lock!} returns when the specified time reaches in
case it couldn't obtain a lock.  You can give @var{timeout}
an absolute point of time (by @code{<time>} object, @pxref{Time}),
or a relative time (by a real number).
@c JP
@var{mutex}がlocked(ロックされた状態)で、@var{timeout}が省略されるか@code{#f}ならば、
この手続きは@var{mutex}のロックが解放されるまでブロックします。
@var{timeout}が指定されている場合は、ロックが獲得できなかったケースでは
指定された時間に達した時に@code{mutex-lock!}は戻ります。
@var{timeout}には、絶対的な時間(@code{<time>}オブジェクト、@ref{Time}参照)か、
相対的な時間を(実数で)指定できます。
@c COMMON

@c EN
@code{Mutex-lock!} returns @code{#t} if @var{mutex} is successfully
locked, or @code{#f} if timeout reached.
@c JP
@var{mutex}のロックが成功すると@code{mutex-lock!}は@code{#t}を返し、
タイムアウトに達すると@code{#f}が返ります。
@c COMMON

@c EN
Note that @var{mutex} itself doesn't implements a 'recursive lock'
feature; that is, if a thread that has locked @var{mutex} tries to lock
@var{mutex} again, the thread blocks.  It is not difficult, however,
to implement a recursive lock semantics on top of this mutex.
The following example is taken from SRFI-18 document:
@c JP
@var{mutex}それ自身は'再帰的なロック'の機能は実装していません。
つまり、@var{mutex}をロックしたスレッドが再度@var{mutex}をロックしようと
すると、そのスレッドはブロックします。しかし、このmutexに
基づいて再帰的なロックのセマンティクスを実装することは難しくありません。
次の例は、SRFI-18のドキュメントから引用したものです。
@c COMMON

@example
(define (mutex-lock-recursively! mutex)
  (if (eq? (mutex-state mutex) (current-thread))
      (let ((n (mutex-specific mutex)))
        (mutex-specific-set! mutex (+ n 1)))
      (begin
        (mutex-lock! mutex)
        (mutex-specific-set! mutex 0))))

(define (mutex-unlock-recursively! mutex)
  (let ((n (mutex-specific mutex)))
    (if (= n 0)
        (mutex-unlock! mutex)
        (mutex-specific-set! mutex (- n 1)))))
@end example
@end defun

@defun mutex-unlock! mutex :optional condition-variable timeout
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Unlocks @var{mutex}.  The state of @var{mutex} becomes unlocked/not-abandoned.
It is allowed to unlock a mutex that is not owned by the calling thread.
@c JP
@var{mutex}をアンロックします。@var{mutex}の状態は、unlocked/not-abandoned
(ロックされておらず、放棄されていない状態)となります。
呼び出しているスレッドにより所有されていないmutexをアンロックすることは
許されています。
@c COMMON

@c EN
If optional @var{condition-variable} is given, @code{mutex-unlock!}
serves the "condition variable wait" operation (e.g. @code{pthread_cond_wait}
in POSIX threads).   The current thread atomically wait on
@var{condition-variable} and unlocks @var{mutex}.
The thread will be unblocked when other thread signals on
@var{condition-variable} (see @code{condition-variable-signal!}
and @code{condition-variable-broadcast!} below), or @var{timeout}
reaches if it is supplied.  The @var{timeout} argument can be either
a @code{<time>} object to represent an absolute time point (@pxref{Time}),
a real number to represent a relative time in seconds, or @code{#f} which
means never.  The calling thread may be unblocked prematurely,
so it should reacquire the lock of @var{mutex} and checks the
condition, as in the following example (it is taken from SRFI-18 document):
@c JP
オプショナル引数の@var{conditional-variable}が与えられている場合、
@code{mutex-unlock!}は``条件変数待機''の動作も行います(例えば、POSIXスレッドの
@code{pthread_cond_wait})。
現在のスレッドは@var{mutex}をアンロックし、
@var{condition-variable}の待ち状態に入る動作をアトミックに行います。
スレッドは、他のスレッドが@var{condition-variable}にシグナルを通知するか
(下記の@code{condition-variable-signal!}と@code{condition-variable-broadcast!}を
見て下さい)、
@var{timeout}が与えられていてそれに達すると、ブロックが解除されます。
引数@var{timeout}は、絶対的な時間を表す@code{<time>}オブジェクト(@ref{Time}参照)、
相対的な時間を秒数で表す実数、タイムアウトしないことを表す@code{#f}のいずれかです。
ブロックが解除された時に、必ずしも条件が満たされているとは限らないので、
次に挙げる例(SRFI-18のドキュメントより引用)のように、
呼び出したスレッドは@var{mutex}のロックを再獲得して条件を検査するべきです。
@c COMMON

@example
(let loop ()
  (mutex-lock! m)
  (if (condition-is-true?)
      (begin
        (do-something-when-condition-is-true)
        (mutex-unlock! m))
      (begin
        (mutex-unlock! m cv)
        (loop))))
@end example

@c EN
The return value of @code{mutex-unlock!} is @code{#f} when it returns
because of timeout, and @code{#t} otherwise.
@c JP
@code{mutex-unlock!}の戻り値は、タイムアウトした場合に@code{#f}、
それ以外の場合は@code{#t}となります。
@c COMMON
@end defun

@defun mutex-locker mutex
@defunx mutex-unlocker mutex
@c MOD gauche.threads
@c EN
Returns @code{(lambda () (mutex-lock! mutex))} and
@code{(lambda () (mutex-unlock! mutex))}, respectively.
Each closure is created at most once per @var{mutex},
thus it is lighter than using literal lambda forms in a tight loop.
@c JP
それぞれ@code{(lambda () (mutex-lock! mutex))} と
@code{(lambda () (mutex-unlock! mutex))} を返します。
これらのクロージャは、各@var{mutex}につきひとつづつしか作られないため、
タイトなループの中ではこれらの形のリテラルなラムダ式を使うよりも軽量です。
@c COMMON
@end defun


@defun with-locking-mutex mutex thunk
@c MOD gauche.threads
@c EN
Calls @var{thunk} with locking a mutex @var{mutex}.  This is defined as
follows.
@c JP
@var{mutex}をロックして@var{thunk}を呼びます。次のように実装されています。
@c COMMON
@example
(define (with-locking-mutex mutex thunk)
  (dynamic-wind
   (mutex-locker mutex)
   thunk
   (mutex-unlocker mutex)))
@end example
@end defun

@defmac run-once expr @dots{}
@c MOD gauche.threads
@c EN
When this form is first evaluated, it evaluates @var{expr} @dots{}
returns the result(s) of the last expression.
The results are memoized, so the subsequent
evaluation of the form returns the same results without
evaluating @var{expr}s.
@c JP
最初にこのフォームが評価された時、@var{expr} @dots{}が順に評価され、
最後の式の結果(複数であることもあります)が変えされます。
結果は記憶され、以降のこのフォームの評価は@var{expr} @dots{}を評価することなく
以前の結果が直ちに返されます。
@c COMMON

@c EN
It may sound somewhat similar to @code{force} a promise,
but @code{run-once} guarantees
that only one thread ever evaluates @var{expr}s.  If more than one thread
tries to evaluate the same @code{run-once} form, the one that aquire the
lock first evaluates it, making other threads wait.  Note that @code{force}
does not prevent more than one thread to start evaluating the promise's
body simultaneously; it
only guarantees that the first delivered result becomes the value
of the promise.
@c JP
プロミスを@code{force}するのに似ていると思うかもしれません。
ただ、@code{run-once}は一つのスレッドだけが@var{exprs}を評価することを保証します。
複数のスレッドが同じ@code{ron-once}フォームを同時に評価しようとした場合、
ロックを獲得したスレッドのみが@var{expr} @dots{}の評価を行い、
他のスレッドはその結果が出るまで待たされます。
これは@code{force}と異なることに注意してください。
@code{force}は複数のスレッドが同時にプロミスの本体を評価し始めることは禁じておらず、
ただ、最初に確定した結果がプロミスの結果となることのみ保証してまいす。
@c COMMON

@c EN
If the control goes out from this form before completing evaluation,
e.g. by an error, it is unlocked and another thread may start
evaluating @var{expr}s.  If you have operations that should never
be evaluated more than once no matter what, you should use @code{guard}
or @code{unwind-protect} to make sure evaluation completes.
@c JP
制御が式の評価を全て完了する前に、エラーなどでフォームから制御が外にに移った場合、
ロックは外され、他のスレッドが@var{expr}を評価できるようになります。
何があっても二度評価してはいけない操作がある場合は、@code{guard}や
@code{unwind-protect}で適切に保護してください。
@c COMMON
@end defmac


@node Condition variable, Atom, Mutex, Synchronization primitives
@subsubsection Condition variable
@c NODE 条件変数

@deftp {Builtin Class} <condition-variable>
@clindex condition-variable
@c MOD gauche.threads
@c EN
A condition variable keeps a set of threads that are waiting for
a certain condition to be true.  When a thread modifies the state
of the concerned condition, it can call @code{condition-variable-signal!}
or @code{condition-variable-broadcast!}, which unblock one or more
waiting threads so that they can check if the condition is satisfied.
@c JP
条件変数は、ある条件が真になるのを待っているスレッドの集合を保持します。
あるスレッドがその条件を変更する時、@code{condition-variable-signal!}あるいは
@code{condition-variable-broadcast!}が呼ばれ、それは1つ以上の待機中の
スレッドのブロックを解除するため、それらのスレッドは条件が満足するかどうか
検査できます。
@c COMMON

@c EN
A condition variable object has the following slots.
@c JP
条件変数オブジェクトは以下のスロットを持ちます。
@c COMMON

@defivar <condition-variable> name
@c EN
The name of the condition variable.
@c JP
条件変数の名前。
@c COMMON
@end defivar

@defivar <condition-variable> specific
@c EN
A slot an application can keep arbitrary data.
@c JP
アプリケーションが任意のデータを保持できるスロット。
@c COMMON
@end defivar

@c EN
Note that SRFI-18 doesn't have a routine equivalent to pthreads'
@code{pthread_cont_wait}.  If you want to wait on condition variable,
you can pass a condition variable to @code{mutex-unlock!} as an
optional argument (see above), then acquire mutex again by
@code{mutex-lock!}.  This design is for flexibility; see
SRFI-18 document for the details.
@c JP
SRFI-18は、pthreadの@code{pthread_cond_wait}に相当する手続きを
持たないことに注意してください。条件変数を待つのは、
@code{mutex-unlock!}の省略可能引数に条件変数を渡し、
その後mutexを再び@code{mutex-lock!}で得ることで行います。
この設計は柔軟性のためです。詳しくはSRFI-18を参照して下さい。
@c COMMON

@c EN
This is the common usage of pthreads' condition variable:
@c JP
このような、pthreadで条件変数を使う定石は：
@c COMMON
@example
while (some_condition != TRUE) @{
  pthread_cond_wait(condition_variable, mutex);
@}
@end example
@c EN
And it can be translated to SRFI-18 as follows:
@c JP
SRFI-18では次のようなコードになります。
@c COMMON
@example
(let loop ()
  (unless some-condition
    (mutex-unlock! mutex condition-variable)
    (mutex-lock! mutex)
    (loop)))
@end example
@end deftp

@defun condition-variable? obj
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is a condition variable,
@code{#f} otherwise.
@c JP
@var{obj}が条件変数なら@code{#t}、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun make-condition-variable :optional name
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns a new condition variable.  You can give its name by
optional @var{name} argument.
@c JP
新しい条件変数を返します。オプショナル引数@var{name}で
その名前を与えることができます。
@c COMMON
@end defun

@defun condition-variable-name cv
[SRFI-18], [SRFI-21]
@c MOD gauche.threads
@c EN
Returns the name of the condition variable.
@c JP
条件変数の名前を返します。
@c COMMON
@end defun

@defun condition-variable-specific cv
@defunx condition-variable-specific-set! cv value
[SRFI-18]、[SRFI-21]
@c MOD gauche.threads
@c EN
Gets/sets the specific value of the condition variable.
@c JP
条件変数の固有の値を取得/セットします。
@c COMMON
@end defun

@defun condition-variable-signal! cv
[SRFI-18]、[SRFI-21]
@c MOD gauche.threads
@c EN
If there are threads waiting on @var{cv}, causes the scheduler to select
one of them and to make it runnable.
@c JP
@var{cv}で待機しているスレッドがある場合は、それらのうちの1つがスケジューラに
より選択され、実行可能にされます。
@c COMMON
@end defun

@defun condition-variable-broadcast! cv
[SRFI-18]、[SRFI-21]
@c MOD gauche.threads
@c EN
Unblocks all the threads waiting on @var{cv}.
@c JP
@var{cv}で待機している全てのスレッドのブロックを解除します。
@c COMMON
@end defun

@node Atom, Semaphore, Condition variable, Synchronization primitives
@subsubsection Atom
@c NODE アトム

@c EN
An atom is a convenient wrapper to make operations on a
given set of objects thread-safe.  Instead of defining
thread-safe counterparts of every structure, you can easily
wrap an existing data structures to make it thread-safe.
@c JP
アトムはオブジェクトの集まりをスレッドセーフに簡単に扱うことができるラッパーです。
それぞれの構造に対応するスレッドセーフ版を作るかわりに、
既にあるいくつかのデータをまとめて包んでスレッドセーフにできます。
@c COMMON

@defun atom val @dots{}
@c MOD gauche.threads
@c EN
Creates and returns an atom object with @var{val} @dots{} as the
initial values.
@c JP
@var{val} @dots{}を初期値に持つアトムオブジェクトを作って返します。
@c COMMON
@end defun

@defun atom? obj
@c MOD gauche.threads
@c EN
Returns @code{#t} iff @var{obj} is an atom.
@c JP
@var{obj}がアトムなら@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@c EN
The following procedures can be used to @emph{atomically}
access and update the content of an atom.   They commonly
take optional @var{timeout} and @var{timeout-val} arguments,
both are defaulted to @code{#f}.  In some cases, the procedure
takes more than one @var{timeout-val} arguments.
With the default value @code{#f} as @var{timeout} argument,
those procedures blocks until they acquire a lock.
@c JP
以下の手続きは、アトムの中身に@emph{アトミック}にアクセスしたり、
それをアップデートするのに使えます。共通する省略可能引数として、
@var{timeout}と@var{timeout-val}を取ります。
これらのデフォルト値は@code{#f}です。手続きによっては一つ以上の@var{timeout-val}
を取ることがあります。
@var{timeout}引数がデフォルト値@code{#f}であれば、
以下の手続きはロックが得られるまでブロックします。
@c COMMON

@c EN
The timeout arguments can be used to modify the behavior when
the lock cannot be acquired in timely manner.
@var{timeout} may be a @code{<time>} object (@pxref{Time})
to specify an absolute point of time, or a real number
to specify the relative time in seconds.  If timeout is
expired, those procedures give up acquiring the lock,
and the value given to @var{timeout-val} is returned.
In @code{atomic} and @code{atomic-update!}, you can make them return
multiple timeout values, by giving
more than one @var{timeout-val} arguments.
@c JP
@var{timeout}引数はすぐにロックが得られなかった場合の動作を変更します。
@var{timeout}引数には、絶対的な時刻を指定する@code{<time>}オブジェクト
(@ref{Time}参照)か、相対的な時刻を秒数で指定する実数を渡すことができます。
指定された時刻が過ぎたら、以下の手続きはロックを獲得するのを諦めて、
@var{timeout-val}に指定された値を返します。
@code{atomic}と@code{atomic-update!}は一つ以上の値を返し得るので、
一つ以上の@var{timeout-val}を渡せます。
@c COMMON

@defun atom-ref atom :optional index timeout timeout-val
@c MOD gauche.threads
@c EN
Returns @var{index}-th value of @var{atom}.
See above for @var{timeout} and @var{timeout-val} arguments.
@c JP
アトム@var{atom}の@var{index}番目の値を返します。
@var{timeout}と@var{timeout-val}については上記参照。
@c COMMON

@example
(define a (atom 'a 'b))

(atom-ref a 0) @result{} a
(atom-ref a 1) @result{} b
@end example
@end defun

@defun atomic atom proc :optional timeout timeout-val timeout-val2 @dots{}
@c MOD gauche.threads
@c EN
Calls @var{proc} with the current values in @var{atom},
while locking @var{atom}.  @var{proc} must take
as many arguments as the number of values @var{atom} has.
@c JP
@var{atom}をロックして、@var{proc}を現在の@var{atom}の値に適用します。
@var{proc}は@var{atom}の値の数だけの引数を取ることができなければなりません。
@c COMMON

@c EN
The returned value(s) of @var{proc} is the result of
@code{atomic}, unless timeout occurs.
See above for @var{timeout} and @var{timeout-val} arguments.
@c JP
タイムアウトが起こらない限り、@var{proc}が返した値が@code{atomic}の返り値となります。
@var{timeout}と@var{timeout-val}については上記参照。
@c COMMON

@c EN
For example, the @code{ref/count} procedure
in the following example counts the number of times
the hashtable is referenced in thread-safe way.
@c JP
例えば次の@code{ref/count}は、
ハッシュテーブルが参照された回数を数えるスレッドセーフな手続きです。
@c COMMON

@example
(define a (atom (make-hash-table 'eq?) (list 0)))

(define (ref/count a key)
  (atomic a
   (lambda (ht count-cell)
     (inc! (car count-cell))
     (hash-table-get h key))))
@end example
@end defun

@defun atomic-update! atom proc :optional timeout timeout-val timeout-val2 @dots{}
@c MOD gauche.threads
@c EN
Calls @var{proc} with the current values in @var{atom}
while locking @var{atom}, and updates the values in @var{atom}
by the returned values from @var{proc}.
@var{proc} must take as many arguments as the number of
values @var{atom} has, and must return the at least the same number of
values.  If @var{proc} returns more than the number of values @var{atom}
holds, the extra values are not used to update the @var{atom}, but
is included in the return values of @code{atomic-update!}.
@c JP
@var{atom}をロックして、その値を引数として@var{proc}を呼び、
@var{proc}の戻り値を@var{atom}の新たな値とします。
@var{proc}は@var{atom}の値の数だけ引数を取らねばならず、
また@var{atom}の値の数以上の戻り値を返さねばなりません。
@var{proc}が@var{atom}の値の数以上の値を返した場合、
余分な値は@var{atom}を更新するのには使われませんが、
@code{atomic-update!}の結果には含まれます。
@c COMMON

@c EN
The returned value(s) of @code{atomic-update!} is what
@var{proc} returns, unless timeout occurs.
See above for @var{timeout} and @var{timeout-val} arguments.
@c JP
@code{atomic-update!}の戻り値は、タイムアウトが起こらなければ@var{proc}の戻り値です。
@var{timeout}と@var{timeout-val}については上記参照。
@c COMMON

@c EN
The following example shows a thread-safe counter.
@c JP
下はスレッドセーフなカウンタです。
@c COMMON

@example
(define a (atom 0))

(atomic-update! a (cut + 1 <>))
@end example
@end defun

@c EN
Note: The term @emph{atom} in historical Lisps
meant an object that is not a cons cell (pair).  Back then
cons cells were the only aggregate datatype and there were
few other datatypes (numbers and symbols), so having a
complementary term to cells made sense.
@c JP
@emph{atom}は古のLispでは「コンスセル(ペア)でないもの」を指していました。
当時、コンスセルは唯一の複合型であり、他の型もごくわずか(数値とシンボル)だったので、
セルでないものを指すことには意味がありました。
@c COMMON

@c EN
Although it still appears in introductory Lisp tutorials,
modern Lisps, including Scheme, has so many datatypes and it makes
little sense to have a specific term for non-pair types.
@c JP
今でもatomはLispのチュートリアルで目にすることがありますが、
Schemeをはじめ現代のLispではたくさんのデータ型があり、
コンスセル以外をひとまとめにする用語を使う意味がほとんどありません。
@c COMMON

@c EN
Clojure adopted the term @emph{atom} for thread-safe (atomic)
primitive data, and we followed it.
@c JP
Clojureはatomをスレッドセーフ(アトミック)な基本データに使ったので、
Gaucheもそれに倣うことにしました。
@c COMMON

@c EN
Note: The constructor of atom is not @code{make-atom}
but @code{atom}, following the convention of @code{list}/@code{make-list},
@code{vector}/@code{make-vector}, and @code{string}/@code{make-string};
that is, the name without @code{make-} takes its elements as
variable number of arguments.
@c JP
註: コンストラクタが@code{make-atom}ではなく@code{atom}なのは、
@code{list}/@code{make-list}、@code{vector}/@code{make-vector}、
@code{string}/@code{make-string}などの慣習に従っています。
つまり、@code{make-}のない手続きは、各要素を可変長引数の形で取ります。
@c COMMON

@node Semaphore, Latch, Atom, Synchronization primitives
@subsubsection Semaphore
@c NODE セマフォ

@deftp {Builtin Class} <semaphore>
@clindex semaphore
@c MOD gauche.threads
@c EN
A semaphore manages ``tokens'' for a fixed number of resources.
A thread that wants to use one of the resources requests a token
by @code{semaphore-acquire!}, and returns the token to the pool
by @code{semaphore-release!}.  When the thread requests a token
but none is available, it waits until a token becomes available
by some other thread returning one.
@c JP
セマフォは、決まった数のリソースを使うための「トークン」を管理します。
リソースを使いたいスレッドは@code{semaphore-acquire!}を呼びトークンを獲得します。
リソースを使い終わったら@code{semaphore-release!}でトークンを返します。
スレッドがトークンを要求した時点でトークンが余っていなければ、他のスレッドがトークンを返す
まで待ちます。
@c COMMON
@end deftp

@defun make-semaphore :optional init-value name
@c MOD gauche.threads
@c EN
Creates and returns a new semaphore, with @var{init-value} tokens
available initially.  If @var{init-value} is omitted, 0 is assumed.
Another optional argument @var{name} is an arbitrary Scheme object
and only used for a debugging purpose only; it is displayed
when a semaphore is printed.
@c JP
新たなセマフォを作って返します。@var{init-value}は初期段階で使えるトークンの数を
指定します。省略された場合は0になります。
もう一つの省略可能引数@var{name}は任意のSchemeオブジェクトで、
セマフォの表示にのみ使われます。
@c COMMON
@end defun

@defun semaphore? obj
@c MOD gauche.threads
@c EN
Returns @code{#t} iff @var{obj} is a semaphore.
@c JP
@var{obj}がセマフォなら@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun semaphore-acquire! sem :optional timeout timeout-val
@c MOD gauche.threads
@c EN
Obtain a token from a semaphore @var{sem}.
If a token is available, this returns @code{#t} immediately,
decrementing the available token count of @var{sem} atomically.
If no token is available, this waits until a token becomes
avaialble, or @var{timeout} reaches if it is given.  If timeout
occurs, it returns @var{timeout-val}, defaulted to @code{#f}.
@c JP
セマフォ@var{sem}からトークンを獲得します。トークンがあれば、
トークンの残り数をデクリメントして、直ちに@code{#t}を返します。
もしトークンが余ってなければ、新たなトークンが返却されるか、
@var{timeout}が指定するタイムアウトまで待ちます。
タイムアウトした場合は@var{timeout-val}が返されます。@var{timeout-val}の
デフォルトは@code{#f}です。
@c COMMON

@c EN
The value of @var{timeout} is the same as @code{mutex}; it can be
@code{#f} (no timeout, default), a @code{<time>} object to specify an absolute
point of time, or a real number to specify the minimum number of seconds
to wait.
@c JP
@var{timeout}に渡せる値は@var{mutex}と同じで、
@code{#f} (タイムアウトなし。デフォルト値)、
絶対的な時刻を指定する@code{<time>}オブジェクト、
あるいは現在からの秒数を相対的に指定する実数です。
@c COMMON
@end defun

@defun semaphore-release! sem :optional count
@c MOD gauche.threads
@c EN
Return a token to a semaphore @var{sem}, by incrementing its token count,
and running one of the threads waiting with @code{semaphore-acquire!} atomically.
@c JP
トークンをセマフォ@var{sem}に返却します。@var{sem}のトークン数をインクリメントするのと
同時に、@var{semaphore-acquire!}で待っているスレッドのひとつを走らせます。
@c COMMON

@c EN
The @var{count} argument specifies number of tokens to return, defaulted to 1.
@c JP
@var{count}引数で返却するトークンの数を指定できます。デフォルトは1です。
@c COMMON

@c EN
Actually, the ``token'' model is to make it easier to understand the
idea of semaphore, but internally it's just a counter, so you can
call @code{semaphore-release!} even you haven't called @code{semaphore-acuqire!}.
@c JP
実のところ、「トークン」と読んでいるのはセマフォのモデルを理解しやすくするためで、
内部的には単なるカウンタにすぎません。なので
@code{semaphore-acuqire!}を呼んでいなくても@code{semaphore-release!}でトークンを追加
することができます。
@c COMMON
@end defun


@node Latch, Barrier, Semaphore, Synchronization primitives
@subsubsection Latch
@c NODE ラッチ

@deftp {Builtin Class} <latch>
@clindex latch
@c MOD gauche.threads
@c EN
A latch is a synchornization device with a counter.
Any number of threads can wait until the counter becomes zero.
Once the counter reaches zero, all threads go.
(As opposed to semaphores, whose internal counter affects
number of waiting threads as well.)
@c JP
ラッチはカウンタを内部に持つ同期デバイスです。
カウンタが0になるまで、スレッドはいくつでも待ちます。
カウンタが0になった途端、全てのスレッドが走ります。
(セマフォでは、内部のカウンタは待つスレッドの数にも影響しますが、
ラッチではカウンタと待つスレッドの数は無関係です)。
@c COMMON

@c EN
One simple usage is to start with initial count 1; it is sometimes
called a ``gate''.  You can let threads wait before the gate, and
decrement the counter, then boom!  All threads proceeds.
@c JP
最も単純な用途では、初期カウントを1から始めます。これはしばしば「ゲート」と呼ばれます。
待つスレッドはゲートに達したらそこで停止し、ひとたびカウンタをデクリメントしたら、
全てのスレッドがそこから走り始めます。
@c COMMON
@end deftp

@defun make-latch initial-count :optional name
@c MOD gauche.threads
@c EN
Creates and returns a new latch with the counter value @var{initial-count},
which must be an exact positive integer.
@c JP
カウンタの初期値として@var{initial-count}を持つラッチを作って返します。
@var{initial-count}は正確な正整数でなければなりません。
@c COMMON

@c EN
The optional @var{name} argument can be any Scheme object, and
used only for debugging.  It is displayed when the latch object
is printed.
@c JP
省略可能な@var{name}引数は任意のSchemeオブジェクトで、
ラッチを表示する時にのみ使われます。
@c COMMON
@end defun

@defun latch? obj
@c MOD gauche.threads
@c EN
Returns @code{#t} iff @var{obj} is a latch.
@c JP
@var{obj}がラッチなら@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun latch-dec! latch :optional n
@c MOD gauche.threads
@c EN
Decrement the counter of @var{latch} by @var{n}.
If @var{n} is omitted, 1 is assumed.

If the value of the latch becomes 0 or less, threads waiting on the
latch are woken up.

Returns the updated counter value.
@c JP
ラッチのカウンタを@var{n}だけ減らします。@var{n}が省略されたら1を使います。

カウンタの値が0以下になったら、ラッチで待っているスレッドを起こします。

更新後のカウンタの値を返します。
@c COMMON

@c EN
@var{N} must be an exact integer.  Zero or negative value is allowed.
@c JP
@var{n}は正確な整数でなければなりません。0や負の値も許されます。
@c COMMON
@end defun

@defun latch-clear! latch
@c MOD gauche.threads
@c EN
If @var{latch}'s count was non-zero, make it zero and wakes up
the threads waiting on it.
If @var{latch}'s count has already been zero, do nothing.

Returns the previous count.
@c JP
@var{latch}のカウンタが0でなければ、それを0にし、待っているスレッドを起こします。
既に0であれば何もしません。

0にする前のカウンタの値を返します。
@c COMMON
@end defun

@defun latch-await latch :optional timeout timeout-val
@c MOD gauche.threads
@c EN
If the counter of @var{latch} is zero or negative, returns @code{#t}
immeiately.  Otherwise, the calling thread is blocked until
the counter value becomes zero or below, or timeout reaches.
If the thread started by the counter value, @code{#t} is returned.
If the thread started by timeout, @var{timeout-val} is returned,
whose default is @code{#f}.
@c JP
ラッチ@var{latch}のカウンタが0以下なら直ちに@code{#t}を返します。
そうでなければ、呼び出しスレッドはカウンタが0以下になるか、タイムアウトするまで
ブロックされます。カウンタによりスレッドが再開された場合は@code{#t}が、
タイムアウトした場合は@var{timeout-val}が返されます。
@var{timeout-val}のデフォルトは@code{#f}です。
@c COMMON

@c EN
The @var{timeout} argument must be either @code{#f} (no timeout, default),
a @code{<time>} object (absolute point of time), or a real number
indicates number of seconds from the time this procedure is called.
@c JP
@var{timeout}引数は、
@code{#f} (タイムアウトなし。デフォルト値)、
絶対的な時刻を指定する@code{<time>}オブジェクト、
あるいは現在からの秒数を相対的に指定する実数です。
@c COMMON
@end defun

@node Barrier,  , Latch, Synchronization primitives
@subsubsection Barrier
@c NODE バリア

@deftp {Builtin Class} <barrier>
@clindex barrier
@c MOD gauche.threads
@c EN
A barrier is a synchronization primitive that multiple threads
wait by @code{barrier-await}
until a specified number of threads reach the point.
Once the specified number of threads get to the barrier,
all threads go, and the barrier automatically returns to the initial
state; the next thread that comes to the barrier waits again.
@c JP
バリアは、指定された個数のスレッドが待ち状態になるまで待ち合わせる
同期プリミティブです。
@code{barrier-await}を呼んだスレッドが指定の個数に達したら、
全てのスレッドが再開し、バリアは初期状態に戻ります。
次にバリアに到達したスレッドは再び待ちに入ります。
@c COMMON

@c EN
A barrier can have an optional @emph{action}, which is run by the
last thread that reached to the barrier before everyone goes.
@c JP
バリアは「アクション」を持つことができます。アクションは、待ち合わせスレッドが
しきい値に到達した時に、他のスレッドが走り出す前に実行されます。
@c COMMON

@c EN
A barrier can be in a ``broken'' state when any one of the threads
timeout, or the action raises an uncaptured exception.  Once the barrier
is broken, all threads waiting on it is released as if timeout has
occured.  The broken barrier remains broken (so any thread that reaches
it just passes through) until it is reset by @code{barrier-reset!}.
@c JP
待っているスレッドのいずれかがタイムアウトするか、アクションで捕捉されない例外が
投げられた場合、バリアは「破れた」状態になります。
バリアが壊れると、待っていたスレッドはあたかもタイムアウトが起きたかのように
再開されます。破れた状態は@code{barrier-reset!}で明示的にリセットされるまで
保たれ、その間にバリアに到達したスレッドはあたかも0のタイムアウトが指定されたかのように
そのまま素通りします。
@c COMMON
@end deftp

@defun make-barrier threshold :optional action name
@c MOD gauche.threads
@c EN
Craetes and returns a new barrier.  The @var{threshold} argument
must be an exact nonnegative integer to specify the number of threads
to let them go---threads calling @code{barrier-await} waits until
the number of threads waiting reaches @var{threshold}.
@c JP
新しいバリアを作って返します。@var{threshold}は正確な非負整数でなければならず、
待ち合わせるスレッドの数を指定します。@code{barrier-await}を
呼んだスレッドがこの数に達した時に、それら全てのスレッドで
@code{barrier-await}から制御が戻ります。
@c COMMON

@c EN
The optional @var{action} argument must be either @code{#f} (no action)
or a thunk.  If it is a thunk, it is run by the last thread
that calls @code{barrier-await}, before all the thread will go.
@c JP
省略可能な@var{action}引数は@code{#f}(アクションなし)かサンクでなければなりません。
サンクの場合、それはバリアが開放される前の最後に@code{barrier-await}を呼んだ
スレッドによって、他のスレッドが走り始める前に実行されます。
@c COMMON

@c EN
The optional @var{name} argument can be any Scheme object,
and only used to print the barrier instance, to help debugging.
@c JP
@var{name}引数は任意のSchemeオブジェクトで、バリアを表示する際にのみ使われます。
@c COMMON
@end defun

@defun barrier? obj
@c MOD gauche.threads
@c EN
Returns @code{#t} iff @var{obj} is a barrier.
@c JP
@var{obj}がバリアなら@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun barrier-await barrier :optional timeout timeout-val
@c MOD gauche.threads
@c EN
Waits on @var{barrier} until the number of waiting threads reaches
the threshold of the barrier, or the barrier is broken.
@c JP
@var{barrier}で待っているスレッドが閾値に達するか、バリアが破れるまで、
呼び出したスレッドを待たせます。
@c COMMON

@c EN
A barrier can be broken if any of waiting threads hit the timeout,
or an uncaptured exception is raised from the action thunk of the barrier.
@c JP
バリアが破れるのは、待っているスレッドのどれかがタイムアウトするか、
バリアのアクションから例外が投げられた時です。
@c COMMON

@c EN
The @var{timeout} and @var{timeout-val} are the same as other synchronization
primitives; @var{timeout} may be @code{#f} (no timeout, default),
a @code{<time>} object
to specify an absolute time point, or a real number indicating relative
time in number of seconds; @var{timeout-val} is the value returned
when @code{barrier-await} returns prematurely---either timeout, or
other barrier breakage conditions.
The default of @var{timeout-val} is @code{#f}.
@c JP
@var{timeout}と@var{timeout-val}引数は他の同期プリミティブと同じです。
@var{timeout}は@code{#t} (タイムアウトなし、デフォルト)か、
絶対的時刻を指定する@code{<time>}オブジェクトか、
相対的な秒数を指定する実数です。
@var{timeout-val}は@code{barrier-await}がタイムアウトかバリア破れで
戻る場合に返される値で、デフォルトは@code{#f}です。
@c COMMON

@c EN
It returns an integer if the thread is released by reaching the threshold,
or @var{timeout-val} if the barrier is broken.  The integer indicates
the number of threads required to reach the threshold at the time
@code{barrier-wait} is called; that is, if you're the first to reach
the barrier it is threshold - 1, and if you're the last it is 0.
@c JP
この手続きの戻り値は、待ちスレッド数が閾値に達して戻った場合は正確な整数、
バリアが破れた場合は@var{timeout-val}です。
正確な整数は、@code{barrier-await}を呼び出した時点であといくつ待ちスレッドが
必要だったかを示します。つまり、最初にバリアに到達したスレッドなら @code{threshold - 1}、
最後に到達したなら0です。
@c COMMON

@c EN
If the barrier is already broken when you call @code{barrier-await},
it returns immediately with @var{timeout-val}.
@c JP
@code{barrier-await}を呼んだ時点で既にバリアが破れていたら、
直ちに@var{timeout-val}が返されます。
@c COMMON

@c EN
If the threads are released normally, the barrier turns back to the
initial state so you can wait on it again.  If the threads are released
because the barrier is broken, it remains in broken state until
reset by @code{barrier-reset!}.
@c JP
スレッド数が閾値に達して全スレッドを解放した場合は、
バリアは初期状態に戻ります。つまり、次に@code{barrier-await}を呼んだスレッドは
再び待たされることになります。
バリアが破れたば場合、@code{barrier-reset!}が呼ばれるまでバリアはずっと破れた
状態のままになります。
@c COMMON
@end defun

@defun barrier-broken? barrier
@c MOD gauche.threads
@c EN
Returns @code{#t} iff @var{barrier} is in broken state.
@c JP
バリア@var{barrier}が破れた状態なら@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun barrier-reset! barrier
@c MOD gauche.threads
@c EN
Resets the barrier to the initial state.  If the barrire is broken,
the broken state is cleared.  If any thread is waiting on the barrier,
it is released as if the number of threads reaches the threshold.
@c JP
バリアを初期状態にリセットします。バリアが破れた状態なら、破れていない状態に戻ります。
バリアで待っているスレッドがいた場合、それはあたかもスレッド数が閾値に達したかのように
解放されます。
@c COMMON
@end defun


@node Thread exceptions,  , Synchronization primitives, Threads
@subsection Thread exceptions
@c NODE スレッド例外

@c EN
Some types of exceptions may be thrown from thread-related procedures.
These exceptions can be handled by Gauche's exception mechanism
(@pxref{Exceptions}).
@c JP
例外のいくつかのタイプは、スレッド関連の手続きから投げられます。
これらの例外は、Gaucheの例外メカニズム(@ref{Exceptions}参照)により
扱われます。
@c COMMON

@c EN
These are originally defined in SRFI-18.  SRFI-226 follows them,
but uses slightly different names for the consistency with
modern Scheme.  We support both.
@c JP
これらは元々SRFI-18で定義されました。SRFI-226もそれに倣いましたが、
名前については現代的なSchemeの名前付けを意識したものに変えています。
Gaucheではどちらの名前もサポートします。
@c COMMON

@deftp {Builtin Class} <thread-exception>
@deftpx {Condition Type} &thread
@clindex thread-exception
@vrindex &thread
[SRFI-226]
@c MOD gauche.threads
@c EN
A base class of thread-related exceptions.  Inherits @code{<exception>} class.
It has one slot.
@c JP
スレッド関連の例外の基底クラスです。@code{<exception>}クラスを継承しています。
スロットを1つ持っています。
@c COMMON

@defivar <thread-exception> thread
@c EN
A thread that threw this exception.
@c JP
この例外を投げたスレッド。
@c COMMON
@end defivar

@c EN
The name @code{&thread} is defined by SRFI-226.  Note that SRFI-226
does not define @code{thread} slot; it's Gauche's extension.
@c JP
@code{&thread}というコンディション名はSRFI-226での定義です。
ただし、SRFI-226のコンディションは@code{thread}スロットは規定していません。
@c COMMON
@end deftp

@deftp {Builtin Class} <join-timeout-exception>
@deftpx {Condition Type} &thread-timeout
@clindex join-timeout-exception
@vrindex &thread-timeout
[SRFI-226]
@c MOD gauche.threads
@c EN
An exception thrown by @code{thread-join!} when a timeout reaches
before the waited thread returns.  Inherits @code{<thread-exception>}.
@c JP
待機していたスレッドが戻る前にタイムアウトに達した時に@code{thread-join!}によって
投げられる例外。@code{<thread-exception>}を継承しています。
@c COMMON

@c EN
The name @code{&thread-timeout} is defined by SRFI-226.
@c JP
@code{&thread-timeout}という名前はSRFI-226で定義されています。
@c COMMON
@end deftp

@deftp {Builtin Class} <abandoned-mutex-exception>
@deftpx {Condition Type} &thread-abandoned-mutex
@clindex abandoned-mutex-exception
@vrindex &thread-abandoned-mutex
[SRFI-226]
@c MOD gauche.threads
@c EN
An exception thrown by @code{mutex-lock!} when a @var{mutex} to be
locked is in unlocked/abandoned state.  Inherits @code{<thread-exception>}.
It has one additional slot.
@c JP
ロックされる@var{mutex}が、unlocked/abandoned(ロックされておらず、放棄された状態)
であるときに@code{mutex-lock!}により投げられる例外。
@code{<thread-exception>}を継承しています。スロットを1つ持ちます。
@c COMMON

@defivar <abandoned-mutex-exception> mutex
@c EN
A mutex that caused this exception.
@c JP
この例外の原因となったmutex。
@c COMMON
@end defivar

@c EN
The name @code{&thread-abandoned-mutex} is defined by SRFI-226.
@c JP
@code{&thread-abandoned-mutex}という名前はSRFI-226で定義されています。
@c COMMON
@end deftp

@deftp {Builtin Class} <terminated-thread-exception>
@deftpx {Condition Type} &thread-already-terminated
@clindex terminated-thread-exception
@vrindex &thread-already-terminated
[SRFI-226]
@c MOD gauche.threads
@c EN
An exception thrown by @code{thread-join!} when the waited thread
is terminated abnormally (by @code{thread-terminate!}).
Inherits @code{<thread-exception>}.  It has one additional slot.
@c JP
待機していたスレッドが(@code{thread-terminate!}により)異常終了した
場合に(@code{thread-join!}により)投げられる例外。
@code{<thread-exception>}を継承し、スロットを1つ持ちます。
@c COMMON

@defivar <terminated-thread-exception> terminator
@c EN
A thread that terminated the thread that causes this exception.
@c JP
この例外の原因となったスレッドを終了したスレッド。
@c COMMON
@end defivar

@c EN
The name @code{&thread-already-terminated} is defined by SRFI-226.
SRFI-226 doesn't define @code{terminator} slot, though.
@c JP
@code{&thread-abandoned-mutex}という名前はSRFI-226で定義されています。
ただし、SRFI-226は@code{terminator}スロットは定義していません。
@c COMMON
@end deftp

@deftp {Builtin Class} <uncaught-exception>
@deftpx {Condition Type} &uncaught-exception
@clindex uncaught-exception
@vrindex &uncaught-exception
[SRFI-226]
@c MOD gauche.threads
@c EN
An exception thrown by @code{thread-join!} when the waited thread
is terminated by an uncaught exception.
Inherits @code{<thread-exception>}.  It has one additional slot.
@c JP
待機していたスレッドが捕捉されない例外により終了された場合に
@code{thread-join!}により投げられる例外。
@code{<thread-exception>}を継承し、スロットを1つ持ちます。
@c COMMON

@defivar <uncaught-exception> reason
@c EN
An exception that caused the termination of the thread.
@c JP
そのスレッドの終了の原因となった例外。
@c COMMON
@end defivar

@c EN
The name @code{&uncaught-exception} is defined by SRFI-226.
@c JP
@code{&uncaught-exception}という名前はSRFI-226で定義されています。
@c COMMON
@end deftp

@deftp {Builtin Class} <concurrent-modification-violation>
@deftpx {Condition Type} &concurrent-modification
@clindex concurrent-modification-violation
@vrindex &concurrent-modification
[SRFI-226]
@c EN
This is a condition thrown when the runtime detects non-thread-safe
data is being modified by multiple threads concurrently.
SRFI-226 defines this, but it allows implementations not to detect
this situation if it's costly.  Currently, no Gauche APIs detect
this condition, though it may do so in future.  For now, this is
provided for the compatibility with SRFI-226.
@c JP
これはスレッドセーフでないデータを複数スレッドで同時に変更しようとした場合に
投げられるコンディションです。SRFI-226で定義されていますが、
SRFIはこの状況を検出するのにオーバヘッドがある場合は検出しなくても良いとしています。
今のところ、GaucheのAPIでこのコンディションを検出するものはありません。
将来はできるかもしれません。今はこれはSRFI-226との互換性のためのみで提供されています。
@c COMMON
@end deftp

@defun make-thread-condition
[SRFI-226]
@c MOD gauche.threads
@c EN
Creates a new @code{<thread-exception>} condition.  This is for SRFI-226
compatibility.  Usually you don't need to use this directly, for
the actual condition is of a subclass of @code{<thread-exception>}.
The @code{thread} slot is initialized with the calling thread.
@c JP
新しい@code{<thread-exception>}コンディションを作ります。
これはSRFI-226との互換のために用意されていますが、直接使う必要はほとんどないでしょう。
実際には@code{<thread-exception>}のサブクラスのコンディションが使われるからです。
コンディションの@code{thread}スロットは呼び出したスレッドで初期化されます。
@c COMMON
@end defun

@defun thread-condition? obj
[SRFI-226]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is a @code{<thread-exception>}
(@code{&thread}) condition,
@code{#f} otherwise.
@c JP
@var{obj}が@code{<thread-exception>}
(@code{&thread})コンディションなら@code{#t}を、
そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun make-thread-timeout-condition
[SRFI-226]
@c MOD gauche.threads
@c EN
Creates a new @code{<join-timeout-exception>} (@code{&thread-timeout}) condition.
@c JP
新たな@code{<join-timeout-exception>} (@code{&thread-timeout})コンディション
を作ります。
@c COMMON
@end defun

@defun join-timeout-exception? obj
@defunx thread-timeout-condition? obj
[SRFI-18], [SRFI-21], [SRFI-226]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is a
@code{<join-timeout-exception>} (@code{&thread-timeout}) condition,
@code{#f} otherwise.
The name @code{join-timeout-exception?} is defined by SRFI-18/21,
and @code{thread-timeout-condition?} is by SRFI-226. They are the same.
@c JP
@var{obj}が@code{<join-timeout-exception>} (@code{&thread-timeout})
コンディションなら@code{#t}を、
そうでなければ@code{#f}を返します。
@code{join-timeout-exception?}はSRFI-18/21で、
@code{thread-timeout-condition?}はSRFI-226で定義された名前です。どちらも同じです。
@c COMMON
@end defun

@defun make-thread-abandoned-mutex
[SRFI-226]
@c MOD gauche.threads
@c EN
Creates a new @code{<abandoned-mutex-exception>}
(@code{&thread-abandoned-mutex}) condition.
@c JP
新たな@code{<abandoned-mutex-exception>}
(@code{&thread-abandoned-mutex})コンディションを作ります。
@c COMMON
@end defun

@defun abandoned-mutex-exception? obj
@defunx thread-abandoned-mutex-condition? obj
[SRFI-18], [SRFI-21], [SRFI-226]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is a
@code{<abandoned-mutex-exception>} (), @code{#f} otherwise.
The name @code{abandoned-mutex-exception?} is defined by SRFI-18/21,
and @code{thread-abandoned-mutex-condition?} is by SRFI-226. They are the same.
@c JP
@var{obj}が@code{<abandoned-mutex-exception>}のインスタンスなら@code{#t}を、
そうでなければ@code{#f}を返します。
@code{abandoned-mutex-exception?}はSRFI-18/21で、
@code{thread-abandoned-mutex-condition?}はSRFI-226で定義された名前です。どちらも同じです。
@end defun

@defun make-thread-already-terminated-condition
[SRFI-226]
@c MOD gauche.threads
@c EN
Creates a new @code{<terminated-thread-exception>}
(@code{&thread-already-terminated}) condition.
@c JP
新たな@code{<termianted-thread-exception>}
(@code{&thread-already-terminated})コンディションを作ります。
@c COMMON
@end defun

@defun terminated-thread-exception? obj
@defunx thread-already-terminated-condition? obj
[SRFI-18], [SRFI-21], [SRFI-226]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is an instance of
@code{<terminated-thread-exception>}, @code{#f} otherwise.
The name @code{terminated-thread-exception?} is defined by SRFI-18/21,
and @code{thread-already-terminated-condition?} is by SRFI-226. They are the same.
@c JP
@var{obj}が@code{<terminated-thread-exception>}のインスタンスなら@code{#t}を、
そうでなければ@code{#f}を返します。
@code{terminated-thread-exception?}はSRFI-18/21で、
@code{thread-already-termianted-condition?}はSRFI-226で定義された名前です。どちらも同じです。
@end defun

@defun make-uncaught-exception-condition reason
[SRFI-226]
@c MOD gauche.threads
@c EN
Creates a new @code{<uncaught-exception>}
(@code{&uncaught-exception}) condition.
The argument is set to the @code{reason} slot of the condition.
@c JP
新たな@code{<uncaught-exception>}
(@code{&uncaught-exception})コンディションを作ります。
引数はコンディションの@code{reason}スロットに保持されます。
@c COMMON
@end defun

@defun uncaught-exception? obj
@defunx uncaught-exception-condition? obj
[SRFI-18], [SRFI-21], [SRFI-226]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is an instance of
@code{<uncaught-exception>}, @code{#f} otherwise.
The name @code{uncaught-exception?} is defined by SRFI-18/21,
and @code{uncaught-exception-condition?} is by SRFI-226. They are the same.
@c JP
@var{obj}が@code{<uncaught-exception>}のインスタンスなら@code{#t}を、
そうでなければ@code{#f}を返します。
@code{uncaught-exception?}はSRFI-18/21で、
@code{uncaught-exception-condition?}はSRFI-226で定義された名前です。どちらも同じです。
@end defun

@defun uncaught-exception-reason exc
@defunx uncaught-exception-condition-reason exc
[SRFI-18], [SRFI-21], [SRFI-226]
@c MOD gauche.threads
@c EN
Returns the value of @code{reason} slot of @code{<uncaught-exception>}
object.
@c JP
@code{<uncaught-exception>}オブジェクトの@code{reason}スロットの値を
返します。
@c COMMON

@c EN
The name @code{uncaught-exception-reason} is defined in
SRFI-18/21, and @code{uncaught-exception-condition-reason} is
defined in SRFI-226.  Both works the same.
@c JP
@code{uncaught-exception-reason}はSRFI-18/21で、
@code{uncaught-exception-condition-reason}はSRFI-226で定義された名前です。
どちらも同じ動作です。
@c COMMON
@end defun

@defun make-concurrent-modification-violation
[SRFI-226]
@c MOD gauche.threads
@c EN
Creates a new @code{<concurrent-modification-violation>}
(@code{&concurrent-modification}) condition.
@c JP
新たな@code{<concurrent-modification-violation>}
(@code{&concurrent-modification})コンディションを作ります。
@c COMMON
@end defun

@defun concurrent-modification-violation? obj
[SRFI-226]
@c MOD gauche.threads
@c EN
Returns @code{#t} if @var{obj} is a
@code{<concurrent-modification-violation>}
(@code{&concurrent-modification}) condition, @code{#f} otherwise.
@c JP
@var{obj}が@code{<concurrent-modification-violation}
(@code{&concurrent-modification})コンディションなら@code{#t}を、
そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@c ----------------------------------------------------------------------
@node Measure timings, Unicode utilities, Threads, Library modules - Gauche extensions
@section @code{gauche.time} - Measure timings
@c NODE 時間の計測, @code{gauche.time} - 時間の計測

@deftp {Module} gauche.time
@mdindex gauche.time
@c EN
Provides three ways to measure execution time of Scheme code.
A macro @code{time}, which is convenient for interactive use,
a set of procedures for benchmarking,
and @code{<time-counter>} objects which are useful to be embedded
in the program.
@c JP
Schemeコードの実行時間を測る3つの方法を提供します。
インタラクティブな使用に便利な@code{time}マクロ、
ベンチマークのための手続きのセット、
プログラム中に埋め込んで使える@code{<time-counter>}オブジェクトです。
@c COMMON
@end deftp

@c EN
@subheading Interactive measurement of execution time
@c JP
@subheading インタラクティブな実行時間の計測
@c COMMON

@c EN
Note: The @code{time} macro is pre-defined to autoload @code{gauche.time}
for the convenience; you don't need to say @code{(use gauche.time)}
to use the @code{time} macro.
@c JP
註: @code{time}マクロは@code{gauche.time}モジュールをオートロードする
ようにあらかじめ定義されているので、@code{time}マクロを使うだけなら
@code{(use gauche.time)}としておく必要はありません。
@c COMMON

@defmac time expr expr2 @dots{}
@c MOD gauche.time
@c EN
Evaluates @var{expr} @var{expr2} @dots{} sequentially, as @code{begin},
and returns the result(s) of the last expression.
Before returning the value(s), the macro reports the elapsed (real) time
and CPU times in the user space and the kernel space to the current
error port, much like the bourne shell's time command.
@c JP
式@var{expr} @var{expr2} @dots{} を順に評価し、最後の式の結果を返します。
結果が返される前に、全ての式の評価にかかった実(経過)時間および
ユーザースペース、カーネルスペースで費されたCPU時間がカレントエラーポートに
報告されます。
@c COMMON

@c EN
The current version uses @code{sys-gettimeofday} (@pxref{Time}) to
calculate the elapsed time, and @code{sys-times} (@pxref{System inquiry})
to calculate user and system CPU times.  So the resolution of these numbers
depends on these underlying system calls.  Usually the CPU
time has 10ms resolution, while the elapsed time might have higher
resolution.  On the systems that doesn't have gettimeofday(2) support,
however, the elapsed time resolution can be as bad as a second.
@c JP
現在の実装は、経過時間に対しては@code{sys-gettimeofday}
(@ref{Time}参照)を、CPU時間に対しては@code{sys-times}
(@ref{System inquiry}参照)を用いています。従って、
それぞれの数値の分解能はこれらの手続きが用いているシステムコールに依存します。
CPU時間は10ms単位で、経過時間はそれより細かいことが多いです。
但しgettimeofday(2)コールをサポートしていないOSでは経過時間が最悪の場合
秒単位になります。
@c COMMON

@smallexample
gosh> (time (length (sort (call-with-input-file "/usr/share/dict/words"
                                                port->string-list))))
;(time (length (sort (call-with-input-file "/usr/share/dict/words" port- ...
; real   0.357
; user   0.350
; sys    0.000
45427
@end smallexample
@end defmac

@c EN
@subheading Benchmarking
@c JP
@subheading ベンチマーク
@c COMMON

@c EN
It is not unusual that the routine you want to measure takes only
a fraction of second, so you have to run it many times for better
measurement.  It is also common that you want to compare results
of measurement of two or more implementation strategies.
Here are useful procedures to do so.
@c JP
計測したいルーチンの一回の実行が一瞬で終わるために、
何度も繰り返して実行してより正確に時間を測りたいということはよくあります。
また、複数の実装を計測して比べてみたいということもよくあります。
ここに挙げるのは、そのために便利な手続きです。
@c COMMON

@c EN
The name and behavior of those benchmarking routines are inspired
by Perl's Benchmark module.
@c JP
これらベンチマーク手続きの名前と振る舞いは、PerlのBenchmarkモジュールを
参考にしています。
@c COMMON

@defun time-this how thunk
@c MOD gauche.time
@c EN
Calls @var{thunk} many times and measure its execution time.
The argument @var{how} can be one of the following forms.
@c JP
@var{thunk}を何度も呼び出し、実行時間を測ります。
@var{how}には次の形が指定できます。
@c COMMON

@table @code
@item @var{integer}
@c EN
It calls @var{thunk} as many times as the given number.
@c JP
指定された回数だけ、@var{thunk}を呼びます。
@c COMMON
@item (@var{metric} @var{real})
@c EN
It calls @var{thunk} as many times as the total time exceeds
the given number of seconds.  @var{Metric} is either one of symbols
@code{cpu}, @code{user}, @code{sys}, or @code{real}, to specify how
the time is measured.
@c JP
時間の合計が指定された数値(秒)を越えるまで@var{thunk}を繰り返し呼びます。
@var{metric}はシンボル@code{cpu}、@code{user}、@code{sys}、@code{real}の
いずれかで、どの時間で測るかを指定します。
@c COMMON
@end table

@c EN
It also runs an empty loop as the same times and subtract the
time took for the empty loop from the measured time, to get
more accurate result.
@c JP
このルーチンはまた、@var{thunk}を実行するのと同じ回数だけ
空のループを実行して、その時間を結果から引くので、
結果には@var{thunk}の実行時間のみが反映されます。
@c COMMON

@c EN
The result is returned in a @code{<time-result>} record, described below.
Here are some examples:
@c JP
戻り値は後述する@code{<time-result>}レコードです。先に例を示しておきます。
@c COMMON
@smallexample
;; Run the thunk 1,000,000 times
(time-this 1000000 (lambda () (expt 100 30)))
  @result{} #<time-result 1000000 times/  1.030 real/  1.040 user/  0.000 sys>

;; Run the thunk at least 5.0 cpu seconds
(time-this '(cpu 5.0) (lambda () (expt 100 30)))
  @result{} #<time-result 4903854 times/  5.090 real/  5.050 user/  0.010 sys>
@end smallexample
@end defun

@deftp {Record} <time-result>
@c MOD gauche.time
@c EN
A record to hold the benchmark result.
Following slots are defined.
@c JP
ベンチマーク結果を保持するレコードです。以下のスロットがあります。
@c COMMON

@defivar {<time-result>} count
@fnindex time-result-count
@c EN
The number of times the thunk was run.   This slot is also
accessed by a procedure @code{time-result-count}.
@c JP
@var{thunk}が実行された回数です。
このスロットはアクセサ手続き@code{time-result-count}でもアクセスできます。
@c COMMON
@end defivar

@defivar {<time-result>} real
@fnindex time-result-real
@c EN
The total real (elapsed) time running the thunk took.
This slot is also accessed by a procedure @code{time-result-real}.
@c JP
@var{thunk}の実行にかかった実経過時間の合計です。
このスロットはアクセサ手続き@code{time-result-real}でもアクセスできます。
@c COMMON
@end defivar

@defivar {<time-result>} user
@fnindex time-result-user
@c EN
The total user cpu time running the thunk took.
This slot is also accessed by a procedure @code{time-result-user}.
@c JP
@var{thunk}の実行にかかったユーザCPU時間の合計です。
このスロットはアクセサ手続き@code{time-result-user}でもアクセスできます。
@c COMMON
@end defivar

@defivar {<time-result>} sys
@fnindex time-result-sys
@c EN
The total system cpu time running the thunk took.
This slot is also accessed by a procedure @code{time-result-sys}.
@c JP
@var{thunk}の実行にかかったシステムCPU時間の合計です。
このスロットはアクセサ手続き@code{time-result-sys}でもアクセスできます。
@c COMMON
@end defivar
@end deftp

@defun make-time-result count real user sys
@c MOD gauche.time
@c EN
The constructor of @code{<time-result>} records.
@c JP
@code{<time-result>}レコードのコンストラクタです。
@c COMMON
@end defun

@defun time-result? obj
@c MOD gauche.time
@c EN
The predicate of @code{<time-result>} records.
@c JP
@code{<time-result>}レコードかどうかを判定します。
@c COMMON
@end defun

@defun time-result+ t1 t2 :key (with-count #f)
@defunx time-result- t1 t2 :key (with-count #f)
@c MOD gauche.time
@c EN
Add or subtract two @code{<time-result>} records and returns a new record.

If @var{with-count} is false,
only the real, user and sys slots are added or subtracted,
and the result's count slot is set to the same as @var{t1}'s count slot.
It is supposed to be used to calculate on measurement
from different chunk of code.

If @var{with-count} is true,
then the values of count slot is also added or subtracted.
It is supposed to calculate on
multiple benchmark results of the same code.
@c JP
ふたつの@code{<time-result>}レコードの和と差を求め、新しいレコードを返します。

@var{with-count}が偽なら、
real, user, sysの各スロットのみが計算対象となり、
結果のcountスロットは@var{t1}のcountスロットの値がそのまま引き継がれます。
これは、部分ごとに別々に計測された結果を対象に計算する場合を意図しています。

@var{with-count}が真なら、
countスロットも同様に計算対象となります。
これは、何度か走らせたベンチマーク結果を対象に計算する場合を意図しています。
@c COMMON
@end defun

@defun time-these how alist
@defunx time-these/report how alist :key metric
@c MOD gauche.time
@c EN
These procedures benchmarks multiple chunks of code to compare.
@c JP
複数のコード片をベンチマークして比較する手続きです。
@c COMMON

@c EN
The @var{alist} argument must be the form of
@code{((key . thunk) @dots{})}, where @code{key} is a symbol
and @var{thunk} is a procedure taking no arguments.
@c JP
@var{alist}は@code{((key . thunk) @dots{})}という形でなければなりません。
ここで、@code{key}はシンボル、@var{thunk}は引数を取らない手続きです。
@c COMMON

@c EN
The @var{how} argument is the same as @code{time-this}; that is,
either an integer for number of iterations, or a list
@code{(cpu @var{x})} to indicate @var{x} seconds of cpu time.
@c JP
@var{how}引数は@code{time-this}と同じです。すなわち、
実行の繰り返し回数を指定する整数か、
使うCPU時間を@var{x}として@code{(cpu @var{x})}の形のリストか、です。
@c COMMON

@c EN
@code{time-these} runs benchmarks for each thunk in @var{alist}
using @code{time-this}, and returns the result in a list of
the form
@code{(@var{how} (@var{key1} . @var{result1}) (@var{key2} . @var{result2}) @dots{})},
where each @var{result} is a @code{<time-result>} object.
@c JP
@code{time-these}は@var{alist}中の@var{thunk}それぞれを走らせて計測し、
結果を
@code{(@var{how} (@var{key1} . @var{result1}) (@var{key2} . @var{result2}) @dots{})}
の形で返します。ここで@var{result}は@code{<time-result>}オブジェクトです。
@c COMMON

@c EN
@code{time-these/report} outputs the benchmark results and
comparison matrix in human readable way to the current output port.
@c JP
@code{time-these/report}はベンチマーク結果を、人間が読みやすい
形式にして表示します。
@c COMMON

@smallexample
gosh> (time-these/report '(cpu 3.0)
        `((real1 . ,(cut expt 100 20))
          (real2 . ,(cut %expt 100 20))
          (imag  . ,(cut expt +100i 20))))
Benchmark: ran real1, real2, imag, each for at least 3.0 cpu seconds.
  real1: 3.312 real, 3.320 cpu (3.320 user + 0.000 sys)@@ 1694277.11/s n=5625000
  real2: 2.996 real, 3.010 cpu (3.010 user + 0.000 sys)@@35595634.55/s n=107142860
   imag: 3.213 real, 3.190 cpu (3.190 user + 0.000 sys)@@  862068.97/s n=2750000

              Rate  real1 real2   imag
  real1  1694277/s     -- 0.048  1.965
  real2 35595635/s 21.009    -- 41.291
   imag   862069/s  0.509 0.024     --
@end smallexample

@c EN
The first part of the report shows, for each thunks,
the real (elapsed) time,
the cpu time used (and its breakdown of user and system time),
the rate of iteration per second, and the total number of iterations.
@c JP
レポートの最初の部分は、各thunkについて、
実経過時間、CPU時間(およびその内訳としてのuser時間とsystem時間)、
一秒あたりの繰り返し回数、そしてトータルの繰り返し回数です。
@c COMMON

@c EN
The second part compares the speed between each pair of the benchmarks.
For example, its first row tells that the benchmark @code{real1} is
0.048 times faster than @code{real2} and 1.965 times faster than
@code{imag}.
@c JP
次の部分は、ベンチマーク間の比較です。
例えば最初の行は、@code{real1}は@code{real2}の0.048倍、
@code{imag}の1.965倍の速度で実行されたことを示しています。
@c COMMON

@c EN
The @var{metric} argument specifies which time metric should be used
for rate calculation and comparison.  It must be either @code{#f}
or one of the symbols @code{cpu}, @code{user}, @code{sys}, or @code{real}.
If it is @code{#f} (default), the same metric as @var{how} argument is used
(if @var{how} is an integer count, @code{cpu} is assumed).
@c JP
@var{metric}引数は、速度計算および比較マトリクスにどの時間を使うかを指定します。
渡す値は@code{#f}か、シンボル@code{cpu}、@code{real}、
@code{user}、@code{sys}のいずれかでなければなりません。
デフォルトは@code{#f}で、その場合は@var{how}に渡したメトリックが使われます
(@var{how}が回数を指定する整数の場合は、@code{cpu}が使われます)。
@c COMMON
@end defun

@defun report-time-results result :optional metric
@c MOD gauche.time
@c EN
This is a utility procedure to create a report from
the result of @code{time-these}.  Actually, @code{time-these/report}
is just a combination of @code{time-these} and this procedure:
@c JP
これは@code{time-these}の結果を見やすいレポートとして表示する
ユーティリティ手続きです。@code{time-these/report}は
@code{time-these}とこの手続きを組み合わせているだけです。
@c COMMON

@c EN
The meaning of the optional @var{metric} argument is the same
as the @var{metric} keyword argument of @code{time-these/report}.
@c JP
省略可能な@var{metric}引数の意味は、
@code{time-these/report}の@var{metric}キーワード引数と同じです。
@c COMMON

@example
(define (time-these/report how samples :key metric)
  (report-time-results (time-these how samples) metric))
@end example
@end defun


@c EN
@subheading Finer measurement
@c JP
@subheading より細かい計測
@c COMMON

@deftp {Class} <time-counter>
@clindex time-counter
@c MOD gauche.time
@c EN
An abstract class of time counters.  Time counter is a kind of timer
whose value is incremented as the time passes.  The counting
can be started and stopped any number of times.
The value of the counter can be read
when the timer is stopping.
You can have multiple time counters.  It is useful, for example,
to measure the time in two parts inside a loop independently.
@c JP
時間カウンタの抽象クラスです。時間カウンタは
時間の経過と共にその値が増加してゆく一種のタイマーです。
何度でもカウントを止めたり開始したりできます。
カウンタの値はカウントが止まっている時に読み出すことができます。
複数の時間カウンタを使えば、
例えばループ中の二つの部分について費される時間を別々に計測することもできます。
@c COMMON

@c EN
The concrete subclass determines which time it is counting.
You have to instantiate one of those subclasses described below
to use the time counter.
@c JP
具体的なサブクラスが、どの時間をカウントするかを決定します。
時間カウンタを使うには、下に挙げるサブクラスのいずれかを
インスタンシエイトしなければなりません。
@c COMMON
@end deftp

@deftp {Class} <real-time-counter>
@deftpx {Class} <user-time-counter>
@deftpx {Class} <system-time-counter>
@deftpx {Class} <process-time-counter>
@clindex real-time-counter
@clindex user-time-counter
@clindex system-time-counter
@clindex process-time-counter
@c MOD gauche.time
@c EN
Classes for time counters that count real (elapsed) time, user-space CPU time,
kernel-space CPU time, and total CPU time (user + system), respectively.
@c JP
それぞれ、実経過時間、ユーザースペースCPU時間、カーネルスペースCPU時間、
総CPU時間 (ユーザー+カーネル)を計測する時間カウンタのクラスです。
@c COMMON
@end deftp

@deffn {Method} time-counter-start! (counter <time-counter>)
@deffnx {Method} time-counter-stop! (counter <time-counter>)
@c MOD gauche.time
@c EN
Starts and stops the @var{counter}.  The time during the counter is
running is accumulated to the counter value when the counter is stopped.
@c JP
時間カウンタ@var{counter}を開始/停止します。カウンタが走っている間の時間が、
カウンタが停止した時点でカウンタの値に加算されます。
@c COMMON

@c EN
Start/stop pairs can be nested,
but only the outermost pair takes the effect.  That is, if you call
@code{time-counter-start!} on the counter that is already started,
it doesn't have any effect except that to stop such a counter
you have to call @code{time-counter-stop!} one more time.  It is useful
when you want to measure the time spent in the larger block that
may already contain timer start/stop pairs.
@c JP
開始/停止の対はネストすることができます。その場合は、一番外側の対のみが
有効です。
つまり、既に走っているカウンタに対し@code{time-counter-start!}を呼んでも
何も起こりませんが、一度余分に@code{time-counter-stop!}を呼ばないと
カウンタは止まりません。
これは、内部に既に開始/停止の対を含んでいるかもしれない大きなコードブロックの
全体の時間を計測したいというような場合に便利です。
@c COMMON

@c EN
Calling @code{time-counter-stop!} on the already stopped counter
has no effect.
@c JP
既に停止しているカウンタに対して@code{time-counter-stop!}を呼んでも
何も起こりません。
@c COMMON
@end deffn

@deffn {Method} time-counter-reset! (counter <time-counter>)
@c MOD gauche.time
@c EN
Resets the value of @var{counter}.  If @var{counter} is already
running, it is forced to stop before being reset.
@c JP
カウンタ@var{counter}の値をリセットします。既に@var{counter}が走っている
場合は、リセットの前にカウンタは停止させられます。
@c COMMON
@end deffn

@deffn {Method} time-counter-value (counter <time-counter>)
@c MOD gauche.time
@c EN
Returns the current value of the counter as the number of seconds,
in a real number.  The resolution depends on the source of the counter.
@c JP
カウンタ@var{counter}の現在の値(秒数)を実数で返します。
分解能はそれぞれのカウンタが用いているシステムコールに依存します。
@c COMMON
@end deffn

@defmac with-time-counter counter expr @dots{}
@c MOD gauche.time
@c EN
A convenience macro to run the @var{counter} while @var{expr} @dots{}
are evaluated.  Returns the result(s) of the last expression.
It is defined as follows.
@c JP
式@var{expr} @dots{}が評価される間だけ@var{counter}を走らせる、
便利なマクロです。最後の式の結果を返します。このマクロは次のように
定義されます。
@c COMMON
@example
(define-syntax with-time-counter
  (syntax-rules ()
    ((_ counter . exprs)
     (dynamic-wind
      (lambda () (time-counter-start! counter))
      (lambda () . exprs)
      (lambda () (time-counter-stop! counter))))
    ))
@end example
@end defmac

@c EN
The following example measures approximate times
spend in process-A and process-B inside a loop.
@c JP
下の例では、ループ内でのprocess-Aとprocess-Bにて費された
概略の時間をそれぞれ計測します。
@c COMMON

@example
(let ((ta (make <real-time-counter>))
      (tb (make <real-time-counter>)))
  (dotimes (i 100000)
    (with-time-counter ta
      (process-A))
    (with-time-counter tb
      (process-B)))
  (format #t "Time spent in process-A: ~s\n" (time-counter-value ta))
  (format #t "Time spent in process-B: ~s\n" (time-counter-value tb))
  )
@end example

@c ----------------------------------------------------------------------
@node Unicode utilities, Uniform vector library, Measure timings, Library modules - Gauche extensions
@section @code{gauche.unicode} - Unicode utilities
@c NODE Unicodeユーティリティ, @code{gauche.unicode} - Unicodeユーティリティ

@deftp {Module} gauche.unicode
@mdindex gauche.unicode
@c EN
This module provides various operations on a sequence of Unicode codepoints.

Gauche used to support a native encoding other than Unicode,
and the full Unicode-compatible behavior on characters and strings may
not have been available on such systems.  So we provide most operations in two
flavors: Operations on characters and strings, or operations on
codepoints represented as a sequence of integers.
@c JP
このモジュールは、Unicodeのコードポイントの列に対する様々な操作を提供します。

Gaucheは以前、内部文字エンコーディングとしてUnicode以外も選べるようになっていました。
その場合、文字列に対して完全にUnicode互換の動作を提供できない場合があったため、
本モジュールの多くの操作は、文字列を対象にするものと、
コードポイントの数値のシーケンスを対象にするものの両方で提供されます。
@c COMMON
@end deftp

@menu
* Unicode transfer encodings::
* Unicode text segmentation::
* Full string case conversion::
* East asian width property::
@end menu

@node Unicode transfer encodings, Unicode text segmentation, Unicode utilities, Unicode utilities
@subsection Unicode transfer encodings

@c EN
The procedures in this group operate on codepoints represented as integers.
In the following descriptions, an octet refers to an integer
between 0 to 255, inclusive.
@c JP
このグループの手続きは、整数で表現されたコードポイントを扱います。
以下の説明で「オクテット」は0から255までの整数です。
@c COMMON

@c EN
They take optional @var{strictness} argument.  It specifies
what to do when the procedure encounters a datum outside
of the defined domain.  Its value can be either one of the
following symbols:
@c JP
これらの手続きは省略可能な@var{strictness}引数を取ります。
この引数は、定義域外の入力が来たときの振る舞いを指定します。
指定できる値は次のいずれかです。
@c COMMON

@table @code
@item strict
@c EN
Raises an error when the procedure encounters such input.
This is the default behavior.
@c JP
定義域外の入力が来たらエラーを投げます。これがデフォルトの振る舞いです。
@c COMMON
@item permissive
@c EN
Whenever possible, treat the date as if it is a valid value.
For example, codepoint value beyond @code{#x10ffff} is invalid
in Unicode standard, but it may be useful for some other purpose
that just want to use UTF-8 as an encoding scheme of binary data.
@c JP
可能な限り、入力を有効な値であるかのように扱います。
例えば@code{#x10ffff}を越えるコードポイント値はUnicode標準では不正な値ですが、
utf-8の規則を拡張することでエンコード可能であり、文字列以外のバイナリデータを単にutf-8風に
エンコードしたいだけの場合などには便利かもしれません。
@c COMMON
@item replace
@c EN
If the procedure sees invalid input, replaces it with a unicode
replacement character @code{U+FFFD} and proceed.
@c JP
不正な入力を見たら、それをユニコード置換文字@code{U+FFFD}に置き換え処理を続行します。
@c COMMON
@item ignore
@c EN
Whenver possible, treat the invalid input as if they do not exist.
@c JP
可能であれば、不正な入力は無視します。
@c COMMON
@end table

@c EN
The procedure may still raise an error in @code{permissive}, @code{replace} or
@code{ignore} strictness mode, if there can't be a sensible
way to handle the input data.
@c JP
@var{strictness}が@code{permissive}や@code{replace}や@code{ignore}であっても、
入力データの妥当な解釈ができない場合はエラーが投げられる可能性があります。
@c COMMON

@defun ucs4->utf8 codepoint :optional strictness
@c MOD gauche.unicode
@c EN
Takes an integer codepoint and returns a list of octets that
encodes the input in UTF-8.
@c JP
整数のコードポイント値を受け取り、utf-8でエンコードされたオクテットのリストを返します。
@c COMMON

@example
(ucs4->utf8 #x3bb)  @result{} (206 187)
(ucs4->utf8 #x3042) @result{} (227 129 130)
@end example

@c EN
If @var{strictness} is @code{strict} (default), input codepoint
between @code{#xd800} to @code{#xdfff}, and beyond @code{#x110000},
are rejected. If @var{strictness} is @code{replace}, such input
yields a utf8 sequence @code{#xef, #xbf, #xbd}, which encodes
@code{U+FFFD}.
If @var{strictness} is @code{permissive}, it accepts
input between @code{0} and @code{#x7fffffff}, inclusive; it may produce
5 or 6 octets if the input is large (as the original UTF-8 definition).
If @var{strictness} is @code{ignore}, it returns an empty list
for invalid codepoints.
@c JP
@var{strictness}が@code{strict}の場合(デフォルト)、
入力が@code{#xd800}と@code{#xdfff}の間か、@code{#x110000}以上の場合は
エラーを投げます。
@var{strictness}が@code{replace}であれば、そのような入力に対しては
utf8シーケンス@code{#xef, #xbf, #xbd} (@code{U+FFFD}) が生成されます。
@var{strictness}が@code{permissive}の場合は、
@code{0}から@code{#x7fffffff}までの入力が許されます。
入力が大きい場合はエンコードされた出力は5〜6オクテットになるでしょう
(初期のutf-8の定義通り)。
@var{strictness}が@code{ignore}の場合は、
Unicodeとして不正なコードポイントに対しては空リストが返されます。
@c COMMON
@end defun

@defun utf8-length octet :optional strictness
@c MOD gauche.unicode
@c EN
Takes @var{octet} as the first octet of UTF-8 sequence, and
returns the number of total octets required to decode
the codepoint.
@c JP
@var{octet}をutf-8シーケンスの最初のオクテットとみなし、
そこからひとつのコードポイントをデコードするのに全部で何オクテット必要かを返します。
@c COMMON

@c EN
If @var{octet} is not an exact integer between 0 and 255 (inclusive),
an error is thrown, regardless of @var{strictness} argument.
@c JP
@var{octet}引数が0から255の間の正確な整数でなければ、
@var{strictness}引数の値にかかわらず、エラーが投げられます。
@c COMMON

@c EN
If @var{strictness} is @code{strict} (default), this
procedure returns either 1, 2, 3 or 4.   An error is
thrown if @var{octet} cannot be a leading octet of
a proper UTF-8 encoded Unicode codepoint.
@c JP
@var{strictness}が@code{strict}の場合(デフォルト)、
戻り値は1,2,3,4のいずれかです。@var{octet}がutf-8でエンコードされた
Unicodeコードポイントの最初のオクテットとしてありえない値であれば
エラーが投げられます。
@c COMMON

@c EN
If @var{strictness} is @code{permissive} or @code{replace}, this procedure
may return an integer between 0 and 6, inclusive.
If the input is from @code{#xf8} to @code{#xfd}, inclusive,
this returns 5 or 6, according to the original utf-8 spec
(these values corresponds to the codepoint
range @code{#x110000} to
@code{#x7fffffff}).
If the input is in the range between @code{#x80}
and @code{#xbf}, inclusive, or @var{#xfe} or @code{#xff},
this procedure returns 1--it's up to the application how to treat these illegal
octets.
@c JP
@var{strictness}が@code{permissive}か@code{replace}の場合、
この手続きは0から6までの整数を返します。
入力が@code{#xf8}から@code{#xfd}の間の値(両端含む)の場合は
元々のutf-8仕様に基づいて5か6を返します
(これらのオクテットはコードポイントが@code{#x110000}から
@code{#x7fffffff}になるような値に相当します)。
引数が@code{#x80}から@code{#xbf}までの値、および@code{#xfe}と@code{#xff}の場合は、
utf-8の先頭バイトになり得ませんが、アプリケーションがこの不正なバイトだけを
適切に処理することを前提にして、1が返されます。
@c COMMON

@c EN
If @var{strictness} is @code{ignore}, this procedure
returns @code{0} when it would raise an error if
@var{strictness} is @code{strict}.  Other than that,
it works the same as the default case.
@c JP
@var{strictness}が@code{ignore}の場合、この手続きは
@code{strict}でエラーが投げられる入力値について@code{0}を返します。
それ以外は@code{strict}の動作と同じです。
@c COMMON
@end defun

@defun utf8->ucs4 octet-list :optional strictness
@c MOD gauche.unicode
@c EN
Takes a list of octets, and decodes it as a utf-8 sequence.
Returns two values: The decoded ucs4 codepoint, and the
rest of the input list.
@c JP
オクテットのリストを取り、それをutf-8のシーケンスとして解釈して、
デコードされたコードポイント及び残りのリストの2つの値を返します。
@c COMMON

@c EN
If it finds a value other than exact integer
between 0 and 255 in the input list, an error is thrown
regardless of the value of @var{strictness}.
@c JP
もし処理中に、0から255の間の正確な整数以外の値が入力に見つかったら、
@var{strictness}の設定に関わらずエラーが投げられます。
@c COMMON

@c EN
An invalid utf8 sequence causes an error if @var{strictness}
is @code{strict}, or skipped if it is @code{ignore}.
If @var{strictness} is @code{replace}, such utf8 sequence
yields @code{U+FFFD}.
If @var{strictness} is @code{permissive}, the procedure accepts
the original utf-8 sequence which can produce surrogated pair
range (between @code{#xd800} and @code{#dfff}) and the range
between @code{#x110000} to @code{#x7fffffff}.  The invalid
octet sequence is still an error with @code{permissive} mode.
@c JP
それ以外の不正なutf-8シーケンスは、@var{strictness}が@code{strict}であれば
エラーに、@code{ignore}であればスキップされます。
@var{strictness}が@code{replace}の場合は、そういったutf8シーケンスは
@code{U+FFFD}を生成します。
@var{strictness}が@code{permissive}の場合は、
最初のutf-8仕様で許されていた全てのコードポイント、すなわち
サロゲートペア領域(@code{#xd800}から@code{#dfff}まで)及び
@code{#x110000}以上@code{#x7fffffff}以下のコードポイントも認識されます。
それ以外の不正なコードポイントは@code{permissive}であってもエラーになります。
@c COMMON
@end defun

@defun utf8->string u8vector :optional start end
[R7RS base]
@c MOD gauche.unicode
@c EN
Converts a sequence of utf8 octets in @var{u8vector} to a string.
Optional @var{start} and/or @var{end} argument(s) will limit the
range of the input.
@c JP
@var{u8vector}の、インデックス@var{start}(含む)から@var{end}(含まない)までに
格納された値をutf-8オクテット列と見なし、文字列に変換して返します。
@var{start}、@var{end}が省略された場合はそれぞれベクタの最初と最後が指定されたものと
解釈します。
@c COMMON

@c EN
This procedure first tries
@code{u8vector->string} (@pxref{Uniform vectors}).
If the input utf8 sequence is valid, this is the fastest way.
If the input contains invalid utf8 sequence, the procedure falls
back to construct a string by one character at at time,
replacing invalid sequence with Unicode replacement character @code{U+FFFD}.
Hence it always returns a complete string.
To know if the input contains invalid utf8 sequence, you can use
@code{u8vector->string} directly.
@c JP
この手続きはまず@code{u8vector->string}を試します
(@ref{Uniform vectors}参照)。
もし入力がutf8シーケンスとして有効であれば、それが最も速いです。
しかし、入力に無効なutf8シーケンスが含まれていた場合、
この手続きは1文字づつ文字列を構築するモードにフォールバックし、
無効なutf8シーケンスの部分はUnicode置換文字@code{U+FFFD}に置き換えられます。
従って戻り値は常に完全な文字列です。
入力に不正なuft8シーケンスが含まれていたかどうかを知りたい場合は
@code{u8vector->string}を直接呼んでください。
@c COMMON
@end defun

@defun string->utf8 string :optional start end
[R7RS base]
@c MOD gauche.unicode
@c EN
Converts a string to a u8vector of utf8 octets.
Optional @var{start} and/or @var{end} argument(s) will limit the
range of the input.
@c JP
文字列をutf8オクテットの並びにエンコードしてu8vectorとして返します。
省略可能な@var{start}と@var{end}引数は対象とする文字列の範囲を指定します。
@c COMMON

@c EN
Now that Gauche always uses utf8 in the internal encoding,
this procedure just calls @code{string->u8vector} (@pxref{Uniform vectors}).
@c JP
現在はGaucheは常にutf8を内部エンコーディングとして使うので、
この手続きは単に@code{string->u8vector}を呼び出すだけです。
(@ref{Uniform vectors}参照)。
@c COMMON
@end defun

@defun ucs4->utf16 codepoint :optional strictness
@c MOD gauche.unicode
@c EN
Takes an integer codepoint and returns a list of integers
that encodes the input in UTF-16.
@c JP
整数で与えられたコードポイントをutf-16にエンコードして整数のリストとして返します。
@c COMMON

@c EN
If @var{strictness} is @code{strict} (default),
the input must be either
between @code{0} and @code{#xd7ff} or between @code{#xe000} and
@code{#x10ffff}.  An error is thrown otherwise.  The 'hole' is the
codepoint reserved for surrogates, and there's no valid
mapping from them to utf-16 is defined.
@c JP
@var{strictness}が@code{strict}の場合(デフォルト)、
入力値は@code{0}から@code{#xd7ff}までの間か、
@code{#xe000}から@code{#x10ffff}までの間でなければなりません。
それ以外の場合はエラーが投げられます。
開いている部分はサロゲートに予約されているコードで、
この領域をutf-16にエンコードする方法は定義されていません。
@c COMMON

@c EN
If @var{strictness} is @code{replace}, such input is replaced
with @code{#xfffd}, which encodes Unicode replacement character.
@c JP
@var{strictness}が@code{replace}であれば、そのような入力は
@code{#xfffd}(Unicode置換文字)に置き換えられます。
@c COMMON

@c EN
If @var{strictness} is @code{permissive}, it accepts
high surrogates and low surrogates, in which case the result is
single element list of input.  An error is still thrown for
negative input and input greater than or equal to @code{#x110000}.
@c JP
@var{strictness}が@code{permissive}の場合、サロゲート領域の入力は
エラーにならず、その値を唯一の要素とするリストが返されます。
負の値および@code{#x110000}の値についてはやはりエラーになります。
@c COMMON

@c EN
If @var{strictness} is @code{ignore},
an empty list is returned for an invalid codepoint (including surrogates).
@c JP
@var{strictness}が@code{ignore}の場合は、不正なコードポイント(サロゲート領域含む)
については空リストが返されます。
@c COMMON

@c EN
Note: We can encode values larger than @code{#x10ffff} in utf-8
in the permissive mode, but not in utf-16.
@c JP
註: permissiveモードでは@code{#x10ffff}より大きな値をutf-8にはエンコードできますが、
utf-16にはエンコードできません。
@c COMMON
@end defun

@defun utf16-length code :optional strictness
@c MOD gauche.unicode
@c EN
@var{Code} must be an exact integer between 0 and 65535, inclusive.
Returns 1 if @var{code} is BMP character codepoint, or
2 if @var{code} is a high surrogate.
@c JP
@var{code}は0から65535までの正確な整数でなければなりません。
@code{code}がBMPのコードポイントなら1を、utf-16の上位サロゲートであれば2を返します。
@c COMMON

@c EN
If @var{strictness} is @code{strict} (default), an error is
signalled if @var{code} is a low surrogate, or it is out of range.
If @var{strictness} is @code{permissive} or @code{replace}, 1 is returned
for low surrogates, but an error is signalled for out of range arguments.
If @var{strictness} is @code{ignore}, 0 is returned
for low surrogates and out of range arguments.
@c JP
@var{strictness}が@code{strict}の場合(デフォルト)、@var{code}が
下位サロゲートであったり、定義外の値であればエラーが投げられます。
@var{strictness}が@code{permissive}や@code{replace}の場合は、
やはり定義外の値であればエラーが投げられますが、
下位サロゲートの場合には1が返されます。
@var{strictness}が@code{ignore}の場合、
定義域外および下位サロゲートに対しては0が返されます。
@c COMMON
@end defun

@defun utf16->ucs4 code-list :optional strictness
@c MOD gauche.unicode
@c EN
Takes a list of exact integers and decodes it as a utf-16 sequence.
Returns two values: The decoded ucs4 codepoint, and the rest of
input list.
@c JP
正確な整数のリストを取り、それをutf-16の並びとして解釈します。
デコードされたucs4コードポイントおよび、残りのリストの二つの値を返します。
@c COMMON

@c EN
If @var{strictness} is @code{strict} (default), an invalid utf-16
sequence and out-of-range integer raise an error.  If @var{strictness}
is @code{permissive}, an out-of-range integer causes an error, but
a lone surrogate is allowed and returned as is.
If @var{strictness} is @code{replace}, a lone surrogate is
replaced with @code{U+FFFD}.
If @var{strictness}
is @code{ignore}, lone surrogates and out-of-range integers are just
ignored.
@c JP
@var{strictness}が@code{strict}の場合(デフォルト)、不正なutf-16の並びや
定義域外の値に出会ったらエラーが投げられます。
@var{strictness}が@code{permissive}の場合は、
やはり定義外の値であればエラーが投げられますが、
片方だけのサロゲートの場合にはそれがそのまま(コードポイントとして)返されます。
@var{strictness}が@code{replace}の場合は、
片方だけのサロゲートは@code{U+FFFD}に置換されます。
@var{strictness}が@code{ignore}の場合、
定義域外および片方だけのサロゲートは無視されます。
@c COMMON
@end defun


@defun utf16->string u8vector :optional endian ignore-bom? start end
@defunx utf32->string u8vector :optional endian ignore-bom? start end
@c MOD guache.unicode
[R7RS scheme.bytevector]
@c EN
Convert utf16 and utf32 sequence stored in @var{u8vector} to a string,
respectively.
For @code{utf16->string},
if the input contains invlaid utf16 sequence (unpaired surrogate),
it is replaced with Unicode replacement character @code{U+FFFD}.
If the number of input octet is not the multiple of unit (2 octets
for utf16, and 4 octets for utf32), an error is thrown.
@c JP
@var{u8vector}に格納されたutf16およびutf32シーケンスを文字列に変換します。
@code{utf16->string}は、
もし入力に不正なutf16シーケンス (ペアになっていないサロゲート) があった場合は、
それがUnicode置換文字(@code{U+FFFD})に置き換えます。
入力のオクテット数がエンコーディング単位(utf16なら2オクテット、utf32なら4オクテット)
の倍数でない場合はエラーが投げられます。
@c COMMON

@c EN
The optional @var{endian} and @var{ignore-bom?} arguments
determines whether the input is in UTF16BE/UTF32BE or UTF16LE/UTF32LE.
If @var{ignore-bom?} is @code{#f} or omitted, the first two octets
of input is examined; if it's BOM, it deterimines the endianness
regardless of @var{endian} argument,
and the BOM won't be included in the output.
If the input does not begin with BOM, or @var{ignore-bom?} is true,
then the endianness is determined by @var{endian} argument: It can be
@code{big-endian} or @code{big} for UTF16BE/UTF32BE, and
@code{little-endian} or @code{little} or @code{arm-big-endian}
for UTF16LE/UTF32LE (@pxref{Endianness}, for the details of endianness).

Note that if @var{ignore-bom?} is given and true,
the initial BOM is interpreted as a codepoint @code{U+FEFF}.
If @var{endian} is @code{#f} or omitted, UTF16BE/UTF32BE
is assumed (it is defined so in R7RS @code{scheme.bytevector}).

In R7RS @code{scheme.bytevector}, @var{ignore-bom?} argument
is called @var{endianness-mandatory}.  The behavior is the same.
@c JP
省略可能な@var{endian}と@var{ignore-bom?}引数は入力がUTF16BE/UTF32BEか
UTF16LE/UTF32LEかを
決めます。@var{ignore-bom?}が@code{#f}または省略された場合、まず入力の
最初の2オクテットが調べられ、BOMであれば@var{endian}の値にかかわらず
それがバイトオーダーを決定します。
入力がBOMで始まっていないか、@var{ignore-bom?}が真の値であれば、
@var{endian}引数がバイトオーダーを決定します。それが
@code{big-endian}か@code{big}であればUTF16BE/UTF32BE、
@code{little-endian}か@code{little}か@code{arm-little-endian}であれば
UTF16LE/UTF32LEとなります (エンディアンについては@ref{Endianness}参照)。

@var{ignore-bom?}が与えられて真の値であった場合、
入力の先頭のBOMはコードポイントとみなされます。
@var{endian}が@code{#f}または省略された場合は、
UTF16BE/UTF32BEとみなされます
(これはR7RS @code{scheme.bytevector}で定義された仕様です)。

なおR7RS @code{scheme.bytevector}では@var{ignore-bom?}引数は
@var{endianness-mandatory}と呼ばれています。動作は同じです。
@c COMMON

@c EN
Optinoal argument @var{start} and @var{end} trims the input octet sequence
before other processing (including BOM detection).  These arguments are
Gauche's extension, and not the part of R7RS @code{scheme.bytevector}.
@c JP
省略可能な@var{start}と@var{end}引数は処理に先立って入力のオクテットシーケンスの
範囲を制限します(BOM検出も範囲制限後に行われます)。
この2つの引数はGauche独自拡張で、R7RS @code{scheme.bytevector}では定義されていません。
@c COMMON
@end defun

@defun string->utf16 str :optional endian add-bom? start end
@defunx string->utf32 str :optional endian add-bom? start end
@c MOD gauche.unicode
[R7RS scheme.bytevector]
@c EN
Encode a string @var{str} to utf-16 and utf-32 sequences stored in a u8vector,
respectively.

The optional @var{endian} argument specifies whether the encoding
is UTF16BE/UTF32BE or UTF16LE/UTF32LE.  If it is a symobl @code{big-endian} or
@code{big}, the encoding is UTF16BE/UTF32BE.  If it is a symbol
@code{little-endian}, @code{little} or @code{arm-little-endian},
the encoding is UTF16LE/UTF32LE.
@xref{Endianness}, for the details of endianness.
If it is omitted or @code{#f}, UTF16BE/UTF32BE is assumed.

The second optional argument @var{add-bom?} specifies, if true value is
given, the output contains BOM.  When omitted BOM won't be added.

The @var{start} and @var{end} arguments limits the range of @var{str}
to be converted.

R7RS @code{scheme.bytevector} only defines @var{endian} optional
argument.  The rest is Gauche's extension.
@c JP
文字列@var{str}をutf-16またはutf-32にエンコードしたオクテット列をu8vectorで返します。

省略可能な@var{endian}引数は、エンコーディングがUTF16BE/UTF32BEかUTF16LE/UTF32LEかを決めます。
シンボル@code{big-endian}か@code{big}が渡されたらUTF16BE/UTF32BE、
シンボル@code{little-endian}か@code{little}か@code{arm-little-endian}が
渡されたらUTF16LE/UTF32LEになります。省略されるか@code{#f}ならUTF16BE/UTF32BEになります。
バイトオーダーについての詳細は@ref{Endianness}を参照してください。

二つめの省略可能引数@var{add-bom?}にもし真の値が与えられたら、
出力の先頭にBOMが含められます。省略されるか@code{#f}であればBOMは付加されません。

続く省略可能引数@var{start}と@var{end}は入力文字列@var{str}の特定の範囲だけを
対象とするのに使います。

R7RSの@code{scheme.bytevector}では@var{endian}引数だけを認めています。
残りはGaucheの拡張です。
@c COMMON
@end defun



@node Unicode text segmentation, Full string case conversion, Unicode transfer encodings, Unicode utilities
@subsection Unicode text segmentation

@c EN
These procedures implements grapheme-cluster and
word breaking algorithms defined in UAX #29: Unicode Text Segmentation.
@c JP
以下の手続きはUAX #29: Unicode Text Segmentationに定義されている
graphemeクラスタへの分割および単語への分割アルゴリズムを実装します。
@c COMMON

@defun string->words string
@defunx codepoints->words sequence
@c MOD gauche.unicode
@c EN
From given string or codepoint sequence (a @code{<sequence>}
object containing codepoints), returns a list of
words.  Each word is represented as a string, or
a sequence of the same type as input, respectively.
@c JP
与えられた文字列あるいはコードポイントシーケンス(コードポイントを要素とする
@code{<sequence>}オブジェクト)から、単語のリストを返します。
各単語はそれぞれ、文字列あるいはコードポイントシーケンスで表現されます。
@c COMMON

@example
(string->words "That's it.")
 @result{} ("That's" " " "it" ".")
(codepoints->words '(84 104 97 116 39 115 32 105 116 46)
 @result{} ((84 104 97 116 39 115) (32) (105 116) (46))
(codepoints->words '#(84 104 97 116 39 115 32 105 116 46)
 @result{} (#(84 104 97 116 39 115) #(32) #(105 116) #(46))
@end example

@c EN
In the second and third example, the input is a sequence of codepoints
of characters in "That's it."
@c JP
二番めと三番目の例の入力は "That's it." をコードポイント列にしたものです。
@c COMMON
@end defun


@defun string->grapheme-clusters string
@defunx codepoints->grapheme-clusters sequence
@c MOD gauche.unicode
@c EN
From given string or codepoint sequence (a @code{<sequence>}
object containing codepoints), returns a list of
grapheme clusters.  Each cluster is represented as a string,
or a sequence of the same type as input, respectively.
@c JP
与えられた文字列あるいはコードポイントシーケンス(コードポイントを要素とする
@code{<sequence>}オブジェクト)から、graphemeクラスタのリストを返します。
各クラスタはそれぞれ、文字列あるいはコードポイントシーケンスで表現されます。
@c COMMON
@end defun

@c EN
The following procedures are low-level building blocks
to build the above @code{string->words} etc.
@c JP
以下の手続きは上記の@code{string->words}等の高レベル手続きを作る部品となる、
低レベル手続きです。
@c COMMON

@defun make-word-breaker generator
@defunx make-grapheme-cluster-breaker generator
@c MOD gauche.unicode
@c EN
From given @var{generator}, which is a generator of characters or codepoints,
returns a generator that returns two values: The first value is the
character or codepoint generated from the original generator, and the
second value is a boolean flag, which is @code{#t} if a word
or a grapheme cluster
breaks before the character/codepoint, and @code{#f} otherwise.
@c JP
文字かコードポイントを生成するジェネレータ@var{generator}を取り、
二つの値を返すジェネレータを返します。最初の値は元のジェネレータから受け取った
文字またはコードポイントで、二つめの値は、その文字またはコードポイントの直前に
単語もしくはgraphemeクラスタ境界があった時に@code{#t}、そうでない時に@code{#f}となる
真偽値です。
@c COMMON

@c EN
Suppose a generator @var{g} returns characters in a string
@code{That's it.}, one at a time.  Then the created generator
will work as follows:
@c JP
ジェネレータ@code{g}が文字列@code{That's it.}に含まれる文字を順に返す
ジェネレータとすれば、作られるジェネレータの動作は次の通りです。
@c COMMON

@example
(define brk (make-word-breaker g))
(brk)  @result{}  #\T     and #t
(brk)  @result{}  #\h     and #f
(brk)  @result{}  #\a     and #f
(brk)  @result{}  #\t     and #f
(brk)  @result{}  #\'     and #f
(brk)  @result{}  #\s     and #f
(brk)  @result{}  #\space and #t
(brk)  @result{}  #\i     and #t
(brk)  @result{}  #\t     and #f
(brk)  @result{}  #\.     and #t
(brk)  @result{}  #<eof>  and #t
@end example

@c EN
It shows the word breaks at those character boundaries shown
by the caret @code{^} below (for clearity, I use @code{_} to indicate
the space).
@c JP
つまり、下図で@code{^}で示される箇所が単語境界となっています
(空白字を@code{_}で表しています)。
@c COMMON

@example
  T h a t ' s _ i t .
 ^           ^ ^   ^ ^
@end example
@end defun

@defun make-word-reader generator return
@defunx make-grapheme-cluster-reader generator return
@c MOD gauche.unicode
@c EN
The input @var{generator} is a generator of characters or codepoints,
and @var{return} is a procedure that takes a list of characters or
codepoints, and returns an object.   These procedures creates a
generator that returns an object at at time, each consists of a
word or a grapheme cluster, respectively.
@c JP
@var{generator}は文字またはコードポイントを生成するジェネレータで、
@var{return}は文字またはコードポイントのリストを受け取り、オブジェクトを返す手続きです。
これらの手続きは、オブジェクト (単語またはgraphemeクラスタ) をひとつづつ生成する
ジェネレータを返します。
@c COMMON

@c EN
Suppose a generator @var{g} returns characters in a string
@code{That's it.}, one at a time, again.
Then the created generator works as follows:
@c JP
ジェネレータ@code{g}が文字列@code{That's it.}に含まれる文字を順に返す
ジェネレータとすれば、作られるジェネレータの動作は次の通りです。
@c COMMON

@example
(define brk (make-word-reader g list->string))
(brk)  @result{}  "That's"
(brk)  @result{}  " "
(brk)  @result{}  "it"
(brk)  @result{}  "."
(brk)  @result{}  #<eof>
@end example

@end defun


@node Full string case conversion, East asian width property, Unicode text segmentation, Unicode utilities
@subsection Full string case conversion
@c NODE フルセットの大文字小文字変換

@defun string-upcase string
@defunx string-downcase string
@defunx string-titlecase string
@defunx string-foldcase string
[R6RS][R7RS char][SRFI-129]
@c MOD gauche.unicode
@c EN
Converts the case of given @var{string}
using language-independent full case folding defined by Unicode standard.
They differ from SRFI-13's procedures
with the same names (@pxref{SRFI-13 String case mapping}),
which simply uses character-by-character case mapping.
Notably, the length of resulting string may differ from the source string,
and some conversions are sensitive to whether the character is at the
word boundary or not.  The word boundaries are determined according
to UAX #29 text segmentation rules.
@c JP
与えられた文字列@var{string}の大文字小文字を、Unicodeで定義された
言語独立のcase folding規則に基づいて変換します。
SRFI-13にも同名の手続きがありますが、そちらは文字ごとに変換する点で
これらの手続きと異なります(@ref{SRFI-13 String case mapping}参照)。
特に、こちらの手続きは元の文字列と変換後の文字列の長さが異なる場合があり、
また文字が単語境界にあるかどうかで変換が変わることもあります。
単語境界はUAX #29の規則に基づいて判断されます。
@c COMMON

@example
(string-upcase "straße")
 @result{} "STRASSE"
(string-downcase "ΧΑΟΣΧΑΟΣ.ΧΑΟΣ. Σ.")
 @result{} "χαοσχαοσ.χαος. σ."
(string-titlecase "You're talking about R6RS, right?")
 @result{} "You're Talking About R6rs, Right?"
(string-foldcase "straße")
 @result{} "strasse"
(string-foldcase "ΧΑΟΣΣ")
 @result{} "χαοσσ"
@end example

@c EN
Procedures @code{string-upcase}, @code{string-downcase},
and @code{string-foldcase} are also in R7RS @code{scheme.char} module.
@c JP
@code{string-upcase}、@code{string-downcase}、@code{string-foldcase}は
R7RSの@code{scheme.char}モジュールでも提供されます。
@c COMMON

@c EN
Procedure @code{string-titlecase} is also defined in SRFI-129.
@c JP
@code{string-titlecase}はSRFI-129でも定義されています。
@c COMMON
@end defun

@defun codepoints-upcase sequence
@defunx codepoints-downcase sequence
@defunx codepoints-titlecase sequence
@defunx codepoints-foldcase sequence
@c MOD gauche.unicode
@c EN
Like @code{string-upcase} etc, but these work on a sequence of
codepoints instead.  Returns a sequence of the same type of the input.
@c JP
@code{string-upcase}などと同じですが、文字列ではなくコードポイント例を対象にします。
戻り値は入力と同じ型になります。
@c COMMON

@example
(codepoints-upcase '#(115 116 114 97 223 101))
 @result{} #(83 84 82 65 83 83 69)
@end example
@end defun

@defun string-ci=? string1 string2 string3 @dots{}
@defunx string-ci<? string1 string2 string3 @dots{}
@defunx string-ci<=? string1 string2 string3 @dots{}
@defunx string-ci>? string1 string2 string3 @dots{}
@defunx string-ci>=? string1 string2 string3 @dots{}
[R7RS char]
@c MOD gauche.unicode
@c EN
Case-insensitive string comparison, using full-string case conversion.
@c JP
文字列全体の大文字小文字変換を使って、大文字小文字の違いを無視した文字列比較を行います。
@c COMMON

@c EN
Note that Gauche has builtin @code{string-ci=?} etc., which use
character-wise case folding (@pxref{String comparison}).  These are
different procedures.
@c JP
Gaucheは組み込みで@code{string-ci=?}などを持っていますが、そちらは
文字ごとの大文字小文字変換を使います(@ref{String comparison}参照)。
それとは異なる手続きです。
@c COMMON

@example
(string-ci=? "\u00df" "SS") @result{} #t
@end example
@end defun

@node East asian width property,  , Full string case conversion, Unicode utilities
@subsection East asian width property
@c NODE 東アジア文字幅プロパティ

@defun char-east-asian-width char-or-codepoint
@c MOD gauche.unicode
@c EN
The argument may be a character or a nonnegative integer of Unicode
codepoint.  Returns one of the symbols @code{N} (neutral),
@code{F} (fullwidth), @code{H} (halfwidth), @code{W} (wide),
@code{Na} (narrow), and @code{A} (ambiguous).

The meaning of this property is explained in Unicode standard annex #11,
@url{http://unicode.org/reports/tr11/}.
@c JP
引数は文字か、Unicodeコードポイントを表す非負整数でなければなりません。
次のいずれかのシンボルを返します:
@code{N} (neutral)、
@code{F} (fullwidth)、 @code{H} (halfwidth)、 @code{W} (wide)、
@code{Na} (narrow)、@code{A} (ambiguous)。

各シンボルの意味についてはUnicode standard annex #11を参照してください:
@url{http://unicode.org/reports/tr11/}。
@c COMMON
@end defun

@defun string-east-asian-width str :key F H W Na N A
@c MOD gauche.unicode
@c EN
Computes the 'width' of the given string @var{str}, taking each character's
East Asian Width int account.  It gives you a rough estimate of
how much space the string will occupy on the screen, when displayed
with monospace fonts.
@c JP
東アジア文字幅プロパティを考慮して、文字列@var{str}の「幅」を計算して返します。
この幅は、概ね文字列を等幅フォントでターミナルに表示した場合の近似と考えることが
できます。
@c COMMON

@c EN
Although it is true that the exact width is generally undecidable without
actually rendering them with glyphs, heuristics can give a good estimate
if the string consists of limited scripts.  For example, if the string
is with ASCII and CJK ideographs, computing 'Full-width' and 'Wide'
letters as twice wide as ASCII character is likely to work.
@c JP
もちろん実際に文字列が表示された時にどのくらいの幅を取るかは、実際にグリフを使って
レンダリングしてみないとわかりません。が、文字列の構成要素がある程度限られている
場合は、ヒューリスティクスでだいたいうまくいきます。
例えば文字列がASCII文字とCJK漢字からなる場合、'Full-width'と'Wide'
プロパティの文字をASCII文字の2倍幅とみなすことができるでしょう。
@c COMMON

@c EN
This procedure assigns the following widths for each character's
East Asian Width category.  They can be altered by giving
keyword arguments @code{F}, @code{H}, @code{W}, @code{Na}, @code{N},
and @code{A}, respectively:
@c JP
この手続きは、各文字の「東アジア文字幅プロパティ」カテゴリに次の幅を割り当てます。
キーワード引数@code{F}, @code{H}, @code{W}, @code{Na}, @code{N}, @code{A}
によってそれぞれの幅に違う値を割り当てることも可能です。
@c COMMON

@table @asis
@item F (Full width)
2
@item H (Half width)
1
@item W (Wide)
2
@item Na (Narrow)
1
@item N (Neutral)
1
@item A (Ambiguous)
2
@end table

@c EN
See UAX #11 (@url{http://unicode.org/reports/tr11/}), section 5,
for more detailed discussions of computing the width of displayed strings.
@c JP
文字幅の考慮について詳しくは、UAX #11 (@url{http://unicode.org/reports/tr11/})
の5節を見てください。
@c COMMON

@example
(string-east-asian-width "abc") @result{} 3
(string-east-asian-width "いろは") @result{} 6
(string-east-asian-width "1番目" :W 1.5) @result{} 4.0
@end example
@end defun

@defun string-take-width str width :key F H W Na N A
@defunx string-drop-width str width :key F H W Na N A
@c MOD gauche.unicode
@c EN
Like @code{string-take} and @code{string-drop} (@pxref{String library}),
returns a prefix and
suffix of the input string @var{str}, but using the string's width
instead of the number of characters.
@c JP
@code{string-take}と@code{string-drop} (@ref{String library}参照) のように、
文字列@var{str}を指定箇所で切った前部分と後部分を返しますが、
文字数で切るかわりに文字の幅で切ります。
@c COMMON

@c EN
@code{string-take-width} returns the longest prefix of a
string @var{str} such that its @code{string-east-asian-width} does
not exceed @var{width}.  On the other hand, @code{string-drop-width}
removes such prefix from @var{str} and returns the rest.
@c JP
@code{string-take-width}は、@var{str}のプレフィクスのうち、
その@code{string-east-asian-width}が@var{width}を越えない部分を返します。
一方@code{string-drop-width}はそのプレフィクスを取り除いた部分を返します。
@c COMMON

@c EN
The keyword arguments are to customize mappings of East Asian Width
categories to numerical widths.  See @code{string-east-asian-width}
above for the details.
@c JP
キーワード引数は東アジア文字幅のカテゴリから幅へのマッピングをカスタマイズするものです。
詳しくは上の@code{string-east-asian-width}の説明を見てください。
@c COMMON
@end defun

@c ----------------------------------------------------------------------
@node Uniform vector library, Comparing version numbers, Unicode utilities, Library modules - Gauche extensions
@section @code{gauche.uvector} - Uniform vector library
@c NODE ユニフォームベクタライブラリ, @code{gauche.uvector} - ユニフォームベクタライブラリ

@deftp {Module} gauche.uvector
@mdindex gauche.uvector
@c EN
Provides procedures that work on uniform vectors
(@pxref{Uniform vectors}).
This module is a superset of R7RS uniform vector library
(@code{scheme.vector.@@}) and SRFI-4.
@c JP
ユニフォームベクタを扱う手続きを提供します
(@ref{Uniform vectors}参照)。
このモジュールは、R7RSユニフォームベクタライブラリ
(@code{scheme.vector.@@})とSRFI-4のスーパーセットです。
@c COMMON

@c EN
The @code{@@} part is actually one of @code{u8}, @code{s8}, @code{u16},
@code{s16}, @code{u32}, @code{s32}, @code{u64}, @code{s64},
@code{f16}, @code{f32}, @code{f64}, @code{c32}, @code{c64} or @code{c128}.
@c JP
@code{@@}の部分は実際には要素の型を示す次のタグのいずれかです:
@code{u8}, @code{s8}, @code{u16},
@code{s16}, @code{u32}, @code{s32}, @code{u64}, @code{s64},
@code{f16}, @code{f32}, @code{f64}, @code{c32}, @code{c64}, @code{c128}。
@c COMMON

@end deftp

@c EN
Gauche's extension to SRFI-160 is as follows:
@c JP
Gaucheで拡張されている機能は次のとおりです:
@c COMMON
@itemize @bullet
@item
@c EN
Support of @code{f16vector} and @code{c32vector}, using 16-bit floating
point numbers as used in high-dynamic range image format.
@c JP
HDR画像フォーマットなどで使われる、16ビット浮動小数点数を使った
@code{f16vector}と@code{c32vector}のサポート。
@c COMMON
@item
@c EN
Efficient element-wise arithmetic procedures, e.g. @code{@@vector-add}.
@c JP
@code{@@vector-add}など、効率の良い要素単位の演算手続き。
@c COMMON
@item
@c EN
Implements the collection framework (@pxref{Collection framework})
and the sequence framework (@pxref{Sequence framework}).  So the
methods like @code{map}, @code{for-each}, @code{ref} or @code{subseq}
can be used.
@c JP
コレクションフレームワーク (@ref{Collection framework}参照)と
シーケンスフレームワーク (@ref{Sequence framework}参照)の実装。
例えば @code{map}, @code{for-each}, @code{ref}, @code{subseq}等の
メソッドが使えます。
@c COMMON
@item
@c EN
Some routines takes optional parameters: @code{@@vector-ref}
takes optional fallback value.
@c JP
いくつかの手続きはSRFI-160に無い省略可能な引数を取ります。
例えば@code{@@vector-ref}は省略可能なデフォルト値を取ります。
@c COMMON
@end itemize

@c EN
When you try to store a number out of the range of the vector type,
an error is signaled by default.  However, some procedures take
an optional argument @var{clamp} that specifies alternative behavior
in such a case.  @var{Clamp} argument may take one of the following values.
@c JP
ベクタの型が許す範囲外の値を格納しようとした場合、通常はエラーとなります。
いくつかの手続きは省略可能な引数@var{clamp}によって、
そのような場合に別のふるまいを指定することができます。
@var{clamp}には以下のいずれかの値を与えることが出来ます。
@c COMMON
@table @code
@item #f
@c EN
Default behavior (signals an error).
@c JP
デフォルト (エラーを通知)
@c COMMON
@item high
@c EN
Clamps high bound; i.e. if the value to be stored is beyond the higher bound
of the range, the maximum value is stored instead.
@c JP
高い方の値をクランプ、すなわち、格納しようとする値が許される値の最大値より大きかった
場合は、可能な最大値を代わりに格納します。
@c COMMON
@item low
@c EN
Clamps low bound; i.e. if the value to be stored is below the lower bound
of the range, the minimum value is stored instead.
@c JP
低い方の値をクランプ、すなわち、格納しようとする値が許される値の最小値より大きかった
場合は、可能な最小値を代わりに格納します。
@c COMMON
@item both
@c EN
Clamps both sides; does both @code{high} and @code{low}.
@c JP
高いほうと低いほうの両方の値をクランプします。
@c COMMON
@end table

@example
(list->u8vector '(-1))         @result{} @r{error}
(list->u8vector '(-1) 'low)    @result{} #u8(0)
(list->u8vector '(-1) 'high)   @result{} @r{error}
(list->u8vector '(3000) 'high) @result{} #u8(255)
(list->u8vector '(-100 20 300) 'both) @result{} #u8(0 20 255)
@end example

@c EN
In the following description, @code{@@} can be replaced
for any of @code{s8}, @code{u8}, @code{s16}, @code{u16},
@code{s32}, @code{u32}, @code{s64}, @code{u64},
@code{f16}, @code{f32}, @code{f64}, @code{c32}, @code{c64} or @code{c128}.
@c JP
以下の記述では、@code{@@}は
@code{s8}, @code{u8}, @code{s16}, @code{u16},
@code{s32}, @code{u32}, @code{s64}, @code{u64},
@code{f16}, @code{f32}, @code{f64}, @code{c32}, @code{c64}, @code{c128}
のいずれにも置き換えて読むことができるものとします。
@c COMMON

@c EN
Note: R7RS-large provides separate library for each type,
and you should import them individually, for example,
@code{(use scheme.vector.u8)} (Gauche way) or
@code{(import (scheme vector u8))} (R7RS way).

On the other hand, using @code{gauche.uvector} imports all the bindings.
@c JP
註： R7RS-largeでは、それぞれの型に対して個別のライブラリがあり、
例えば@code{u8}ベクタが使いたければ
@code{(use scheme.vector.u8)} (Gauche式)
あるいは @code{(import (scheme vector u8))} (R7RS式)
のようにする必要があります。

一方、@code{gauche.uvector}を使った場合は全ての手続きがインポートされます。
@c COMMON

@menu
* Uvector basic operations::
* Uvector conversion operations::
* Uvector numeric operations::
* Uvector block I/O::
* Bytevector compatibility::
@end menu

@node Uvector basic operations, Uvector conversion operations, Uniform vector library, Uniform vector library
@subsection Uvector basic operations
@c NODE ユニフォームベクタの基本操作

@c EN
The following procedures are built-in; @pxref{Uniform vectors}:
@c JP
次の手続きは組み込みです。@ref{Uniform vectors}参照:
@c COMMON

@example
make-@@vector
uvector?          @@vector?
uvector-ref       @@vector-ref
uvector-set!      @@vector-set!
uvector-length
@end example

@deffn {Function} @@? obj
@findex s8?
@findex u8?
@findex s16?
@findex u16?
@findex s32?
@findex u32?
@findex s64?
@findex u64?
@findex f16?
@findex f32?
@findex f64?
@findex c32?
@findex c64?
@findex c128?
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns @code{#t} iff @var{obj} can be an element of @code{@@vector}.
@c JP
引数が@@ベクタの要素に収まるなら@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON

@example
(u8? 3)    @result{} #t
(u8? -1)   @result{} #f
(u8? 256)  @result{} #f
(u16? 256) @result{} #t
(s8? -1)   @result{} #t
(s8? 128)  @result{} #f
@end example
@end deffn

@defun uvector-class-valid-element? class obj
@c MOD gauche.uvector
@c EN
Generic version of @code{u8?} etc.  Takes a @var{class}, which must
be one of subclasses of @code{<uvector>}, and returns @code{#t}
if @var{obj} is suitable as an element of the instance of @var{class},
or @var{#f} otherwise.
@c JP
@code{u8?}等のジェネリックなバージョンです。
@var{class}は@code{<uvector>}のサブクラスでなければなりません。
@var{obj}が@var{class}のインスタンスの要素として有効であれば
@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON

@example
(uvector-class-valid-element? <u16vector> 65535) @result{} #t
(uvector-class-valid-element? <u16vector> 65536) @result{} #f
(uvector-class-valid-element? <s16vector> 32768) @result{} #f
(uvector-class-valid-element? <s16vector> 'a) @result{} #f
@end example
@end defun


@deffn {Function} @@vector-empty? obj
@findex u8vector-empty?
@findex s8vector-empty?
@findex u16vector-empty?
@findex s16vector-empty?
@findex u32vector-empty?
@findex s32vector-empty?
@findex u64vector-empty?
@findex s64vector-empty?
@findex f16vector-empty?
@findex f32vector-empty?
@findex f64vector-empty?
@findex c32vector-empty?
@findex c64vector-empty?
@findex c128vector-empty?
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
The argument must be a @@vector.
Returns @code{#t} iff it is empty.
@c JP
引数は@@vectorでなければなりません。
それが空なら@code{#t}を、そうでなければ@var{#f}を返します。
@c COMMON
@end deffn

@deffn {Function} @@vector x @dots{}
@findex s8vector
@findex u8vector
@findex s16vector
@findex u16vector
@findex s32vector
@findex u32vector
@findex s64vector
@findex u64vector
@findex f16vector
@findex f32vector
@findex f64vector
@findex c32vector
@findex c64vector
@findex c128vector
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Constructs @@vector whose elements are numbers @var{x} @dots{}.
The numbers must be exact integer for exact integer vectors,
and in the valid range of the vector.
@c JP
数値@var{x} @dots{} を要素に持つ@@vectorを作成して返します。
正確な整数のベクタに対しては、数値は正確な整数でなければならず、
また有効な範囲内の値でなければなりません。
@c COMMON
@example
(s8vector 1 2 3) @result{} #s8(1 2 3)
@end example
@end deffn

@defun make-uvector @code{class} @code{len} :optional @code{fill}
@c MOD gauche.uvector
@c EN
This is a Gauche extension; instead of using separate constructor for
each uvector type, you can pass the class of desired uvector.

Type-specific constructors (@code{make-s8vector} etc.) are defined
in the core library (@pxref{Uniform vectors}).
@c JP
これはGaucheの拡張です。各ユニフォームベクタの型に対応する関数を呼ぶかわりに、
欲しいユニフォームベクタのクラスを渡してベクタを作ることができます。

型ごとのコンストラクタ (@code{make-s8vector}等)はコアのライブラリで提供
されています (@ref{Uniform vectors}参照)。
@c COMMON

@example
(make-uvector <u8vector> 3)    @result{} #u8(0 0 0)
(make-uvector <s8vector> 5 -1) @result{} #s8(-1 -1 -1 -1 -1)
@end example
@end defun

@deffn {Function} @@vector-unfold f len seed
@deffnx {Function} @@vector-unfold-right f len seed
@findex u8vector-unfold
@findex s8vector-unfold
@findex u16vector-unfold
@findex s16vector-unfold
@findex u32vector-unfold
@findex s32vector-unfold
@findex u64vector-unfold
@findex s64vector-unfold
@findex f16vector-unfold
@findex f32vector-unfold
@findex f64vector-unfold
@findex c32vector-unfold
@findex c64vector-unfold
@findex c128vector-unfold
@findex u8vector-unfold-right
@findex s8vector-unfold-right
@findex u16vector-unfold-right
@findex s16vector-unfold-right
@findex u32vector-unfold-right
@findex s32vector-unfold-right
@findex u64vector-unfold-right
@findex s64vector-unfold-right
@findex f16vector-unfold-right
@findex f32vector-unfold-right
@findex f64vector-unfold-right
@findex c32vector-unfold-right
@findex c64vector-unfold-right
@findex c128vector-unfold-right
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Construct a @@vector of length @var{len}, with each element
as a result of @code{(f seed)}, @code{(f (f seed))},
@code{(f (f (f seed)))}, @dots{}.
@@vector-unfold fills the element from left to right,
while @@vector-unfold-right from right to left.
@c JP
長さ@var{len}の@@vectorを作り、
@code{(f seed)}、@code{(f (f seed))}、
@code{(f (f (f seed)))}、@dots{} の結果を順に要素とします。
@@vector-unfoldは左から右に、
@@vector-unfold-rightは右から左に埋めてゆきます。
@c COMMON
@example
(u8vector-unfold (cut + 2 <>) 5 0)
 @result{} #u8(2 4 6 8 10)
(u8vector-unfold-right (pa$ + 2) 5 0)
 @result{} #u8(10 8 6 4 2)
@end example
@end deffn

@deffn {Function} @@vector-unfold! f vec start end seed
@deffnx {Function} @@vector-unfold-right! f vec start end seed
@findex u8vector-unfold!
@findex s8vector-unfold!
@findex u16vector-unfold!
@findex s16vector-unfold!
@findex u32vector-unfold!
@findex s32vector-unfold!
@findex u64vector-unfold!
@findex s64vector-unfold!
@findex f16vector-unfold!
@findex f32vector-unfold!
@findex f64vector-unfold!
@findex c32vector-unfold!
@findex c64vector-unfold!
@findex c128vector-unfold!
@findex u8vector-unfold-right!
@findex s8vector-unfold-right!
@findex u16vector-unfold-right!
@findex s16vector-unfold-right!
@findex u32vector-unfold-right!
@findex s32vector-unfold-right!
@findex u64vector-unfold-right!
@findex s64vector-unfold-right!
@findex f16vector-unfold-right!
@findex f32vector-unfold-right!
@findex f64vector-unfold-right!
@findex c32vector-unfold-right!
@findex c64vector-unfold-right!
@findex c128vector-unfold-right!
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Fill an @@vector @var{vec} between @var{start}-th index (inclusive)
and @var{end}-th index (exclusive), with the values generated by @var{f},
which is called with two arguments, the integer index and
the current seed value.

In @code{@@vector-unfold!}, @var{f} is first called with
@var{start} and @var{seed}.  It must return two values,
the element to put to @var{vec} and the next seed value.
Then @var{f} is called with @var{start} + 1 and the previously
returnd seed value, and so on, until @var{end} - @var{start} elements
are generated.

@code{@@vector-unfold-right!} works similarly, but the elements
are generated from right (@var{end}-1) to left (@var{start}).

If @var{start} >= @var{end}, @var{f} is never called and @var{vec} isn't
altered.  It is an error if the index falls out of range of @var{vec}.

Return an unspecified value.
@c JP
@@vectorである@var{vec}の、@var{start}要素目(含む)から@var{end}要素目(含まない)
までを、@var{f}の呼び出し結果で埋めてゆきます。@var{f}は整数のインデックスと
現在のシード値を引数にして呼ばれます。

@code{@@vector-unfold!}では、@var{f}はまず@var{start}と@var{seed}を引数にして
呼ばれます。@var{f}は@var{start}に埋めるべき値と次のシード値の2値を返さねばなりません。
次に@var{f}は@var{start}+1と戻されたシード値を引数に呼ばれ…と、
それが@var{end}-@var{start}回繰り返されます。

@code{@@vector-unfold-right!}も同様に動作しますが、右から左、
つまり@var{end}-1から始めて@var{start}に向けて値が埋めてゆかれます。

@var{start} >= @var{end} であった場合、@var{f}は呼ばれることなく、
@var{vec}は変更されません。もしインデックスが@var{vec}の範囲の外に出た場合は
エラーが投げられます。

戻り値は未規定です。
@c COMMON
@end deffn


@deffn {Function} @@vector-length vec
@findex u8vector-length
@findex s8vector-length
@findex u16vector-length
@findex s16vector-length
@findex u32vector-length
@findex s32vector-length
@findex u64vector-length
@findex s64vector-length
@findex f16vector-length
@findex f32vector-length
@findex f64vector-length
@findex c32vector-length
@findex c64vector-length
@findex c128vector-length
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns the length of the @@vector @var{vec}.

Note that the generic function @code{size-of} can be used
to obtain the length of @var{vec} as well,
if you import @code{gauche.collection}
(@pxref{Collection framework}).
@c JP
@@vector @var{vec}の長さを返します。

モジュール@code{gauche.collection}をインポートしていれば、
@var{vec}の長さを知るのに、総称関数@code{size-of}を使うこともできます
(@ref{Collection framework}参照)。
@c COMMON
@example
(s16vector-length '#s16(111 222 333)) @result{} 3

(use gauche.collection)
(size-of '#s16(111 222 333)) @result{} 3
@end example
@end deffn

@defun uvector-size uvector :optional start end
@c MOD gauche.uvector
@c EN
This function can be applied to any type of uniform vectors, and
returns the raw size of the @var{uvector} in number of octets.

When @var{start} and/or @var{end} is/are given, the size of data
between those indices are calculated.  The special value @code{-1}
for @var{end} indicates the end of the vector.
The returned value matches the number of octets to be written out
by @code{(write-uvector @var{uvector} port @var{start} @var{end})}.

(Do not confuse this with @code{uvector-length}, which returns
the number of elements.)
@c JP
この手続きは全てのユニフォームベクタに適用することができます。
@var{uvector}のバイナリデータとしてのサイズをオクテット数で返します。

@var{start}および/または@var{end}が与えられた場合は、
これらのインデックスの間のデータについてのみサイズが計算されます。
@var{end}には、ベクタ終端を示すために@code{-1}を与えることもできます。
返される値は
@code{(write-uvector @var{uvector} port @var{start} @var{end})} によって
出力されるオクテット数と一致します。

(要素数を返す@code{uvector-length}と混同しないようにしてください。)
@c COMMON

@example
(uvector-size '#u8(1 2 3))        @result{} 3
(uvector-size '#u64(1 2 3))       @result{} 24

(uvector-size '#u32(0 1 2 3) 2)   @result{} 8
(uvector-size '#u32(0 1 2 3) 0 1) @result{} 4
@end example
@end defun

@defun uvector-class-element-size class
@c MOD gauche.uvector
@c EN
Returns the size of an element of a uvector of the given class, in bytes.
An error is raised when @var{class} is not a uvector class.
@c JP
与えられたクラスのユニフォームベクタの1要素が占める大きさをバイト数で返します。
@var{class}がユニフォームベクタのクラスでない場合はエラーが投げられます。
@c COMMON

@example
(uvector-class-element-size <u8vector>)  @result{} 1
(uvector-class-element-size <s64vector>) @result{} 8
@end example
@end defun

@deffn {Function} @@vector-swap! vec i j
@findex u8vector-swap!
@findex s8vector-swap!
@findex u16vector-swap!
@findex s16vector-swap!
@findex u32vector-swap!
@findex s32vector-swap!
@findex u64vector-swap!
@findex s64vector-swap!
@findex f16vector-swap!
@findex f32vector-swap!
@findex f64vector-swap!
@findex c32vector-swap!
@findex c64vector-swap!
@findex c128vector-swap!
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Interchanges @var{i}th and @var{j}th elements of the uvector @var{vec}.
Return value is not specified.
@c JP
ユニフォームベクタ@var{vec}の@var{i}番目と@var{j}番目の要素を入れ替えます。
戻り値は規定されていません。
@c COMMON
@end deffn

@deffn {Function} @@vector-fill! vec fill :optional start end
@findex u8vector-fill!
@findex s8vector-fill!
@findex u16vector-fill!
@findex s16vector-fill!
@findex u32vector-fill!
@findex s32vector-fill!
@findex u64vector-fill!
@findex s64vector-fill!
@findex f16vector-fill!
@findex f32vector-fill!
@findex f64vector-fill!
@findex c32vector-fill!
@findex c64vector-fill!
@findex c128vector-fill!
@c MOD gauche.uvector
@c EN
Stores @var{fill} in every element of @var{vec},
ranging from @var{start} to @var{end} of @var{vec},
if they are given.
Return value is not specified.
@c JP
@var{vec}のすべて要素に@var{fill}をセットします。
@var{start}と@var{end}で要素の範囲を指定することも出来ます。
戻り値は規定されていません。
@c COMMON
@end deffn

@deffn {Function} @@vector= @var{vec1} @dots{}
@findex u8vector=
@findex s8vector=
@findex u16vector=
@findex s16vector=
@findex u32vector=
@findex s32vector=
@findex u64vector=
@findex s64vector=
@findex f16vector=
@findex f32vector=
@findex f64vector=
@findex c32vector=
@findex c64vector=
@findex c128vector=
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
All arguments must be @@vectors.  Returns @code{#t} iff
all arguments have the same length and has the same values (in terms of @code{=})
at the corresponding position. Zero arguments
return @var{#t}.

Note that in Gauche you can compare uvectors with @code{equal?}as well.
@c JP
全ての引数は@@vectorでなければなりません。
引数が全て同じ長さで、対応する要素が同じ価(@code{=}の意味で)なら@code{#t}を、
そうでなければ@code{#f}を返します。

Gaucheでは、uvectorは@code{equal?}で比較することができます。
@c COMMON
@end deffn


@deffn {Function} @@vector=? @var{vec1} @var{vec2}
@findex u8vector=?
@findex s8vector=?
@findex u16vector=?
@findex s16vector=?
@findex u32vector=?
@findex s32vector=?
@findex u64vector=?
@findex s64vector=?
@findex f16vector=?
@findex f32vector=?
@findex f64vector=?
@findex c32vector=?
@findex c64vector=?
@findex c128vector=?
[SRFI-66]
@c MOD gauche.uvector
@c EN
Note: This is provided only for the SRFI-66 compatibility.
Use @code{@@vector=} instead.

Both arguments must be a @@vector.  Returns @code{#t} if
@var{vec1} and @var{vec2} are equal to each other, @code{#f} otherwise.
@c JP
註: これはSRFI-66との互換性のためだけに提供されています。
@code{@@vector=} を使ってください。

引数はどちらも@@vectorでなければなりません。
両引数が等価なら@code{#t}が、そうでなければ@code{#f}が返されます。
@c COMMON
@end deffn

@deffn {Function} @@vector-compare @var{vec1} @var{vec2}
@findex u8vector-compare
@findex s8vector-compare
@findex u16vector-compare
@findex s16vector-compare
@findex u32vector-compare
@findex s32vector-compare
@findex u64vector-compare
@findex s64vector-compare
@findex f16vector-compare
@findex f32vector-compare
@findex f64vector-compare
@findex c32vector-compare
@findex c64vector-compare
@findex c128vector-compare
[SRFI-66]
@c MOD gauche.uvector
@c EN
Both arguments must be a @@vector.  Returns @code{-1} if
@var{vec1} is smaller than @var{vec2},
@code{0} if both are equal to each other,
and @code{1} if @var{vec1} is greater than @var{vec2}.

Shorter vector is smaller than longer vectors.  If the lengths of
both vectors are the same, elements are compared from left to right.

Note that you can compare uvectors with @code{compare} in Gauche.
These are provided because SRFI-66 defines @code{u8vector-compare}.
You can also use them to indicate arguments are vectors of the specific type.
@c JP
引数はどちらも@@vectorでなければなりません。
@var{vec1}が@var{vec2}よりも小さければ@code{-1}が、
両者が等しければ@code{0}が、
@var{vec1}が@var{vec2}よりも大きければ@code{1}が返されます。

短い方のベクタが常に小さいと評価されます。長さが等しい場合は要素を左から順に比較します。

Gaucheでは、uvectorは@code{compare}で比較することができます。
これらの手続きが提供されるのは、SRFI-66が@code{u8vector-compare}を定義しているためです。
引数が特定の型のベクタであることを明示したい場合に使っても良いでしょう。
@c COMMON
@end deffn

@deffn {Function} @@vector-copy vec :optional start end
@findex u8vector-copy
@findex s8vector-copy
@findex u16vector-copy
@findex s16vector-copy
@findex u32vector-copy
@findex s32vector-copy
@findex u64vector-copy
@findex s64vector-copy
@findex f16vector-copy
@findex f32vector-copy
@findex f64vector-copy
@findex c32vector-copy
@findex c64vector-copy
@findex c128vector-copy
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns a fresh copy of uniform vector @var{vec}.
If @var{start} and/or @var{end} are given, they limit the range of
@var{vec} to be copied.
@c JP
ベクタ@var{vec}の新たなコピーを返します。
省略可能な引数@var{start}と@var{end}が与えられた場合、
それらは取り出される要素の範囲を制限します。
@c COMMON

@example
(u8vector-copy '#u8(1 2 3 4))     @result{} #u8(1 2 3 4)
(u8vector-copy '#u8(1 2 3 4) 2)   @result{} #u8(3 4)
(u8vector-copy '#u8(1 2 3 4) 1 3) @result{} #u8(2 3)
@end example
@end deffn

@defun uvector-copy vec :optional start end
@c MOD gauche.uvector
@c EN
This is a generic version of @code{@@vector-copy}.
You can give any type of uvector to @var{vec}, and get its copy
(or copy of its part, depending on @var{start}/@var{end} argument).
@c JP
これは@code{@@vector-copy}の汎用バージョンです。
どんな型のuvectorでも@var{vec}に渡すことができ、そのコピー
(もしくは、@var{start}/@var{end}によっては一部のコピー)が返されます。
@c COMMON
@end defun

@deffn {Function} @@vector-reverse-copy vec :optional start end
@findex u8vector-reverse-copy
@findex s8vector-reverse-copy
@findex u16vector-reverse-copy
@findex s16vector-reverse-copy
@findex u32vector-reverse-copy
@findex s32vector-reverse-copy
@findex u64vector-reverse-copy
@findex s64vector-reverse-copy
@findex f16vector-reverse-copy
@findex f32vector-reverse-copy
@findex f64vector-reverse-copy
@findex c32vector-reverse-copy
@findex c64vector-reverse-copy
@findex c128vector-reverse-copy
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Copies @var{vec} between @var{strat} and @var{end} index, but
reversing it.
@c JP
@var{vec}の要素を逆順にしたコピーを作って返します。
省略可能な@var{start}と@var{end}はコピー範囲を限定します。
@c COMMON
@example
(u8vector-reverse-copy '#u8(1 2 3 4 5))
  @result{} #u8(5 4 3 2 1)

(u8vector-reverse-copy '#u8(1 2 3 4 5) 1 4)
  @result{} #u8(4 3 2)
@end example
@end deffn

@deffn {Function} @@vector-copy! target tstart source :optional sstart send
@findex u8vector-copy!
@findex s8vector-copy!
@findex u16vector-copy!
@findex s16vector-copy!
@findex u32vector-copy!
@findex s32vector-copy!
@findex u64vector-copy!
@findex s64vector-copy!
@findex f16vector-copy!
@findex f32vector-copy!
@findex f64vector-copy!
@findex c32vector-copy!
@findex c64vector-copy!
@findex c128vector-copy!
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Both @var{target} and @var{source} must be @@vectors, and
@var{target} must be mutable.
This procedure copies the elements of @var{source}, beginning from index
@var{sstart} (inclusive) and up to @var{send}, into @var{target},
beginning from index @var{tstart}.  @var{sstart} and @var{send}
may be omitted, and in that case 0 and the length of @var{source}
are assumed, respectively.
@c JP
@var{target} および @var{source} はともに @@vector でなければ
なりません。さらに、@var{target} は変更可能でなければなりません。
この手続きは、@var{source}の要素を、インデックス@var{sstart}から(これを含み)
@var{send} までを、@var{target} へインデックス @var{tstart}からコピーします。
@var{sstart}および@var{send}は省略可能で、その場合には、それぞれ、
0 および @var{source}の長さが仮定されます。
@c COMMON

@example
(let ((target (u8vector 0 1 2 3 4 5 6)))
  (u8vector-copy! target 2 '#u8(10 11 12 13 14) 1 4)
  target)
 @result{} #u8(0 1 11 12 13 6)
@end example

@c EN
If the number of elements in the source vector between @var{sstart}
and @var{send} is larger than the target vector beginning from @var{tstart},
the excess elements are silently discarded.
@c JP
もし、コピー元のベクタの @var{sstart} と @var{send} の間にある要素の
数がコピー先のベクタの@var{tstart}以降の部分よりも大きければ、超過分の
ベクタはだまって捨てられます。
@c COMMON

@c EN
It is ok to pass the same vector to @var{target} and @var{source};
it always works even if the regions of source and destination are
overlapping.
@c JP
@var{target}と@var{source}に同一のベクタを渡しても構いません。
コピー先とコピー元の領域が重なっていても、コピーは常に正しく行われます。
@c COMMON

@c EN
@emph{Note:} This procedure used to take just two uniform vectors, @var{target}
and @var{source}, and just copies contents of @var{source} to @var{target}.
Both vectors had to be the same type and same length.  The API is revised
according to SRFI-160.  The old interface is still supported
for the backward compatibility, but it is deprecated and will be gone
in the future releases.

Also note that SRFI-66 provides @code{uvector-copy!} with different
argument order (@pxref{Octet vectors}).
@c JP
@emph{注意事項:} この手続きは以前はユニフォームベクタ @var{target} および
@var{source} のみを引数としてとり、@var{source} の内容を @var{target} へ
コピーするためだけに使われました。両方のベクタは同じ型で、同じ長さでなけ
ればなりませんでした。この API はSRFI-160にあわせて現在の形式に改訂されています。
旧来のインタフェースも後方互換性のためにサポートされて
いますが、これは廃止予定で、将来のリリースではサポートされなくなります。

また、SRFI-66も@code{u8vector-copy!}を提供していますが、
引数の順序が異なります(@ref{Octet vectors}参照)。
@c COMMON
@end deffn


@defun uvector-copy! target tstart source :optional sstart send
@c MOD gauche.uvector
@c EN
This is a generic version of @code{@@vector-copy!}.
The destination @var{target} and the source @var{source} can be
any type of uniform vectors, and they don't need to match.
The copy is done bit-by-bit.  So if you copy to a different type
of uvector, the result depends on how the numbers are represented
internally.  This is mainly to manipulate binary data.

@var{Tstart} is interpreted according to the type of @var{target},
and @var{sstart} and @var{send} are interpreted according to the
type of @var{source}.
@c JP
これは@code{@@vector-copy!}の汎用バージョンです。
コピー元@var{source}とコピー先@var{target}はユニフォームベクタであれば
どの型でも許され、また両者の型が異なっていても構いません。
ビット表現がそのままコピーされます。従って異なる型のユニフォームベクタ間で
コピーした場合は、結果は数値の内部表現に依存します。
そのような用法は、バイナリデータを扱う時には便利でしょう。

@var{tstart}は@var{target}の型によって解釈され、
@var{sstart}と@var{send}は@var{source}の型によって解釈されます。
@c COMMON

@example
(rlet1 v (make-u8vector 6 0)
  (uvector-copy! v 1 '#u32(0 #x01020304 0) 1 2))
 @result{} #u8(0 1 2 3 4 0) or #u8(0 4 3 2 1 0)
@end example
@end defun

@deffn {Function} @@vector-reverse! vec :optional start end
@findex u8vector-reverse!
@findex s8vector-reverse!
@findex u16vector-reverse!
@findex s16vector-reverse!
@findex u32vector-reverse!
@findex s32vector-reverse!
@findex u64vector-reverse!
@findex s64vector-reverse!
@findex f16vector-reverse!
@findex f32vector-reverse!
@findex f64vector-reverse!
@findex c32vector-reverse!
@findex c64vector-reverse!
@findex c128vector-reverse!
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
The argument @var{vec} must be mutable.
Reverses contents of @var{vec} in-place, and returns an undefined value.
If the optional integer index @var{start} and @var{end} are given,
only the elements in the range (including @var{start}, excluding @var{end})
are modified.

(Note: This is not a ``linear update'' version.  It is guaranteed that
@var{vec} is modified.)
@c JP
@var{vec}は変更可能でなければなりません。
@var{vec}の要素の順序を逆転させて書き込み、未定義値を返します。
省略可能な整数インデックス@var{start}と@var{end}が与えられた場合は、
@var{start}番目(含む)から@var{end}番目(含まない)までの要素に限って
変更します。

(注: これは「線形更新」バージョンとは異なり、
@var{vec}が変更されることは保証されています)。
@c COMMON

@example
(define v (u8vector 1 2 3 4 5 6))

(u8vector-reverse! v 1 5) @result{} #<undef>
v @result{} #u8(1 5 4 3 2 6)
@end example
@end deffn

@deffn {Function} @@vector-reverse-copy! target tstart source :optional start end
@findex u8vector-reverse-copy!
@findex s8vector-reverse-copy!
@findex u16vector-reverse-copy!
@findex s16vector-reverse-copy!
@findex u32vector-reverse-copy!
@findex s32vector-reverse-copy!
@findex u64vector-reverse-copy!
@findex s64vector-reverse-copy!
@findex f16vector-reverse-copy!
@findex f32vector-reverse-copy!
@findex f64vector-reverse-copy!
@findex c32vector-reverse-copy!
@findex c64vector-reverse-copy!
@findex c128vector-reverse-copy!
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Similar to @code{@@vector-copy!}, but the source elements are copied in
reverse order.
@c JP
@code{@@vector-copy!}とほぼ同じですが、@var{source}ベクタの要素が
逆順でコピーされます。
@c COMMON

@example
(rlet1 v (s8vector 0 1 2 3 4 5 6 7)
  (s8vector-reverse-copy! v 1 '#s8(0 -1 -2 -3 -4 -5) 1 5))
  @result{} #s8(0 -4 -3 -2 -1 5 6 7)
@end example
@end deffn



@deffn {Function} @@vector-multi-copy! target tstart tstride source :optional sstart ssize sstride count
@findex u8vector-multi-copy!
@findex s8vector-multi-copy!
@findex u16vector-multi-copy!
@findex s16vector-multi-copy!
@findex u32vector-multi-copy!
@findex s32vector-multi-copy!
@findex u64vector-multi-copy!
@findex s64vector-multi-copy!
@findex f16vector-multi-copy!
@findex f32vector-multi-copy!
@findex f64vector-multi-copy!
@findex c32vector-multi-copy!
@findex c64vector-multi-copy!
@findex c128vector-multi-copy!
@c MOD gauche.uvector
@c EN
This procedure allows different parts of the source uvector @var{source} into
various parts of the target uvector @var{target}, all at once.

When @var{ssize} is omitted or zero, this procedure does the following:
@c JP
この手続きは、コピー元ベクタ@var{source}の異なる部分を
コピー先ベクタ@var{target}の異なる部分へと一度にコピーするのに使えます。

@var{ssize}が省略されるか0の場合、この手続きは次の動作をします。
@c COMMON

@example
;; For each @var{i} from 0 to @var{count}:
(u8vector-copy! target (+ tstart (* i tstride))
                source sstart)
@end example

@c EN
That is, it copies the content of @var{source} (offset by @var{sstart},
which defaults to 0)
into the @var{target} repeatedly, advancing index with @var{tstride}.
If either the target index reaches the end or @var{count} copies
are made, the procedure returns.  See the example:
@c JP
つまり、@var{source}ベクタの内容 (@var{sstart}が指定されてればそこから、
指定が無ければ最初から)を@var{target}ベクタに、@var{tstride}づつインデックスを
進めながらコピーします。コピー先のインデックスが@var{target}ベクタの範囲を
越えるか、@var{count}が指定されていればその回数分だけコピーが済むかすれば
手続きは終了します。次の例を見てください。
@c COMMON

@example
(define t (make-u8vector 10 0))
(u8vector-multi-copy! t 0 4 '#u8(1 2 3))

t @result{} #u8(1 2 3 0 1 2 3 0 1 2)
@end example

@c EN
If @var{ssize} is given and positive, the source is also splitted
as follows:
@c JP
@var{ssize}に正の整数が与えられた場合は、コピー元ベクタも@var{ssize}ごとに
分割されます。
@c COMMON

@example
;; For each @var{i} from 0 to @var{count}:
(u8vector-copy! target (+ tstart (* i tstride))
                source (+ sstart (* i sstride))
                       (+ sstart (* i sstride) ssize))
@end example

@c EN
That is, each @var{ssize} slice from @var{source},
 is copied into @var{target}, advancing source index
by @var{sstride} and the destination index by @var{dstride}.
In this case, @var{sstride} defaults to @var{ssize} if omitted.
@c JP
つまり、コピー元インデックスを@var{sstride}づつ、コピー先を
@var{dstride}づつ増やしながら、コピー元からそれぞれ@var{ssize}分のデータが切り出されて
@var{target}にコピーされます。この場合、@var{sstride}は省略されると
@var{ssize}と同じになります。
@c COMMON

@example
(define t (make-u8vector 12 0))
(u8vector-multi-copy! t 0 4 '#u8(1 2 3 4 5 6 7 8 9) 0 3)

t @result{} #u8(1 2 3 0 4 5 6 0 7 8 9 0)
@end example

@c EN
The operation ends when either @var{count} slices are copied,
or destination index or source index reaches the end.
@c JP
操作は@var{count}個のデータ片がコピーされるか、コピー元あるいはコピー先の
インデックスがそれぞれのベクタの終端に達したら終わります。
@c COMMON

@c EN
Hint: If you want to copy a part of the source vector repeatedly
(instead of to its end), you can specify 0 to @var{sstride}:
@c JP
ヒント: コピー元のベクタの中程だけ (最後までではなく) をコピーしたい場合は、
@var{sstride}に0を与えればできます。
@c COMMON

@example
(define t (make-u8vector 12 0))
(u8vector-multi-copy! t 0 4 '#u8(1 2 3 4 5 6 7 8 9) 2 4 0)

t @result{} #u8(3 4 5 6 3 4 5 6 3 4 5 6)
@end example
@end deffn


@c EN
Using collection and sequence framework, you can perform
various operations on the homogeneous vectors.
@c JP
コレクションやシーケンスフレームワークを使うと、さらに様々な操作を
行うことができます。
@c COMMON

@example
(use gauche.collection)
(use gauche.sequence)

(fold + 0 '#s32(1 2 3 4)) @result{} 10

(map-to <f32vector> * '#f32(3.2 1.1 4.3) '#f32(-4.3 2.2 9.4))
  @result{} #f32(-13.760001 2.420000 40.420002)

(subseq #u32(1 4 3 4 5) 2 4) @result{} #u32(3 4)
@end example


@deffn {Function} @@vector-append vec @dots{}
@findex u8vector-append
@findex s8vector-append
@findex u16vector-append
@findex s16vector-append
@findex u32vector-append
@findex s32vector-append
@findex u64vector-append
@findex s64vector-append
@findex f16vector-append
@findex f32vector-append
@findex f64vector-append
@findex c32vector-append
@findex c64vector-append
@findex c128vector-append
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
All arguments must be @@vectors.  Returns a fresh vector
whose contents are concatenation of the given vectors.
(It returns a fresh vector even there's only one argument).
@c JP
引数はすべて@@vectorでなければなりません。
引数ベクタの内容を全てつなぎ合わせた新たなベクタを返します。
(引数が一つだけの場合も、新たにアロケートされたベクタが返されます。)
@c COMMON

@example
(u8vector-append '#u8(1 2 3) '#u8(4 5) '#u8() '#u8(6 7 8))
  @result{} #u8(1 2 3 4 5 6 7 8)
@end example
@end deffn

@deffn {Function} @@vector-concatenate vecs
@findex u8vector-concatenate
@findex s8vector-concatenate
@findex u16vector-concatenate
@findex s16vector-concatenate
@findex u32vector-concatenate
@findex s32vector-concatenate
@findex u64vector-concatenate
@findex s64vector-concatenate
@findex f16vector-concatenate
@findex f32vector-concatenate
@findex f64vector-concatenate
@findex c32vector-concatenate
@findex c64vector-concatenate
@findex c128vector-concatenate
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns a new @@vector which is concatenation of the list of
@@vectors @var{vecs}.
@c JP
@@vectorのリスト@var{vecs}にあるベクタを全て連結した新たな
@@vectorを返します。
@c COMMON
@example
(u8vector-concatenate '(#u8(1 2 3) #u8(4 5 6)))
  @result{} #u8(1 2 3 4 5 6)
@end example
@end deffn

@deffn {Function} @@vector-append-subvectors :optional vec start end @dots{}
@findex u8vector-append-subvectors
@findex s8vector-append-subvectors
@findex u16vector-append-subvectors
@findex s16vector-append-subvectors
@findex u32vector-append-subvectors
@findex s32vector-append-subvectors
@findex u64vector-append-subvectors
@findex s64vector-append-subvectors
@findex f16vector-append-subvectors
@findex f32vector-append-subvectors
@findex f64vector-append-subvectors
@findex c32vector-append-subvectors
@findex c64vector-append-subvectors
@findex c128vector-append-subvectors
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns a new @@vector which is concatenation of the subvectors of
given @var{vec}s, using accompanied @var{start} and @var{end} index.
@c JP
各@var{vec}の@var{start}と@var{end}で指定される範囲のサブベクタを
連結した新たな@@vectorを返します。
@c COMMON
@example
(u8vector-append-subvectors '#u8(1 2 3 4) 1 3 '#u8(5 6 7 8) 0 2)
  @result{} #u8(2 3 5 6)
@end example
@end deffn

@deffn {Function} @@vector-take vec n
@deffnx {Function} @@vector-take-right vec n
@deffnx {Function} @@vector-drop vec n
@deffnx {Function} @@vector-drop-right vec n
@findex u8vector-take
@findex s8vector-take
@findex u16vector-take
@findex s16vector-take
@findex u32vector-take
@findex s32vector-take
@findex u64vector-take
@findex s64vector-take
@findex f16vector-take
@findex f32vector-take
@findex f64vector-take
@findex c32vector-take
@findex c64vector-take
@findex c128vector-take
@findex u8vector-take-right
@findex s8vector-take-right
@findex u16vector-take-right
@findex s16vector-take-right
@findex u32vector-take-right
@findex s32vector-take-right
@findex u64vector-take-right
@findex s64vector-take-right
@findex f16vector-take-right
@findex f32vector-take-right
@findex f64vector-take-right
@findex c32vector-take-right
@findex c64vector-take-right
@findex c128vector-take-right
@findex u8vector-drop
@findex s8vector-drop
@findex u16vector-drop
@findex s16vector-drop
@findex u32vector-drop
@findex s32vector-drop
@findex u64vector-drop
@findex s64vector-drop
@findex f16vector-drop
@findex f32vector-drop
@findex f64vector-drop
@findex c32vector-drop
@findex c64vector-drop
@findex c128vector-drop
@findex u8vector-drop-right
@findex s8vector-drop-right
@findex u16vector-drop-right
@findex s16vector-drop-right
@findex u32vector-drop-right
@findex s32vector-drop-right
@findex u64vector-drop-right
@findex s64vector-drop-right
@findex f16vector-drop-right
@findex f32vector-drop-right
@findex f64vector-drop-right
@findex c32vector-drop-right
@findex c64vector-drop-right
@findex c128vector-drop-right
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns a new uvector that has the first @var{n} elements,
the last @var{n} elements, the elements without the first @var{n} elements,
and the elements without the last @var{n} elements, respectively.

@var{N} must be a nonnegative exact integer no greater than the
length of @var{vec}.
@c JP
それぞれ、最初の@var{n}要素、最後の@var{n}要素、最初の@var{n}要素を取り残り、
および最後の@var{n}要素を取り除いた残り、を要素とするuvectorを作って返します。

@var{n}は非負の正確な整数で、@var{vec}の長さを越えてはいけません。
@c COMMON

@example
(u8vector-take '#u8(0 1 2 3 4 5) 4) @result{} #u8(0 1 2 3)
(u8vector-drop '#u8(0 1 2 3 4 5) 4) @result{} #u8(4 5)

(u8vector-take-right '#u8(0 1 2 3 4 5) 4) @result{} #u8(2 3 4 5)
(u8vector-drop-right '#u8(0 1 2 3 4 5) 4) @result{} #u8(0 1)
@end example

@c EN
You can also use @code{uvector-alias} to obtain a partial uvector
that shares the storage with the original uvector, avoiding copying overhead.
@c JP
なお、@code{uvector-alias}を使うと、元のuvectorと記憶領域を共有する
部分的なuvectorを得ることができます。コピーのオーバヘッドを避けることができます。
@c COMMON
@end deffn

@deffn {Function} @@vector-segment vec n
@findex u8vector-segment
@findex s8vector-segment
@findex u16vector-segment
@findex s16vector-segment
@findex u32vector-segment
@findex s32vector-segment
@findex u64vector-segment
@findex s64vector-segment
@findex f16vector-segment
@findex f32vector-segment
@findex f64vector-segment
@findex c32vector-segment
@findex c64vector-segment
@findex c128vector-segment
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Segment @var{vec} into fresh uvectors of length @var{n}, and returns
a list of them.  The last uvector may be shorter than @var{n} if the
length of @var{vec} is not a multiple of @var{n}.

@var{N} must be a positive exact integer.
@c JP
@var{vec}を長さ@var{n}の新たなuvectorに分割し、そのリストを返します。
@var{vec}の長さが@var{n}の倍数でなければ、最後のuvectorは@var{n}より短くなります。

@var{n}は正の正確な整数でなければなりません。
@c COMMON

@example
(u8vector-segment '#u8(0 1 2 3 4 5 6 7) 3)
 @result{} (#u8(0 1 2) #u8(3 4 5) #u8(6 7))
@end example
@end deffn

@deffn {Function} @@vector-fold kons knil vec vec2 @dots{}
@deffnx {Function} @@vector-fold-right kons knil vec vec2 @dots{}
@findex u8vector-fold
@findex s8vector-fold
@findex u16vector-fold
@findex s16vector-fold
@findex u32vector-fold
@findex s32vector-fold
@findex u64vector-fold
@findex s64vector-fold
@findex f16vector-fold
@findex f32vector-fold
@findex f64vector-fold
@findex c32vector-fold
@findex c64vector-fold
@findex c128vector-fold
@findex u8vector-fold-right
@findex s8vector-fold-right
@findex u16vector-fold-right
@findex s16vector-fold-right
@findex u32vector-fold-right
@findex s32vector-fold-right
@findex u64vector-fold-right
@findex s64vector-fold-right
@findex f16vector-fold-right
@findex f32vector-fold-right
@findex f64vector-fold-right
@findex c32vector-fold-right
@findex c64vector-fold-right
@findex c128vector-fold-right
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Like @var{fold}/@var{fold-right} (@pxref{Walking over lists})
and @var{vector-fold}/@var{vector-fold-right (@pxref{R7RS vectors}},
these procedures apply @var{kons} over each element of input uvectors,
carrying around the previous result of @var{kons} as the state value,
whose default is @var{knil}.
@c JP
@var{fold}/@var{fold-right} (@ref{Walking over lists}参照)や
@var{vector-fold}/@var{vector-fold-right (@ref{R7RS vectors}参照}と
同じように、これらの手続きは@var{kons}を、入力ユニフォームベクタの各要素と
状態値(一つ前の@var{kons}の戻り値)に適用してゆきます。
@var{knil}は最初の状態値になります。
@c COMMON

@example
(u8vector-fold + 0 '#u8(1 2 3 4))
  @result{} 10
(u8vector-fold cons '() '#u8(1 2 3 4))
  @result{} ((((() . 1) . 2) . 3) . 4)
(u8vector-fold-right cons '() '#u8(1 2 3 4))
  @result{} (1 2 3 4)
@end example
@end deffn

@deffn {Function} @@vector-map f vec vec2 @dots{}
@deffnx {Function} @@vector-map! f vec vec2 @dots{}
@deffnx {Function} @@vector-for-each f vec vec2 @dots{}
@findex u8vector-map
@findex s8vector-map
@findex u16vector-map
@findex s16vector-map
@findex u32vector-map
@findex s32vector-map
@findex u64vector-map
@findex s64vector-map
@findex f16vector-map
@findex f32vector-map
@findex f64vector-map
@findex c32vector-map
@findex c64vector-map
@findex c128vector-map
@findex u8vector-map!
@findex s8vector-map!
@findex u16vector-map!
@findex s16vector-map!
@findex u32vector-map!
@findex s32vector-map!
@findex u64vector-map!
@findex s64vector-map!
@findex f16vector-map!
@findex f32vector-map!
@findex f64vector-map!
@findex c32vector-map!
@findex c64vector-map!
@findex c128vector-map!
@findex u8vector-for-each
@findex s8vector-for-each
@findex u16vector-for-each
@findex s16vector-for-each
@findex u32vector-for-each
@findex s32vector-for-each
@findex u64vector-for-each
@findex s64vector-for-each
@findex f16vector-for-each
@findex f32vector-for-each
@findex f64vector-for-each
@findex c32vector-for-each
@findex c64vector-for-each
@findex c128vector-for-each
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
The procedur @var{f} is applied on each @var{i}-th elements from
@var{vec} @dots{}.  @code{@@vector-map} collects the results of @code{f}
into a fresh uniform vector of the same type and length of the
input uvector and returns it.
@code{@@vector-map!} uses the first @var{vec} to store the results
of @code{f} and returns @code{#<undef>} (it is not a ``linear-update''
procedure, which may or may not modify the input and you need to use
the returned value.)
@code{@@vector-for-each} calls @var{f} for side-effects and
discards its results.

The order how @var{f} is applied on elements of input isn't specified
for @code{@@vector-map} and @code{@@vector-map!}, while @code{@@vector-for-each}
is guaranteed to appli @var{f} in order.

If lengths of input vectors differ, only the portions of the length
of shortest vector are considered.
@c JP
手続き@var{f}を、入力ユニフォームベクタの@var{i}番目の要素にそれぞれ適用します。
@code{@@vector-map}は@var{f}の結果を、入力ユニフォームベクタと同じ型、長さの
新しいユニフォームベクタに格納します。
@code{@@vector-map!}は@var{f}の結果を最初の引数に格納し、
@code{#<undef>}を返します。
(この手続きは「線形更新」版ではありません。線形更新版では引数が変更されることは
保証されず、呼び出し側は返り値を使わなければなりませんが、
この手続きは引数が変更されることが保証されています。)
@code{@@vector-for-each}は@var{f}を副作用のために呼び出し、結果は捨てます。

@var{f}が適用される順番は、@code{@@vector-map}と@code{@@vector-map!}については
保証されていません。
@code{@@vector-for-each}は@var{f}をインデックスの順に適用します。

入力ユニフォームベクタの長さが異なる場合は、最も短いユニフォームベクタの
長さの部分だけが考慮されます。
@c COMMON

@example
(u8vector-map + '#u8(1 2 3) '#u8(4 5 6))
  @result{} #u8(5 7 9)

(define v (u8vector 1 2 3 4))
(u8vector-map! + v '#u8(4 5 6)) @result{} #<undef>
v  @result{} #u8(5 7 9 4)
@end example
@end deffn

@deffn {Function} @@vector-count pred vec vec2 @dots{}
@findex u8vector-count
@findex s8vector-count
@findex u16vector-count
@findex s16vector-count
@findex u32vector-count
@findex s32vector-count
@findex u64vector-count
@findex s64vector-count
@findex f16vector-count
@findex f32vector-count
@findex f64vector-count
@findex c32vector-count
@findex c64vector-count
@findex c128vector-count
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Calls @var{pred} with each @var{i}-th elements from @var{vec} @dots{},
from @var{i}=0 and up,
and returns the number of times @var{pred} returns true.
If lengths of input uvectors differ, iteration stops at the end of
the shortest uvector.
@c JP
@var{vec} @dots{}の各@var{i}番目の要素を引数にして@var{pred}を呼び出し、
それが真の値を返した回数を返します。
入力のユニフォームベクタの長さが同じでない場合は、
繰り返しは一番短いユニフォームベクタの終端で止まります。
@c COMMON

@example
(u8vector-count <= '#u8(3 3 3 3 3) '#u8(1 2 3 4 5)) @result{} 3
@end example
@end deffn

@deffn {Function} @@vector-cumulate f knil vec
@findex u8vector-cumulate
@findex s8vector-cumulate
@findex u16vector-cumulate
@findex s16vector-cumulate
@findex u32vector-cumulate
@findex s32vector-cumulate
@findex u64vector-cumulate
@findex s64vector-cumulate
@findex f16vector-cumulate
@findex f32vector-cumulate
@findex f64vector-cumulate
@findex c32vector-cumulate
@findex c64vector-cumulate
@findex c128vector-cumulate
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns a fresh uvector of the same type and legnth as @var{vec}.
Each element of returned vector is computed as follows:

@itemize @bullet
@item
The first item is @code{(f knil (~ vec 0))}.
@item
The second item is @code{(f previous-result (~ vec 1))}.
@item
@dots{} and so on.
@end itemize
@c JP
@var{vec}と同じ型、長さの新たなユニフォームベクタを作って返します。
返されるユニフォームベクタの要素は次のとおり決定されます。

@itemize @bullet
@item
最初の要素は@code{(f knil (~ vec 0))}
@item
次の要素は@code{(f previous-result (~ vec 1))}.
@item
@dots{} 以下同様
@end itemize
@c COMMON

@example
(s8vector-cumulate + 1 '#s8(1 2 3 4 5)) @result{} #s8(2 4 7 11 16)
(s8vector-cumulate - 1 '#s8(1 2 3 4 5)) @result{} #s8(0 -2 -5 -9 -14)
@end example
@end deffn

@deffn {Function} @@vector-take-while pred vec
@deffnx {Function} @@vector-take-while-right pred vec
@deffnx {Function} @@vector-drop-while pred vec
@deffnx {Function} @@vector-drop-while-right pred vec
@findex u8vector-take-while
@findex s8vector-take-while
@findex u16vector-take-while
@findex s16vector-take-while
@findex u32vector-take-while
@findex s32vector-take-while
@findex u64vector-take-while
@findex s64vector-take-while
@findex f16vector-take-while
@findex f32vector-take-while
@findex f64vector-take-while
@findex c32vector-take-while
@findex c64vector-take-while
@findex c128vector-take-while
@findex u8vector-take-while-right
@findex s8vector-take-while-right
@findex u16vector-take-while-right
@findex s16vector-take-while-right
@findex u32vector-take-while-right
@findex s32vector-take-while-right
@findex u64vector-take-while-right
@findex s64vector-take-while-right
@findex f16vector-take-while-right
@findex f32vector-take-while-right
@findex f64vector-take-while-right
@findex c32vector-take-while-right
@findex c64vector-take-while-right
@findex c128vector-take-while-right
@findex u8vector-drop-while
@findex s8vector-drop-while
@findex u16vector-drop-while
@findex s16vector-drop-while
@findex u32vector-drop-while
@findex s32vector-drop-while
@findex u64vector-drop-while
@findex s64vector-drop-while
@findex f16vector-drop-while
@findex f32vector-drop-while
@findex f64vector-drop-while
@findex c32vector-drop-while
@findex c64vector-drop-while
@findex c128vector-drop-while
@findex u8vector-drop-while-right
@findex s8vector-drop-while-right
@findex u16vector-drop-while-right
@findex s16vector-drop-while-right
@findex u32vector-drop-while-right
@findex s32vector-drop-while-right
@findex u64vector-drop-while-right
@findex s64vector-drop-while-right
@findex f16vector-drop-while-right
@findex f32vector-drop-while-right
@findex f64vector-drop-while-right
@findex c32vector-drop-while-right
@findex c64vector-drop-while-right
@findex c128vector-drop-while-right
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Return a fresh uvector of the same type as @var{vec}, containing
a subset of original elements computed as follows:
@table @code
@item @@vector-take-while
The consecutive elements from the beginning of @var{vec} satisfying
@var{pred}.
@item @@vector-take-while-right
The consecutive elements from the end of @var{vec} satisfying
@var{pred}.
@item @@vector-drop-while
The elements except the consecutive elements from the beginning of
@var{vec} satisfying @var{pred}.
@item @@vector-drop-while-right
The elements except the consecutive elements from the end of
@var{vec} satisfying.
@var{pred}.
@end table
@c JP
@var{vec}と同じ型の新たなユニフォームベクタを返します。その要素は
@var{vec}のサブセットで、次のとおり決定されます。
@table @code
@item @@vector-take-while
@var{vec}の最初から、@var{pred}を満たす限りの連続する要素
@item @@vector-take-while-right
@var{vec}の最後から、@var{pred}を満たす限りの連続する要素
@var{pred}.
@item @@vector-drop-while
@var{vec}の要素のうち、その最初から@var{pred}を満たす限りの連続する要素を除いたもの
@item @@vector-drop-while-right
@var{vec}の要素のうち、その最後から@var{pred}を満たす限りの連続する要素を除いたもの
@end table
@c COMMON
@end deffn

@deffn {Function} @@vector-index pred vec vec2 @dots{}
@deffnx {Function} @@vector-index-right pred vec vec2 @dots{}
@findex u8vector-index
@findex s8vector-index
@findex u16vector-index
@findex s16vector-index
@findex u32vector-index
@findex s32vector-index
@findex u64vector-index
@findex s64vector-index
@findex f16vector-index
@findex f32vector-index
@findex f64vector-index
@findex c32vector-index
@findex c64vector-index
@findex c128vector-index
@findex u8vector-index-right
@findex s8vector-index-right
@findex u16vector-index-right
@findex s16vector-index-right
@findex u32vector-index-right
@findex s32vector-index-right
@findex u64vector-index-right
@findex s64vector-index-right
@findex f16vector-index-right
@findex f32vector-index-right
@findex f64vector-index-right
@findex c32vector-index-right
@findex c64vector-index-right
@findex c128vector-index-right
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns an integer
index of the first (@code{*-index}) or last (@code{*-index-right})
element that sastisfies @var{pred}, or @code{#f} if no element satisfies
@var{pred}.
@c JP
@var{pred}を満たす最初(@code{*-index})もしくは最後(@code{*-index-right})の
要素の整数インデックスを返します。@var{pred}を満たす要素がなければ@code{#f}
が返ります。
@c COMMON

@example
(u8vector-index odd? '#u8(10 11 12 13 14 15 16)) @result{} 1
(u8vector-index-right odd? '#u8(10 11 12 13 14 15 16)) @result{} 5
@end example
@end deffn

@deffn {Function} @@vector-skip pred vec vec2 @dots{}
@deffnx {Function} @@vector-skip-right pred vec vec2 @dots{}
@findex u8vector-skip
@findex s8vector-skip
@findex u16vector-skip
@findex s16vector-skip
@findex u32vector-skip
@findex s32vector-skip
@findex u64vector-skip
@findex s64vector-skip
@findex f16vector-skip
@findex f32vector-skip
@findex f64vector-skip
@findex c32vector-skip
@findex c64vector-skip
@findex c128vector-skip
@findex u8vector-skip-right
@findex s8vector-skip-right
@findex u16vector-skip-right
@findex s16vector-skip-right
@findex u32vector-skip-right
@findex s32vector-skip-right
@findex u64vector-skip-right
@findex s64vector-skip-right
@findex f16vector-skip-right
@findex f32vector-skip-right
@findex f64vector-skip-right
@findex c32vector-skip-right
@findex c64vector-skip-right
@findex c128vector-skip-right
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns an integer
index of the first (@code{*-index}) or last (@code{*-index-right})
element that @emph{does not} sastisfy @var{pred},
or @code{#f} if all elements satisfiy @var{pred}.
@c JP
@var{pred}を満たさない最初(@code{*-index})もしくは最後(@code{*-index-right})の
要素の整数インデックスを返します。全ての要素が@var{pred}を満たした場合は@code{#f}
が返ります。
@c COMMON

@example
(u8vector-skip > '#u8(8 3 2 9) '#u8(1 4 5 6)) @result{} 1
(u8vector-skip-right > '#u8(8 3 2 9) '#u8(1 4 5 6)) @result{} 2
@end example
@end deffn

@deffn {Function} @@vector-any pred vec vec2 @dots{}
@deffnx {Function} @@vector-every pred vec vec2 @dots{}
@findex u8vector-any
@findex s8vector-any
@findex u16vector-any
@findex s16vector-any
@findex u32vector-any
@findex s32vector-any
@findex u64vector-any
@findex s64vector-any
@findex f16vector-any
@findex f32vector-any
@findex f64vector-any
@findex c32vector-any
@findex c64vector-any
@findex c128vector-any
@findex u8vector-every
@findex s8vector-every
@findex u16vector-every
@findex s16vector-every
@findex u32vector-every
@findex s32vector-every
@findex u64vector-every
@findex s64vector-every
@findex f16vector-every
@findex f32vector-every
@findex f64vector-every
@findex c32vector-every
@findex c64vector-every
@findex c128vector-every
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Apply @var{pred} on the @var{i}-th elements of given uvectors,
from the first eleement to the last element.  For @code{@@vector-any},
as soon as @var{pred} returns a true value, it returns that value.  If
no elements satisfy @var{pred}, returns @code{#f}.
For @code{@@vector-every}, as soon as @var{pred} returns @code{#f},
it returns @code{#f}.  If every element satisfies @var{pred}, returns
the last result of @var{pred}.
@c JP
述語@var{pred}を、引数の各ユニフォームベクタの@var{i}番目の要素
(0 <= i < vecの長さ)に順に適用します。
@code{@@vector-any}では、@var{pred}が真の値を返したら直ちにその
値を返します。どの要素も@var{pred}満たさなければ@code{#f}を返します。
@code{@@vector-every}では、@var{pred}が@code{#f}を返したら
直ちに@code{#f}を返します。どの要素も@var{pred}を満たした場合は
最後の@var{pred}の値を返します。
@c COMMON

@c EN
If the lengths of given uvectors differ, it stops at the end
of the shortest one.
@c JP
もし与えられたユニフォームベクタの長さが異なる場合は、
一番短いベクタの最後に到達した時点で評価を打ち切ります。
@c COMMON
@end deffn

@deffn {Function} @@vector-partition pred vec
@findex u8vector-partition
@findex s8vector-partition
@findex u16vector-partition
@findex s16vector-partition
@findex u32vector-partition
@findex s32vector-partition
@findex u64vector-partition
@findex s64vector-partition
@findex f16vector-partition
@findex f32vector-partition
@findex f64vector-partition
@findex c32vector-partition
@findex c64vector-partition
@findex c128vector-partition
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Returns a uniform vectors of the same type and length as @var{vec},
and an integer index.
The returned vector contains the elements in @var{vec} that satisfies
@var{pred} at the left, up to the returned index, followed by
the elements that don't satisfy @var{pred}
@c JP
@var{vec}と同じ型で同じ大きさのユニフォームベクタと、整数のインデックスを返します。
戻り値のベクタは左から、@var{vec}の要素のうち@var{pred}を満たすものが順に
インデックスまで格納され、続いて@var{pred}を満たさない要素が格納されます。
@c COMMON

@example
(u8vector-partition odd? '#u8(0 1 2 3 4 5 6 7))
 @result{} #u8(1 3 5 7 0 2 4 6) @r{and} 4
@end example
@end deffn

@deffn {Function} @@vector-filter pred vec
@deffnx {Function} @@vector-remove pred vec
@findex u8vector-filter
@findex s8vector-filter
@findex u16vector-filter
@findex s16vector-filter
@findex u32vector-filter
@findex s32vector-filter
@findex u64vector-filter
@findex s64vector-filter
@findex f16vector-filter
@findex f32vector-filter
@findex f64vector-filter
@findex c32vector-filter
@findex c64vector-filter
@findex c128vector-filter
@findex u8vector-remove
@findex s8vector-remove
@findex u16vector-remove
@findex s16vector-remove
@findex u32vector-remove
@findex s32vector-remove
@findex u64vector-remove
@findex s64vector-remove
@findex f16vector-remove
@findex f32vector-remove
@findex f64vector-remove
@findex c32vector-remove
@findex c64vector-remove
@findex c128vector-remove
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Applies @var{pred} on each element of a uniform vector @var{vec},
and collects the elements that satisfies ('filter'), or doest not satisfy
('remove'), into the same type of @var{vec} and returns it.
@c JP
ユニフォームベクタ@var{vec}の各要素に@var{pred}を適用し、
それを満たす要素(filter)あるいは満たさない要素(remove)だけを集めた、
@var{vec}と同じ型のユニフォームベクタを作って返します。
@c COMMON

@example
(u8vector-filter odd? '#u8(0 1 2 3 4 5 6 7))
 @result{} #u8(1 3 5 7)
(u8vector-remove odd? '#u8(0 1 2 3 4 5 6 7))
 @result{} #u8(0 2 4 6)
@end example
@end deffn


@deffn {Function} make-@@vector-generator vec
@findex make-u8vector-generator
@findex make-s8vector-generator
@findex make-u16vector-generator
@findex make-s16vector-generator
@findex make-u32vector-generator
@findex make-s32vector-generator
@findex make-u64vector-generator
@findex make-s64vector-generator
@findex make-f16vector-generator
@findex make-f32vector-generator
@findex make-f64vector-generator
@findex make-c32vector-generator
@findex make-c64vector-generator
@findex make-c128vector-generator
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Creates and returns a generator that returns elements of @var{vec}
one at a time in order.
@c JP
@var{vec}の要素を一つづつ順に返すジェネレータを作って返します。
@c COMMON

@c EN
For Gauche-specific code, you can use the generic version,
@code{uvector->generator} in @code{gauche.generator}
(@pxref{Generators}).
@c JP
Gauche専用のコードであれば、@code{gauche.generator}にある
ジェネリックなバージョン@code{uvector->generator}を使うこともできます
(@ref{Generators}参照)。
@c COMMON
@end deffn


@defvar @@vector-comparator
@vindex u8vector-comparator
@vindex s8vector-comparator
@vindex u16vector-comparator
@vindex s16vector-comparator
@vindex u32vector-comparator
@vindex s32vector-comparator
@vindex u64vector-comparator
@vindex s64vector-comparator
@vindex f16vector-comparator
@vindex f32vector-comparator
@vindex f64vector-comparator
@vindex c32vector-comparator
@vindex c64vector-comparator
@vindex c128vector-comparator
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Bound to comparators that can compare two @code{@@vector}s and
to hash a @code{@@vector}.  @xref{Basic comparators}, for the details
of comparators.  These comparators both provides ordering predicate
and hash function.
@c JP
ふたつの@code{@@vector}を比較したり、@code{@@vector}のハッシュを取ったりできる
比較器に束縛された変数です。比較器の詳細については
@ref{Basic comparators}を参照してください。
これらの比較器は順序手続きとハッシュ関数を両方とも実装しています。
@c COMMON
@end defvar


@defun uvector-binary-search uvector key :optional start end skip rounding
@c MOD gauche.uvector
@c EN
The @code{uvector} must contain values in increasing order.
This procedure finds the index of an element that is equal to @var{key},
using binary search.   If such element can't be found, @code{#f} is returned.
@c JP
@var{uvector}は値が昇順に格納されたユニフォームベクタでなければなりません。
この手続きは二分探索を使って、@var{key}と一致する要素を探し、そのインデックスを返します。
一致する要素が無ければ@code{#f}が返されます。
@c COMMON

@example
(uvector-binary-search '#u8(0 5 19 32 58 96) 32)
  @result{} 3

(uvector-binary-search '#u8(0 5 19 32 58 96) 33)
  @result{} #f
@end example

@c EN
The optional @var{start} and @var{end} arguments limits the portion
of @var{uvector} to search; @var{start} specifies starting index (inclusive)
and @var{end} specifies ending index (exclusive).
Passing @code{#f} indicates the default
value (0 for @var{start}, the length of the vector for @var{end}).
The returned index is the actual index of the vector, but the elements
outside of @var{start}-@var{end} range don't need to be sorted.
@c JP
省略可能引数@var{start}と@var{end}は@var{uvector}中の探すべき部分を制限します。
@var{start}が開始インデックス(その要素も含む)、@var{end}が終了インデックス
(その要素自体は含まない)です。
@code{#f}を渡すとデフォルト値(@var{start}は0、@var{end}はベクタの長さ)と
みなされます。返ってくるインデックスはベクタ全体から見たインデックスになりますが、
@var{start}-@var{end}間以外の@var{uvector}の要素はソートされている必要はありません。

@c COMMON

@example
(uvector-binary-search '#u8(99 99 19 32 58 99) 32 2 5)
  @result{} 3

(uvector-binary-search '#u8(99 99 19 32 58 99) 99 2 5)
  @result{} #f
@end example

@c EN
The optional @var{skip} argument must be a nonnegative exact integer
or @code{#f}.  If it is a positive integer, the number of elements after
every key in the @var{uvector} is ignored.  For example, if @var{skip} is 2
and @var{uvector} is @code{#u8(3 100 101 5 102 103 13 104 105)},
only @code{3}, @code{5} and @code{13} are subject to search, and elements
inbetween are ignored.  This allows the caller to store @emph{payload},
or associated value to each key, in the @var{uvector} itself.
If @var{skip} is positive integer, the length of the searched portion
of @var{uvector} must be a multiple of the record size (@var{skip}+1).
@c JP
省略可能な@var{skip}引数は、非負の正確な整数か@code{#f}でなければなりません。
@var{skip}が正の整数の場合、@var{uvector}中の各キーに続く@var{skip}個の要素を
飛ばして探索します。例えば@var{skip}が2で@var{uvector}が
@code{#u8(3 100 101 5 102 103 13 104 105)}であれば、
@code{3}、@code{5}、@code{13}だけが探索の対象となります。
この機能を使うと、キーに結びつけられた値(ペイロード)を@var{uvector}中に直接
格納したまま探索を行うことができます。@var{skip}が正の整数の場合、
@var{uvector}の探索が行われる部分の大きさは@var{skip}+1の整数倍でなければなりません。
@c COMMON

@example
(uvector-binary-search '#u8(3 100 101 5 102 103 13 104 105) 13 #f #f 2)
  @result{} 6

(uvector-binary-search '#u8(3 100 101 5 102 103 13 104) 13 #f #f 2)
  @result{} ; @r{Error: uvector size (8) isn't multiple of record size (3)}
@end example

@c EN
Finally, @var{rounding} argument adjusts the behavior when the exact
match isn't found.  It can be either one of the following values:
@c JP
最後に、@var{rounding}引数は一致する要素が見つからなかった場合の振る舞いを
調整します。値は以下のいずれかでなければなりません。
@c COMMON

@table @asis
@item @code{#f}
@c EN
This is the default.
The procedure searches the element that is equal to @var{key}, and
returns @code{#f} if such element isn't found.
@c JP
これがデフォルトです。@var{key}と等しい要素だけを探し、
見つからなければ@code{#f}を返します。
@c COMMON
@item a symbol @code{floor}
@c EN
When the exact match isn't found, the procedure
returns an index of the element that's closest to but
not greater than @var{key}.  If @var{key} is smaller than all the elements,
@code{#f} is returned.
@c JP
@var{key}と等しい要素がみつからなかった場合、@var{key}を越えない、もっとも近い
要素のインデックスを返します。@var{key}がどの要素よりも小さい場合は@code{#f}が
返されます。
@c COMMON
@item a symbol @code{ceiling}
@c EN
When the exact match isn't found, the procedure
returns an index of the element that's closest to but
not smaller than @var{key}.  If @var{key} is greater than all the elements,
@code{#f} is returned.
@c JP
@var{key}と等しい要素がみつからなかった場合、@var{key}を下回らない、もっとも近い
要素のインデックスを返します。@var{key}がどの要素よりも大きい場合は@code{#f}が
返されます。
@c COMMON
@end table

@example
(uvector-binary-search '#u32(1 10 100 1000 10000) 3757)
  @result{} #f

(uvector-binary-search '#u32(1 10 100 1000 10000) 3757 #f #f #f 'floor)
  @result{} 3

(uvector-binary-search '#u32(1 10 100 1000 10000) 3757 #f #f #f 'ceiling)
  @result{} 4
@end example

@c EN
Note: SRFI-133 has @code{vector-binary-search}, which is quite similar to
this procedure (@pxref{R7RS vectors}) but it requires comparison
procedure, for it needs to compare general Scheme values.  And it
does not support @var{skip} and @var{rounding} arguments.
@c JP
註: SRFI-133の@code{vector-binary-search}はこの手続きと良く似ています
(@ref{R7RS vectors}参照)。ただし、
そちらは一般のScheme値を相手にするために、比較手続きも取ります。
また@var{skip}と@var{rounding}引数の機能はサポートされません。
@c COMMON
@end defun

@node Uvector conversion operations, Uvector numeric operations, Uvector basic operations, Uniform vector library
@subsection Uvector conversion operations
@c NODE ユニフォームベクタの変換

@deffn {Function} @@vector->list vec :optional start end
@findex u8vector->list
@findex s8vector->list
@findex u16vector->list
@findex s16vector->list
@findex u32vector->list
@findex s32vector->list
@findex u64vector->list
@findex s64vector->list
@findex f16vector->list
@findex f32vector->list
@findex f64vector->list
@findex c32vector->list
@findex c64vector->list
@findex c128vector->list
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Converts @@vector @var{vec} to a list.
If @var{start} and/or @var{end} are given, they limit the range of
@var{vec} to be extracted.

Note that the generic function @code{coerce-to} can be used as well,
if you import @code{gauche.collection}.
@c JP
@@vector @var{vec}をリストに変換します。
省略可能な引数@var{start}と@var{end}が与えられた場合、
それらは取り出される要素の範囲を制限します。

モジュール@code{gauche.collection}をインポートしていれば、
総称関数@code{coerce-to}を使うこともできます。
@c COMMON
@example
(u32vector->list '#u32(9 2 5)) @result{} (9 2 5)

(use gauche.collection)
(coerce-to <list> '#u32(9 2 5)) @result{} (9 2 5)
@end example
@end deffn

@defun uvector->list uvec :optional start end
@c MOD gauche.uvector
@c EN
This is a generic version of @code{@@vector->list}.
It can take any kind of uvector as @var{uvec}.  The meaning of
optional arguments are the same as @code{@@vector->list}.
@c JP
これは@code{@@vector->list}の汎用バージョンで、
ユニフォームベクタなら何であれ@var{uvec}に取ることができます。
省略可能引数の意味は@code{@@vector->list}と同じです。
@c COMMON
@end defun


@deffn {Function} @@vector->vector vec :optional start end
@findex u8vector->vector
@findex s8vector->vector
@findex u16vector->vector
@findex s16vector->vector
@findex u32vector->vector
@findex s32vector->vector
@findex u64vector->vector
@findex s64vector->vector
@findex f16vector->vector
@findex f32vector->vector
@findex f64vector->vector
@findex c32vector->vector
@findex c64vector->vector
@findex c128vector->vector
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Converts @@vector @var{vec} to a vector.
If @var{start} and/or @var{end} are given, they limit the range of
@var{vec} to be copied.

Note that the generic function @code{coerce-to} can be used as well,
if you import @code{gauche.collection}.
@c JP
@@vector @var{vec}をベクタに変換します。
省略可能な引数@var{start}と@var{end}が与えられた場合、
それらは取り出される要素の範囲を制限します。

モジュール@code{gauche.collection}をインポートしていれば、
総称関数@code{coerce-to}を使うこともできます。
@c COMMON
@example
(f32vector->vector '#f32(9.3 2.2 5.5))   @result{} #(9.3 2.2 5.5)
(f32vector->vector '#f32(9.3 2.2 5.5) 2) @result{} #(5.5)

(use gauche.collection)
(coerce-to <vector> '#f32(9.3 2.2 5.5)) @result{} #(9.3 2.2 5.5)
@end example
@end deffn

@defun uvector->vector uvec :optional start end
@c MOD gauche.uvector
@c EN
This is a generic version of @code{@@vector->vector}.
It can take any kind of uvector as @var{uvec}.  The meaning of
optional arguments are the same as @code{@@vector->vector}.
@c JP
これは@code{@@vector->vector}の汎用バージョンで、
ユニフォームベクタなら何であれ@var{uvec}に取ることができます。
省略可能引数の意味は@code{@@vector->vector}と同じです。
@c COMMON
@end defun

@deffn {Function} list->@@vector list :optional clamp
@findex list->s8vector
@findex list->u8vector
@findex list->s16vector
@findex list->u16vector
@findex list->s32vector
@findex list->u32vector
@findex list->s64vector
@findex list->u64vector
@findex list->f16vector
@findex list->f32vector
@findex list->f64vector
@findex list->c32vector
@findex list->c64vector
@findex list->c128vector
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Converts a list @var{list} to a @@vector.
Optional argument @var{clamp} specifies the behavior when
the element of @var{list} is out of the valid range.
(The @var{clamp} argument is Gauche's extension.)

Note that the generic function @code{coerce-to} can be used as well,
if you import @code{gauche.collection}.
@c JP
リスト@var{list}を@@vectorに変換します。
省略可能な引数@var{clamp}が、リスト内の要素が正しい範囲外の数であった場合の
動作を指定します。
(@var{clamp}引数はGauche独自拡張です。)

モジュール@code{gauche.collection}をインポートしていれば、
総称関数@code{coerce-to}を使うこともできます。
@c COMMON
@example
(list->s64vector '(9 2 5)) @result{} #s64(9 2 5)

(use gauche.collection)
(coerce-to <s64vector> '(9 2 5)) @result{} #s64(9 2 5)
@end example
@end deffn

@defun list->uvector classs list
@c MOD gauche.uvector
@c EN
A ganeric version of @code{list->@@vector}.  You can pass a uvector
class @var{class}.
@c JP
@code{list->@@vector}の汎用バージョンです。
ユニフォームベクタのクラスを@var{class}に渡します。
@c COMMON

@example
(list->uvector <u8vector> '(0 1 2)) @result{} #u8(0 1 2)
@end example
@end defun


@deffn {Function} reverse-list->@@vector list :optional clamp
@findex reverse-list->s8vector
@findex reverse-list->u8vector
@findex reverse-list->s16vector
@findex reverse-list->u16vector
@findex reverse-list->s32vector
@findex reverse-list->u32vector
@findex reverse-list->s64vector
@findex reverse-list->u64vector
@findex reverse-list->f16vector
@findex reverse-list->f32vector
@findex reverse-list->f64vector
@findex reverse-list->c32vector
@findex reverse-list->c64vector
@findex reverse-list->c128vector
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Create a new @code{@@vector} with the elements of @var{list} in
reverse order.
Optional argument @var{clamp} specifies the behavior when
the element of @var{list} is out of the valid range.
(The @var{clamp} argument is Gauche's extension.)
@c JP
@var{list}の要素を逆順に持つ新たな@code{@@vector}を作って返します。
省略可能な引数@var{clamp}が、リスト内の要素が正しい範囲外の数であった場合の
動作を指定します。
(@var{clamp}引数はGauche独自拡張です。)
@c COMMON
@end deffn


@deffn {Function} vector->@@vector vec :optional start end clamp
@findex vector->s8vector
@findex vector->u8vector
@findex vector->s16vector
@findex vector->u16vector
@findex vector->s32vector
@findex vector->u32vector
@findex vector->s64vector
@findex vector->u64vector
@findex vector->f16vector
@findex vector->f32vector
@findex vector->f64vector
@findex vector->c32vector
@findex vector->c64vector
@findex vector->c128vector
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
Converts a vector @var{vec} to a @@vector.
If @var{start} and/or @var{end} are given, they limit the range of
@var{vec} to be copied.
Optional argument @var{clamp} specifies the behavior when
the element of @var{vec} is out of the valid range.
(The @var{clamp} argument is Gauche's extension.)

Note that the generic function @code{coerce-to} can be used as well,
if you import @code{gauche.collection}.
@c JP
ベクタ@var{vec}を@@vectorに変換します。
省略可能な引数@var{start}と@var{end}が与えられた場合、
それらは取り出される要素の範囲を制限します。
省略可能な引数@var{clamp}が、ベクタ内の要素が正しい範囲外の数であった場合の
動作を指定します。
(@var{clamp}引数はGauche独自拡張です。)

モジュール@code{gauche.collection}をインポートしていれば、
総称関数@code{coerce-to}を使うこともできます。
@c COMMON
@example
(vector->f64vector '#(3.1 5.4 3.2)) @result{} #f64(3.1 5.4 3.2)

(use gauche.collection)
(coerce-to <f64vector> '#(3.1 5.4 3.2)) @result{} #f64(3.1 5.4 3.2)
@end example
@end deffn

@defun vector->uvector classs vec
@c MOD gauche.uvector
@c EN
A ganeric version of @code{vector->@@vector}.  You can pass a uvector
class @var{class}.
@c JP
@code{vector->@@vector}の汎用バージョンです。
nユニフォームベクタのクラスを@var{class}に渡します。
@c COMMON

@example
(vector->uvector <u8vector> '#(0 1 2)) @result{} #u8(0 1 2)
@end example
@end defun

@defun uvector-alias uvector-class vec :optional start end
@c MOD gauche.uvector
@c EN
This procedure creates an uvector of class @var{uvector-class}
that shares the storage of the given uniform vector @var{vec}.
If optional @var{start} and @var{end} arguments are given,
only the specified range of @var{vec} is used for the new vector.
Since the storage is shared, modification of the original vector
can be seen from the new vector, or vice versa.
@c JP
この手続きは、クラスが@var{uvector-class}であり、
ユニフォームベクタ@var{vec}のメモリ領域を共有するような
新しいユニフォームベクタを作成して返します。
省略可能な引数@var{start}と@var{end}が与えられた場合は
@var{vec}の内容のうちそれらのインデックスで指定される範囲のみが使われます。
メモリ領域が共有されているので、@var{vec}に加える変更は
新しいベクタから見えますし、その逆も可能です。
@c COMMON

@c EN
The class @var{uvector-class} must be either one of the uniform
vector class, but is not necessary match the class of the
source vector @var{vec}.   In such case, the new vector looks at the same
region of @var{vec}'s memory, but interprets it differently.
For example, the following code determines whether Gauche
is running on big-endian or little-endian machine:
@c JP
クラス@var{uvector-class}はユニフォームベクタのクラスでなければなりませんが、
@var{vec}のクラスと一致している必要はありません。
そのような場合は、新しいベクタは@var{vec}と同じメモリ領域の値を
異なる値と解釈するかもしれません。
例えば、次のコードはGaucheが走っているマシンが
リトルエンディアンであるかビッグエンディアンであるかを判定します。
@c COMMON

@example
(let ((u8v (uvector-alias <u8vector> #u32(1))))
  (if (zero? (u8vector-ref u8v 0))
      'big-endian
      'little-endian))
@end example

@c EN
If the @var{uvector-class} is other than s8vector or u8vector,
the region the new vector points has to meet the alignment
requirement.  You can assume the beginning of the source vector
is aligned suitable for any uniform vectors.  So, for example,
if you're creating u32vector from u8vector, the @var{start} and
@var{end} must be multiple of 4 (or, if they're omitted, the length
of the original u8vector must be multiple of 4).
An error is signaled when the given parameters doesn't satisfy
alignment constraint.
@c JP
@var{uvector-class}がs8vectorかu8vector以外の場合、
新しいベクタが指す領域は、そのベクタの要素のアラインメントの要請に
したがっていなければなりません。
ユニフォームベクタの開始点は常に全てのユニフォームベクタのアラインメント要請を
満たします。したがって、例えばu8vectorからu32vectorを作成する場合、
@var{start}および@var{end}は4の倍数でなければなりません
(あるいは、@var{start}/@var{end}が省略された場合、@var{vec}の長さが
4の倍数でなければなりません)。
与えられたパラメータでアラインメントの要請が満たせない場合はエラーが通知されます。
@c COMMON
@end defun




@node Uvector numeric operations, Uvector block I/O, Uvector conversion operations, Uniform vector library
@subsection Uvector numeric operations
@c NODE ユニフォームベクタの数値演算

@c EN
These are Gauche extension that allows faster arithmetic over uniform
vectors, than extracting and calculating element-wise values.

Most procedures comes with two flavors, a functional version (without @code{!}
in the name) and a linear-update version (with @code{!} in the name).

A functional version assumes the caller treats the arguments and
results immutable objects; mutating them later could have unexpected
consequences.  (Notably, the functional version may return one of its
arguments as is, or returns a pre-computed value,
so you shouldn't assume the return values are freshly
allocated objects, unless it is noted so explicitly.)

A linear update version may reuse the storage of the designated
argument to produce the return value.  Gauche tries to reuse the
argument as much as possible, but you should always use the return
value and shouldn't assume the argument itself is modified in-place.
In fact, after calling linear-updating procedure, you can't use
the argument that may be modified, since you can't assume the state
of the object after calling the procedure.
@c JP
ここに上げる手続きはGaucheの拡張で、
ユニフォームベクタ全体に渡る演算を、要素ごとに計算するよりも速く行います。

ほとんどの手続きには関数型バージョン(名前に@code{!}の無いもの)と
線形更新バージョン(名前に@code{!}のついたもの)の二つが用意されています。

関数型バージョンは、呼び出し元が引数と戻り値を変更不可なオブジェクトとして
扱うことを期待します。後からそれらを変更することは予想外の結果を引き起こすかも
しれません(特に、関数型バージョンでは引数に渡されたオブジェクトをそのまま
返したり、既に計算済みの値を返したりする可能性もあるので、
特に記述されてなければ、戻り値が常に新たにアロケートされたものであると考えてはいけません。)

線形更新バージョンは、結果を作るために特定の引数のメモリを再利用する可能性が
あります。Gaucheではアロケーションを最小化するようにできるだけメモリの再利用をしますが、
引数がその場で変更されていることをあてにしてはいけません。必ず戻り値を利用するように
してください。
変更され得る引数については、呼び出し後にそれがどういう状態になっているかは定義されません。
@c COMMON

@deffn {Function} @@vector-add vec val :optional clamp
@deffnx {Function} @@vector-add! vec val :optional clamp
@deffnx {Function} @@vector-sub vec val :optional clamp
@deffnx {Function} @@vector-sub! vec val :optional clamp
@deffnx {Function} @@vector-mul vec val :optional clamp
@deffnx {Function} @@vector-mul! vec val :optional clamp
@findex s8vector-add
@findex s8vector-add!
@findex s8vector-sub
@findex s8vector-sub!
@findex s8vector-mul
@findex s8vector-mul!
@findex u8vector-add
@findex u8vector-add!
@findex u8vector-sub
@findex u8vector-sub!
@findex u8vector-mul
@findex u8vector-mul!
@findex s16vector-add
@findex s16vector-add!
@findex s16vector-sub
@findex s16vector-sub!
@findex s16vector-mul
@findex s16vector-mul!
@findex u16vector-add
@findex u16vector-add!
@findex u16vector-sub
@findex u16vector-sub!
@findex u16vector-mul
@findex u16vector-mul!
@findex s32vector-add
@findex s32vector-add!
@findex s32vector-sub
@findex s32vector-sub!
@findex s32vector-mul
@findex s32vector-mul!
@findex u32vector-add
@findex u32vector-add!
@findex u32vector-sub
@findex u32vector-sub!
@findex u32vector-mul
@findex u32vector-mul!
@findex s64vector-add
@findex s64vector-add!
@findex s64vector-sub
@findex s64vector-sub!
@findex s64vector-mul
@findex s64vector-mul!
@findex u64vector-add
@findex u64vector-add!
@findex u64vector-sub
@findex u64vector-sub!
@findex u64vector-mul
@findex u64vector-mul!
@findex f16vector-add
@findex f16vector-add!
@findex f16vector-sub
@findex f16vector-sub!
@findex f16vector-mul
@findex f16vector-mul!
@findex f32vector-add
@findex f32vector-add!
@findex f32vector-sub
@findex f32vector-sub!
@findex f32vector-mul
@findex f32vector-mul!
@findex f64vector-add
@findex f64vector-add!
@findex f64vector-sub
@findex f64vector-sub!
@findex f64vector-mul
@findex f64vector-mul!
@findex c32vector-add
@findex c32vector-add!
@findex c32vector-sub
@findex c32vector-sub!
@findex c32vector-mul
@findex c32vector-mul!
@findex c64vector-add
@findex c64vector-add!
@findex c64vector-sub
@findex c64vector-sub!
@findex c64vector-mul
@findex c64vector-mul!
@findex c128vector-add
@findex c128vector-add!
@findex c128vector-sub
@findex c128vector-sub!
@findex c128vector-mul
@findex c128vector-mul!
@c MOD gauche.uvector
@c EN
Element-wise arithmetic.  @var{Vec} must be a @@vector,
and @var{val} must be either a @@vector, a vector, or a list
of the same length as @var{vec}, or a number
(an exact integer for integer vectors,
and a real number for f32- and f64-vectors).
@c JP
要素毎の計算手続きです。@var{vec}は@@vectorでなければなりません。
また、@var{val}は@var{vec}と同じ長さの@@vectorかベクタかリスト、
あるいは数値(整数ベクタに対しては正確な整数、実数ベクタに対しては実数)
でなければなりません。
@c COMMON

@c EN
If @var{val} is a @@vector, its elements are
added to, subtracted from, or multiplied by the corresponding
elements of @var{vec}, respectively,
and the results are gathered to a @@vector
and returned.  The linear-update version (those have bang `!' in the name)
reuses @var{vec} to store the result, and also returns it.
If the result of calculation goes out of the range of @@vector's
element, the behavior is specified by @var{clamp} optional argument.
(For f32vector and f64vector, @var{clamp} argument is ignored and
the result may contain infinity).
@c JP
@var{val}が@@vectorの場合、
@var{vec}と対応する要素毎に加算、減算、乗算が行われ、
結果が@@vectorとして返されます。
線形更新バージョン(名前に`!'がついているもの)では、@var{vec}が
結果を格納するために再利用され、またそれが返されます。
演算の結果が@@vectorの要素の値域外になった場合の動作は
省略可能な引数@var{clamp}によって指定されます。
(f32vectorとf64vectorでは、値域外になった要素にはinfinityが格納され、
@var{clamp}の値は無視されます)。
@c COMMON

@c EN
If @var{val} is a number, it is added to, subtracted from, or
multiplied by each element of @var{vec}, respectively.
@c JP
@var{val}が数値である場合、@var{vec}の各要素とその数値の間で演算が行われます。
@c COMMON

@example
(s8vector-add '#s8(1 2 3 4) '#s8(5 6 7 8)) @result{} #s8(6 8 10 12)
(u8vector-sub '#u8(1 2 3 4) '#u8(2 2 2 2)) @result{} @r{error}
(u8vector-sub '#u8(1 2 3 4) '#u8(2 2 2 2) 'both) @result{} #u8(0 0 1 2)

(f32vector-mul '#f32(3.0 2.0 1.0) 1.5) @result{} #f32(4.5 3.0 1.5)
@end example
@end deffn

@deffn {Function} @@vector-div vec val
@deffnx {Function} @@vector-div! vec val
@findex f16vector-div
@findex f16vector-div!
@findex f32vector-div
@findex f32vector-div!
@findex f64vector-div
@findex f64vector-div!
@findex c32vector-div
@findex c32vector-div!
@findex c64vector-div
@findex c64vector-div!
@findex c128vector-div
@findex c128vector-div!
@c MOD gauche.uvector
@c EN
Element-wise division of flonum vectors.   These are only defined
for f16, f32 and f64vector.  @var{val} must be a @@vector,
a vector or a list of the same length as @var{vec}, or a real number.
@c JP
要素毎の除算です。これらはf32vectorとf64vectorのみに対して定義されます。
@var{val}は@var{vec}と同じ大きさの@@vectorかベクタかリスト、
あるいは実数でなければなりません。
@c COMMON

@example
(f32vector-div '#f32(1.0 2.0 3.0) 2.0) @result{} #f32(0.5 1.0 1.5)
@end example
@end deffn


@deffn {Function} @@vector-and vec val
@deffnx {Function} @@vector-and! vec val
@deffnx {Function} @@vector-ior vec val
@deffnx {Function} @@vector-ior! vec val
@deffnx {Function} @@vector-xor vec val
@deffnx {Function} @@vector-xor! vec val
@findex s8vector-and
@findex s8vector-and!
@findex s8vector-ior
@findex s8vector-ior!
@findex s8vector-xor
@findex s8vector-xor!
@findex u8vector-and
@findex u8vector-and!
@findex u8vector-ior
@findex u8vector-ior!
@findex u8vector-xor
@findex u8vector-xor!
@findex s16vector-and
@findex s16vector-and!
@findex s16vector-ior
@findex s16vector-ior!
@findex s16vector-xor
@findex s16vector-xor!
@findex u16vector-and
@findex u16vector-and!
@findex u16vector-ior
@findex u16vector-ior!
@findex u16vector-xor
@findex u16vector-xor!
@findex s32vector-and
@findex s32vector-and!
@findex s32vector-ior
@findex s32vector-ior!
@findex s32vector-xor
@findex s32vector-xor!
@findex u32vector-and
@findex u32vector-and!
@findex u32vector-ior
@findex u32vector-ior!
@findex u32vector-xor
@findex u32vector-xor!
@findex s64vector-and
@findex s64vector-and!
@findex s64vector-ior
@findex s64vector-ior!
@findex s64vector-xor
@findex s64vector-xor!
@findex u64vector-and
@findex u64vector-and!
@findex u64vector-ior
@findex u64vector-ior!
@findex u64vector-xor
@findex u64vector-xor!
@c MOD gauche.uvector
@c EN
Element-wise logical (bitwise) operation.
These procedures are only defined for integral vectors.
@var{val} must be a @@vector, a vector or a list
of the same length as @var{vec},
or an exact integer.  Bitwise and, inclusive or or exclusive or
is calculated between each element in @var{vec} and the corresponding
element of @var{val} (when @var{val} is a non-scalar value),
or @var{val} itself (when @var{val} is an integer).
The result is returned in a @@vector.
The linear-update version reuses @var{vec} to store the result,
and also returns it.
@c JP
要素毎の論理(ビット)演算です。
これらの手続きは整数ベクタに対してのみ定義されています。
@var{val}は@var{vec}と同じ大きさの@@vectorかベクタかリスト、
あるいは正確な整数でなければなりません。@var{vec}の各要素と、対応する@var{val}の要素
(@var{val}が非スカラー値の場合)もしくは@var{val}自身
(@var{val}が整数の場合)とのビット毎のand, inclusive orまたはexclusive or
が計算され、結果が@@vectorで返されます。
線形更新バージョン(名前に`!'がついているもの)では、@var{vec}が
結果を格納するために再利用され、またそれが返されます。
@c COMMON
@end deffn

@deffn {Function} @@vector-dot vec0 vec1
@findex s8vector-dot
@findex s16vector-dot
@findex s32vector-dot
@findex s64vector-dot
@findex u8vector-dot
@findex u16vector-dot
@findex u32vector-dot
@findex u64vector-dot
@findex f16vector-dot
@findex f32vector-dot
@findex f64vector-dot
@findex c32vector-dot
@findex c64vector-dot
@findex c128vector-dot
@c MOD gauche.uvector
@c EN
Calculates the dot product of two @@vectors.
The length of @var{vec0} and @var{vec1} must be the same.
@c JP
ふたつの@@vectorの内積を計算します。
@var{vec0}と@var{vec1}の長さは等しくなければなりません。
@c COMMON
@end deffn

@deffn {Function} @@vector-range-check vec min max
@findex s8vector-range-check
@findex s16vector-range-check
@findex s32vector-range-check
@findex s64vector-range-check
@findex u8vector-range-check
@findex u16vector-range-check
@findex u32vector-range-check
@findex u64vector-range-check
@findex f16vector-range-check
@findex f32vector-range-check
@findex f64vector-range-check
@c MOD gauche.uvector
@c EN
@var{Vec} must be a @@vector, and each of @var{min} and @var{max}
must be either a @@vector, a vector or a list of the same length
as @var{vec}, or a number, or @code{#f}.

For each element in @var{vec}, this procedure checks if the value
is between @var{minval} and @var{maxval} inclusive, where
@var{minval} and @var{maxval} are the corresponding values of
@var{min} and @var{max} (when @var{min} and/or @var{max} is/are
non-scalar value) or @var{min} and @var{max} themselves (when
@var{min} and/or @var{max} is/are a number).
When @var{min} is @code{#f}, negative infinity is assumed.
When @var{max} is @code{#f}, positive infinity is assumed.

If all the elements in @var{vec} are within the range, @code{#f} is
returned.  Otherwise, the index of the leftmost element of @var{vec}
that is out of range is returned.
@c JP
@var{vec}は@@vectorでなければなりません。
@var{min}と@var{max}はそれぞれ、@var{vec}と同じ長さの@@vector、
ベクタ、リストのいずれかか、実数もしくは@code{#f}でなければなりません。

@var{vec}の各要素に対して、この手続きはそれが対応する@var{minval}と@var{maxval}
の間にあるかどうかを検査します。@var{minval}と@var{maxval}も範囲に含みます。
ここで、@var{minval}と@var{maxval}は、@var{min}/@var{max}が非スカラー値
であれば@var{vec}の要素に対応するそれぞれの要素、
@var{min}/@var{max}が数値であればその数値そのものです。
@var{min}が@code{#f}の場合、最小値はマイナス無限大と考えられます。
@var{max}が@code{#f}の場合、最大値はプラス無限大と考えられます。

@var{vec}の全ての要素が範囲内であった場合は@code{#f}が返されます。
そうでなければ、範囲を外れた要素のうちもっとも左のものの@var{vec}内での
インデックスが返されます。
@c COMMON

@example
(u8vector-range-check '#u8(3 1 0 2) 0 3)  @result{} #f
(u8vector-range-check '#u8(3 1 0 2) 1 3)  @result{} 2

(u8vector-range-check '#u8(4 32 64 98) 0 '#u8(10 40 70 90))
  @result{} 3

;; Range check in a program
(cond
 ((u8vector-range-check u8v 1 31)
  => (lambda (i)
      (errorf "~sth vector element is out of range: ~s"
              i (u8vector-ref u8v i))))
 (else (do-something u8v)))
@end example
@end deffn

@deffn {Function} @@vector-clamp vec min max
@deffnx {Function} @@vector-clamp! vec min max
@findex s8vector-clamp
@findex s16vector-clamp
@findex s32vector-clamp
@findex s64vector-clamp
@findex u8vector-clamp
@findex u16vector-clamp
@findex u32vector-clamp
@findex u64vector-clamp
@findex f32vector-clamp
@findex f64vector-clamp
@findex s8vector-clamp!
@findex s16vector-clamp!
@findex s32vector-clamp!
@findex s64vector-clamp!
@findex u8vector-clamp!
@findex u16vector-clamp!
@findex u32vector-clamp!
@findex u64vector-clamp!
@findex f16vector-clamp!
@findex f32vector-clamp!
@findex f64vector-clamp!
@c MOD gauche.uvector
@c EN
@var{Vec} must be a @@vector, and each of @var{min} and @var{max}
must be either a @@vector, a vector or a list of the same length
as @var{vec}, or a number, or @code{#f}.

Like @@vector-range-check, these procedures check if
each element of @var{vec} are within the range between @var{minval}
and @var{maxval} inclusive, which are derived from @var{min} and @var{max}.
If the value is less than @var{minval}, it is replaced by @var{minval}.
If the value is grater than @var{maxval}, it is replaced by @var{maxval}.

@@vector-clamp creates a copy of @var{vec} and do clamp
operation on it, while @@vector-clamp! modifies @var{vec}.
Both return the clamped vector.
@c JP
@var{vec}は@@vectorでなければなりません。
@var{min}と@var{max}はそれぞれ、@var{vec}と同じ長さの@@vector、
ベクタ、リストのいずれかか、実数もしくは@code{#f}でなければなりません。

@@vector-range-checkと同じように、この手続きは@var{vec}の各要素が
@var{min}および@var{max}で指定される最小値と最大値の間にあるかどうかを
検査します。要素が最小値より小さかった場合はそれが最小値に置き換えられます。
要素が最大値より大きかった場合はそれが最大値に置き換えられます。

@@vector-clampは@var{vec}のコピーを作ってそれに対して
クランプ操作を行います。@@vector-clamp!は@var{vec}を直接
変更します。どちらもクランプ操作が行われた後の@@vectorを返します。
@c COMMON

@example
(s8vector-clamp '#s8(8 14 -3 -22 0) -10 10) @result{} #s8(8 10 -3 -10 0)
@end example
@end deffn


@node Uvector block I/O, Bytevector compatibility, Uvector numeric operations, Uniform vector library
@subsection Uvector block I/O
@c NODE ユニフォームベクタのブロック入出力

@c EN
A uniform vector can be seen as an abstraction of a chunk of memory.
So you might want to use it for binary I/O.  Yes, you can do it.
@c JP
ユニフォームベクタは、メモリの固まりを抽象化しているものと考えることも
できます。それなら、それをバイナリI/Oに使えないでしょうか。もちろんできます。
@c COMMON

@defun read-uvector class size :optional iport endian
@c MOD gauche.uvector
@c EN
Reads @var{size} elements of uvector of class @var{class} from
@var{iport}, and returns fleshly created uvector.  If @var{iport}
is omitted, the curret input port is used.
@c JP
クラス@code{class}のユニフォームベクタの要素を@var{size}個、@var{iport}から
読み込み、それを新たに作ったユニフォームベクタとして返します。
@var{iport}が省略された場合は、現在の入力ポートが使われます。
@c COMMON

@c EN
For example, you can read input as an octet stream as follows:
@c JP
例えば次のようにして、入力をオクテットストリームとして読み込めます:
@c COMMON

@example
(with-input-from-string "abcde"
  (^[] (read-uvector <u8vector> 5)))
 @result{} #u8(97 98 99 100 101)
@end example

@c EN
If the input port has already reached EOF, an EOF object is
returned.  The returned uvector can be shorter than @var{size}
if the input reaches EOF before @var{size} elements are read.
@c JP
入力ポートが既にEOFに達していた場合はEOFオブジェクトが返されます。
@var{size}要素を読む前に入力がEOFに達した場合、返されるuvectorの長さは
@var{size}より短いものとなります。
@c COMMON

@c EN
If the @var{iport} is a buffered port with `modest' or `none'
buffering mode (@pxref{File ports}), @code{read-uvector} may return
before @var{size} elements are read, even if @var{iport}
hasn't reached EOF.  The ports connected to a pipe or a network socket
behave so by default.
@c JP
@var{iport}がバッファードポートであり、そのバッファリングモードが
`modest' か `none' であった場合、@code{read-uvector}は@var{iport}が
EOFに達していなくても、@var{size}要素を読む前に戻ることがあります
(バッファリングモードについては@ref{File ports}を参照して下さい)。
パイプやネットワークに接続されたポートはデフォルトでそのように振舞います。
@c COMMON

@c EN
The data is read as a byte stream, so if you give uniform vectors
other than s8vector or u8vector, your result may affected by
the endianness.  If the optional argument @var{endian} is
given, the input is interpreted in that endianness.
When omitted, the value of the parameter @code{default-endian}
is used.  @xref{Endianness}, for more about endian handling.
@c JP
データはバイトストリームとして読まれるので、
s8vectorとu8vector以外のユニフォームベクタを与えた場合は
結果がエンディアンに影響を受けることに注意して下さい。
省略可能引数@var{endian}によって、入力データのエンディアンを指定
することができます。省略した場合はパラメータ@code{default-endian}の
値が使われます。エンディアンの扱いについてより詳しくは@ref{Endianness}を参照して
ください。
@c COMMON

@c EN
If the size of the input data is unknown and you need to read everything
until EOF, use @code{port->uvector} below.
@c JP
入力データの大きさが不明で、EOFまで全てを読み込みたい場合は、下の
@code{port->uvector}を使ってください。
@c COMMON
@end defun

@defun read-bytevector size :optional iport
[R7RS base]
@c MOD gauche.uvector
@c EN
Equivalent to @code{(read-uvector <u8vector> size iport)}.
This is an R7RS base procedure.
@c JP
@code{(read-uvector <u8vector> size iport)}と等価です。
R7RS baseにある手続きです。
@c COMMON
@end defun

@defun read-uvector! vec :optional iport start end endian
@c MOD gauche.uvector
@c EN
Reads a chunk of data from the given input port @var{iport},
and stores it to the uniform vector @var{vec}.
You can give any uniform vector.
If optional @var{start} and @var{end}
arguments are given, they specify the index range in @var{vec}
that is to be filled, and the rest of the vector remains untouched.
Otherwise, entire vector is used.  A special value -1 for @var{end}
indicates the end of @var{vec}.
If @var{iport} is omitted, the current input port is used.
@c JP
与えられた入力ポート@var{iport}からデータの固まりを読みだし、それを
ユニフォームベクタ@var{vec}に格納します。
どんな種類のユニフォームベクタでも与えることができます。
省略可能な引数@var{start}と@var{end}が与えられた場合は、
それらが@var{vec}中でデータが格納されるべき領域のインデックスの範囲を
示します。@var{end}については-1で@var{vec}の最後を示すこともできます。
その範囲外の@var{vec}の値は変更されません。
@var{start}、@var{end}が与えられなかった場合は@var{vec}全体が使われます。
@var{iport}が省略された場合はカレント入力ポートが使われます。
@c COMMON

@c EN
If the input reached EOF before the required region of @var{vec}
is filled, the rest of the vector is untouched.
@c JP
要求された領域を埋め終る前に入力がEOFに達した場合は、ベクタの残りの部分は
変更されません。
@c COMMON

@c EN
If @var{iport} is already reached EOF when @code{read-uvector!} is
called, an EOF object is returned.  Otherwise,
the procedure returns the number of @emph{elements} read (not bytes).
@c JP
@code{read-uvector!}が呼ばれた時既に@var{iport}がEOFに達していた場合は
EOFが、そうでなければ読まれた要素の数 (バイト数ではありません) が返されます。
@c COMMON

@c EN
If the @var{iport} is a buffered port with `modest' or `none'
buffering mode (@pxref{File ports}), @code{read-uvector!} may return
before all the elements in @var{vec} is filled, even if @var{iport}
hasn't reached EOF.  The ports connected to a pipe or a network socket
behave so by default.  If you know there will be enough data arriving and
want to make sure @var{vec} is filled, change the buffering mode of
@var{iport} to `full'.
@c JP
@var{iport}がバッファードポートであり、そのバッファリングモードが
`modest' か `none' であった場合、@code{read-uvector!}は@var{iport}が
EOFに達していなくても、@var{vec}を埋める前に戻ることがあります
(バッファリングモードについては@ref{File ports}を参照して下さい)。
パイプやネットワークに接続されたポートはデフォルトでそのように振舞います。
もし、十分なデータが到着することがわかっており、@var{vec}を確実に埋めたい場合は
ポートのバッファリングモードを`full'に変更して下さい。
@c COMMON

@c EN
The data is read as a byte stream, so if you give uniform vectors
other than s8vector or u8vector, your result may affected by
the endianness.  If the optional argument @var{endian} is
given, the input is interpreted in that endianness.
When omitted, the value of the parameter @code{default-endian}
is used.  @xref{Endianness}, for more about endian handling.
@c JP
データはバイトストリームとして読まれるので、
s8vectorとu8vector以外のユニフォームベクタを与えた場合は
結果がエンディアンに影響を受けることに注意して下さい。
省略可能引数@var{endian}によって、入力データのエンディアンを指定
することができます。省略した場合はパラメータ@code{default-endian}の
値が使われます。エンディアンの扱いについてより詳しくは@ref{Endianness}を参照して
ください。
@c COMMON
@end defun

@defun read-block! vec :optional iport start end endian
@c MOD gauche.uvector
@c DEPRECATED
@c EN
An old name of @code{read-uvector!}.  Supported for the backward
compatibility, but new code should use @code{read-uvector!}.
@c JP
@code{read-uvector!}の古い名前です。互換性のためサポートされていますが、
新しいコードでは@code{read-uvector!}を使ってください。
@c COMMON
@end defun

@defun port->uvector iport :optional class
@c MOD gauche.uvector
@c EN
Read data from the input port @var{iport} until EOF and store them
into a uvector of @var{class}.  If @var{class} is omitted,
@code{<u8vector>} is used.

If you specify a class of uvector whose element is more than an octet,
the input data is packed with platform's native byteorder.

This procedure is parallel to @code{port->string} etc.
(@pxref{Input utility functions}).
@c JP
入力ポート@var{iport}からEOFまでデータを読み込み、@var{class}クラスの
ユニフォームベクタに格納して返します。@var{class}が省略された場合は
@code{<u8vector>}が使われます。

要素が1オクテット以上のユニフォームベクタのクラスを指定した場合、
各要素はプラットフォームのネイティブバイトオーダーで埋められます。

この手続きは組み込みの@code{port->string}等と対応しています
(@ref{Input utility functions}参照)。
@c COMMON
@end defun

@defun read-bytevector! bv :optional iport start end
[R7RS base]
@c MOD gauche.uvector.
@c EN
Similar to @code{read-uvector!}, but @var{bv} must be a u8vector.
This is an R7RS base procedure.
@c JP
@code{read-uvector!}と似ていますが、@var{bv}はu8vectorでなければなりません。
これはR7RS baseにある手続きです。
@c COMMON
@end defun


@defun write-uvector vec :optional oport start end endian
@c MOD gauche.uvector
@c EN
Writes out the content of the uniform vector @var{vec} 'as is'
to the output port @var{oport}.   If @var{oport} is omitted,
the current output port is used.
If optional @var{start} and @var{end} arguments are given,
they specify the index range in @var{vec} to be written out.
A special value -1 for @var{end} indicates the end of @var{vec}.
This procedure returns an unspecified value.
@c JP
ユニフォームベクタ@var{vec}の内容を「そのまま」@var{oport}に書き出します。
@var{oport}が省略された場合はカレント出力ポートが使われます。
省略可能な引数@var{start}と@var{end}が与えられた場合は、
それらのインデックスの範囲が示す@var{vec}の内容のみが出力されます。
@var{end}に-1を渡して@var{vec}の最後を示すこともできます。
この手続きの返す値は未定義です。
@c COMMON

@c EN
If you write out a uniform vector except s8vector and u8vector, the
care should be taken about the endianness, as in @code{read-uvector}.
The optional argument @var{endian} specifies the output endian.
When it is omitted, the value of the parameter @code{default-endian}
is used (@pxref{Endianness}).
@c JP
@code{s8vector}と@code{u8vector}以外のユニフォームベクタを与えた場合、
@code{read-uvector}と同じようにエンディアンの影響を受けることに注意して
下さい。省略可能引数@var{endian}によって出力のエンディアンを
指定できます。省略した場合はパラメータ@code{default-endian}の値が
使われます (@ref{Endianness}参照)。
@c COMMON
@end defun

@deffn {Function} write-@@vector vec :optional port
@findex write-u8vector
@findex s8ite-u8vector
@findex u16ite-u8vector
@findex s16ite-u8vector
@findex u32ite-u8vector
@findex s32ite-u8vector
@findex u64ite-u8vector
@findex s64ite-u8vector
@findex f16ite-u8vector
@findex f32ite-u8vector
@findex f64ite-u8vector
@findex c32ite-u8vector
@findex c64ite-u8vector
@findex c128ite-u8vector
[R7RS vector.@@]
@c MOD gauche.uvector
@c EN
@c JP
@c COMMON
@end deffn

@defun write-bytevector bv :optional oport start end
[R7RS base]
@c MOD gauche.uvector
@c EN
Similar to @code{write-uvector}, but @var{bv} must be a u8vector.
This is an R7RS base procedure.
@c JP
@code{write-uvector}と似ていますが、@var{bv}はu8vectorでなければなりません。
R7RS baseの手続きです。
@c COMMON
@end defun

@defun write-block vec :optional oport start end endian
@c MOD gauche.uvector
@c DEPRECATED
@c EN
An old name of @code{write-uvector}.  Supported for the backward
compatibility, but new code should use @code{write-uvector}.
@c JP
@code{write-uvector}の古い名前です。互換性のためサポートされていますが、
新しいコードでは@code{write-uvector}を使ってください。
@c COMMON
@end defun



@node Bytevector compatibility,  , Uvector block I/O, Uniform vector library
@subsection Bytevector compatibility
@c NODE バイトベクタ互換性

@c EN
R7RS-small includes bytevectors in its core (@code{scheme.base}).
In Gauche, bytevectors are the same as u8vectors.

The basic R7RS bytevector procedures are provided in this module.
Conversion between bytevectors and strings are provided in
@code{gauche.unicode} (@pxref{Unicode transfer encodings})
and @code{srfi.181} (@pxref{Transcoded ports}).
@c JP
R7RS-smallはコア(@code{scheme.base})にバイトベクタを含んでいます。
Gaucheでは、バイトベクタはu8vectorと同じです。

R7RSのバイトベクタの基本的な手続きはこのモジュールで提供されます。
ただし、文字列とバイトベクタの変換手続きは
@code{gauche.unicode}(@ref{Unicode transfer encodings}参照)および
@code{srfi.181}(@ref{Transcoded ports}参照)にあります。
@c COMMON

@defun bytevector byte @dots{}
@c MOD gauche.uvector
[R7RS base]
@c EN
Alias of @code{u8vector}.  Returns a fresh bytevector (u8vector) with
@var{byte} @dots{} as its elements.
@c JP
@code{u8vector}の別名です。@var{byte} @dots{}を要素とするバイトベクタ(u8vector)を
新たに作って返します。
@c COMMON
@end defun

@defun bytevector? obj
@c MOD gauche.uvector
[R7RS base]
@c EN
Alias of @code{u8vector?}.  Returns true iff @var{obj} is
a bytevector (u8vector).
@c JP
@code{u8vector?}の別名です。@var{obj}がバイトベクタ(u8vector)なら
@code{#t}を、そうでなければ@code{#f}を返します。
@c COMMON
@end defun

@defun make-bytevector len :optional byte
@c MOD gauche.uvector
[R7RS base][R7RS bytevector]
@c EN
Returns a fresh bytevector (u8vector)
of length @var{len}.  All elements are initialized by @var{byte}
if given.

R7RS base accepts an exact integer between 0 and 255 inclusive as
@var{byte}.  R7RS bytevector extends the range to -128 to 255 inclusive,
while the negative value is wrapped-around by modulo 255.
This procedure supports the extended range.
@c JP
長さ@var{len}の新たなバイトベクタ(u8vector)を作って返します。
@var{byte}が与えられていれば、全ての要素をそれで初期化します。

R7RS baseでは@var{byte}の範囲を0から255(両端含む)としていますが、
R7RS bytevectorではそれを-128から255(両端含む)に拡張しています。
負の場合は256を法としてラップアラウンドします。この手続きは拡張範囲をサポートします。
@c COMMON
@end defun

@defun bytevector-length bv
@c MOD gauche.uvector
[R7RS base]
@c EN
Alias of @code{u8vector-length}.  Returns the length of the
bytevector (u8vector) @var{bv}.
@c JP
@code{u8vector-length}の別名です。バイトベクタ(u8vector) @var{bv}の長さを返します。
@c COMMON
@end defun

@defun bytevector-u8-ref bv k
@defunx bytevector-u8-set! bv k byte
@c MOD gauche.uvector
[R7RS base]
@c EN
Alias of @code{u8vector-ref} and @code{u8vector-set!}.
Read and write @var{k}-th element of a bytevector (u8vector) @var{bv}.

It is an error to give out-of-bound index.

The return value of @code{bytevector-u8-set!} is unspecified.

As Gauche's extension, @code{(setter bytevector-u8-ref)} is
@code{bytevector-u8-set!}.
@c JP
@code{u8vector-ref}と@code{u8vector-set!}の別名です。
バイトベクタ(u8vector) @var{bv} の@var{k}番目の要素を返す/セットします。

@var{k}が領域外ならエラーが投げられます。

@code{bytevector-u8-set!}の戻り値は規定されていません。

Gaucheの拡張として、@code{(setter bytevector-u8-ref)} は
@code{bytevector-u8-set!}になっています。
@c COMMON
@end defun

@defun bytevector-s8-ref bv k
@defunx bytevector-s8-set! bv k signed-byte
@c MOD gauche.uvector
[R7RS bytevector]
@c EN
Like @code{bytevector-u8-ref} and @code{bytevector-u8-set!}, but
treates octets as a signed byte, ranging from -128 to 127, inclusive.

As Gauche's extension, @code{(setter bytevector-s8-ref)} is
@code{bytevector-s8-set!}.
@c JP
オクテットを-128から127までの符号つきバイトと扱うことを除き、
それぞれ@code{bytevector-u8-ref}および@code{bytevector-u8-set!}と同じです。

Gaucheの拡張として、@code{(setter bytevector-s8-ref)} は
@code{bytevector-s8-set!}になっています。
@c COMMON
@end defun

@defun bytevector-copy bv :optional start end
@c MOD gauche.uvector
[R7RS base]
@c EN
Alias of @code{u8vector-copy}.  Returns a fresh copy of a
bytevector (u8vector) @var{bv}.  Optionally you can restrict the
range of the source vector by indices @var{start} (inclusive)
and @var{end} (exclusive).
@c JP
@code{u8vector-copy}の別名です。
バイトベクタ(u8vector) @var{bv} の新たなコピーを作って返します。
インデックス@var{start}と@var{end}でコピーする範囲を限定することができます
(@var{start}は含まれ、@var{end}は含まれない)。
@c COMMON
@end defun

@defun bytevector-copy! target tstart source :optional sstart send
@c MOD gauche.uvector
[R7RS base]
@c EN
Alias of @code{u8vector-copy!}.  Both @var{target} and @var{source}
muse be bytevectors (u8vectors), and @var{target} must be mutable.
Copy the content of @var{source} (optionally restricting the range
between indices @var{start} (inclusive) and @var{end} (exclusive))
into @var{target} starting at the index @var{tstart}.
@c JP
@code{u8vector-copy!}の別名です。
@var{target}と@var{source}はバイトベクタ(u8vector)で、@var{target}は
変更可能でなければなりません。@var{source}の内容 (@var{start}と@var{end}で
範囲を限定することもできます) を@var{target}の@var{tstart}以降へとコピーします。
@c COMMON
@end defun

@defun bytevector-copy!-r6 src sstart target tstart len
@c MOD gauche.uvector
@c EN
This is a compatibility procedure for R6RS @code{bytevector-copy!}
(hence the suffix @code{-r6}).  When R6RS bytevectors are
adpoted as R7RS-large @code{scheme.bytevector}, the R6RS version
of @code{bytevector-copy!} comes into R7RS as well
(hence R7RS has two different @code{bytevector-copy!}, one in
@code{scheme.base} and one in @code{scheme.bytevector}).

It's unfortunate
that R6RS tends to break tradition and invent a new API; here, the
arguments differ from other @code{*-copy!} procedures:
This procedure copies from @var{src}, starting from
@var{sstart} and length @var{len}, to @var{target} starting @var{tstart}.
@c JP
これはR6RSの@code{bytevector-copy!}との互換ルーチンです
(なので@code{-r6}サフィックスがついています)。
R6RSバイトベクタライブラリがR7RS-largeにも@code{scheme.bytevector}として
採り入れられたので、R6RSバージョンの@code{bytevector-copy!}もR7RSに入ってきました。
(なのでR7RSには二つの異なる@code{bytevector-copy!}があります。
ひとつは@code{scheme.base}に、もうひとつは@code{scheme.bytevector}に。)

残念なことに、R6RSはしばしば伝統を破って新しいAPIを発明することがあり、
この手続きもそのひとつで、他の@code{*-copy!}系の手続きと引数が異なります。
この手続きでは、バイトベクタ@var{src}の@var{sstart}から@var{len}の長さのデータを
@var{target}の@var{tstart}からの領域にコピーします。
@c COMMON
@end defun

@defun bytevector-append bv @dots{}
@c MOD gauche.uvector
[R7RS base]
@c EN
Alias of @code{u8vector-append}.  All arguments must be bytevectors
(u8vectors).  Returns a fresh bytevector whose elements are
the concatenation of elements of @var{bv} @dots{}.
@c JP
@code{u8vector-append}の別名です。
全ての引数はバイトベクタ(u8vector)でなければなりません。
引数の全ての要素をつなげた新たなバイトベクタを作って返します。
@c COMMON
@end defun

@defun bytevector=? bv1 bv2
@c MOD gauche.uvector
[R7RS bytevector]
@c EN
Alias of @code{u8vector=?}.  All arguments must be bytevectors
(u8vectors).  Returns @code{#t} iff all bytevectors are of the same
size and content.
@c JP
@code{u8vector=?}の別名です。全ての引数はバイトベクタ(u8vector)でなければなりません。
引数の大きさと内容が一致している時に限り@code{#t}を返します。
@c COMMON
@end defun

@defun bytevector->u8-list bv
@defunx u8-list->bytevector list
[R7RS bytevector]
@c EN
Convert a u8vector to a list of bytes, and vice versa.
Same as @code{u8vector->list} and @code{list->u8vector}, except to not
taking optional @var{start}/@var{end} arguments.
@c JP
それぞれ、u8vectorをバイトのリストへ変換、およびその逆を行う手続きです。
省略可能な@var{start}/@var{end}引数を取らないことを除き、
@var{u8vector->list}およぎ@code{list->u8vector}と同じです。
@c COMMON
@end defun


@c ----------------------------------------------------------------------
@node Comparing version numbers, Virtual ports, Uniform vector library, Library modules - Gauche extensions
@section @code{gauche.version} - Comparing version numbers
@c NODE バージョン番号の比較, @code{gauche.version} - バージョン番号の比較

@deftp {Module} gauche.version
@mdindex gauche.version
@c EN
This module provides a convenient procedure to compare
@emph{version numbers} or @emph{revision numbers},
such as "@code{0.5.1}", "@code{3.2-3}" or "@code{8.2pl1}".
Usually each release of software component has
a version number, and you can define order between them.
For example, version "1.2.3" is newer than "1.2" and
older than "2.1".   You can compare those version numbers like this:
@c JP
このモジュールは、バージョン番号(リリース番号)を比較する便利な手続きを提供します。
ここでのバージョン番号とはソフトウェアのリリースにつけられる
"@code{0.5.1}"、"@code{3.2-3}"、"@code{8.2pl1}"といった文字列で、
通常これらの番号間には順序関係が定義できます。
例えば "1.2.3" は "1.2" より新しいが "2.1" より古い、といった具合です。
以下のようにこれらの文字列の順序を比較することができるようになります。
@c COMMON

@example
(version<? "2.2.3" "2.2.11")     @result{} #t
(version<? "2.3.1" "2.3")        @result{} #f
(version<? "2.3.1-1" "2.3.1-10") @result{} #t
(version<? "13a" "5b")           @result{} #f
@end example

@c EN
There are no standard way to name versions, so I chose
one convention.   This won't work for all possible
variations, but I think it covers typical cases.
@c JP
バージョン番号の付け方には特に標準というものはありませんが、
よく使われている方法を採用しました。全ての場合に使えるとはいきませんが、
大抵の場合はカバーできるのではないかと思います。
@c COMMON

@c EN
Strictly speaking, you can only define partial order between
version numbers, for there can be branches.   This module
uses simple measure and just assumes the version numbers
can be fully ordered.
@c JP
厳密に言えば、分岐などの場合があるのでバージョン番号間の関係は半順序関係にしかなりません。
このモジュールでは単純な定義を使って、全順序関係があるものとして扱います。
@c COMMON

@c EN
The version number here is defined by the following syntax.
@c JP
まず、ここでのバージョン番号は以下の構文に従うものとします。
@c COMMON
@example
 <version> : <principal-release>
           | <version> <post-subrelease>
           | <version> <pre-subrelease>
 <principal-release> : <relnum>
 <post-subrelease>   : [.-] <relnum>
 <pre-subrelease>    : _ <relnum>?
 <relnum>            : [^._-]+
@end example

@c EN
Typically @code{<relnum>} is composed by numeric part and extension part.
For example, "23a" is composed by an integer 23 and extension "a".
If @code{<relnum>} doesn't begins with digits, we assume its
numeric part is -1.
@c JP
通常@code{<relnum>}は数字部分と、それに続く省略可能な拡張部分とからなります。
例えば "@code{23a}" は数字部分23と拡張部分"@code{a}"からなります。
もし@code{<relnum>}が数字で始まらない場合、その数字部分は-1であると考えることにします。
@c COMMON

@c EN
Then, the order of @code{<relnum>} is defined as follows:
@c JP
@code{<relnum>}の順序関係を次のように定義します。
@c COMMON
@enumerate
@item
@c EN
If relnum A and relnum B have different numeric part, we ignore the
extension and order them numerically, e.g.  "@code{3b}" < "@code{4a}".
@c JP
relnum Aとrelnum Bが異なる数字部分を持っている場合、拡張部分を無視して
数字部分を数値として比較します。例："@code{3b}" < "@code{4a}"。
@c COMMON
@item
@c EN
If relnum A and relnum B have the same numeric part, we compare
extension by alphabetically, e.g.  "@code{4c}" < "@code{4d}"
and "@code{5}" < "@code{5a}".
@c JP
relnum Aとrelnum Bの数字部分が等しい場合、拡張部分を辞書順に比較します。
例："@code{4c}" < "@code{4d}"、"@code{5}" < "@code{5a}"。
@c COMMON
@end enumerate

@c EN
Given the order of @code{<relnum>}, the order of version numbers
are defined as follows:
@c JP
@code{<relnum>}間の順序が定義できたところで、バージョン番号の順序を次のように定義します。
@c EN
@enumerate
@item
Decompose each version number into a list of @code{<principal-release>} and
subsequence subrelease components.   We call each element of
the list "release components".
@item
If the first release component of both lists are the same,
remove it from both.  Repeat this until the head of the lists differ.
@item
Now we have the following cases.
@enumerate
@item
Both lists are empty: versions are the same.
@item
One list (A) is empty and the other list (B) has post-subrelease
at head: A is prior to B
@item
One list (A) is empty and the other list (B) has pre-subrelease
at head: B is prior to A
@item
List A's head is post-subrelease and list B's head is
pre-subrelease: B is prior to A
@item
Both lists have post-subrelease or pre-subrelease at head:
compare their relnums.
@end enumerate
@end enumerate
Here are some examples:
@c JP
@enumerate
@item
各々のバージョン番号を分解して @code{<principal-release>} とそれに続く
サブリリース部品のリストに入れる。このリストの各要素のことを「リリース部品」
と呼びます。
@item
もし両方のリストの最初のリリース部品が同じなら、それを両方のリストから
取り除きます。これをリストの先頭が異るまでくりかえします。
@item
そうすると次のような場合に分られます。
@enumerate
@item
両方のリストが空： バージョンは同じ。
@item
一方のリスト (A) が空で、他方のリスト (B) の先頭がポストサブリリース：
A が B より前のバージョン。
@item
一方のリスト (A) が空で、他方のリスト (B) の先頭がプリサブリリース：
B が A より前のバージョン
@item
リスト A の先頭がポストサブリリースで、リスト B の先頭がプリサブリリース：
B が A より前のバージョン
@item
両方のリストとも先頭がポストサブリリースであるかプリサブリリース：
relnum を比較する。
@end enumerate
@end enumerate

以下はいくつかの例です。
@c COMMON
@example
"1" < "1.0" < "1.1" < "1.1.1" < "1.1.2" < "1.2" < "1.11"
"1.2.3" < "1.2.3-1" < "1.2.4"
"1.2.3" < "1.2.3a" < "1.2.3b"
"1.2_" < "1.2_rc0" < "1.2_rc1" < "1.2" < "1.2-pl1" < "1.2-pl2"
"1.1-patch112" < "1.2_alpha"
@end example

@c EN
The reason of having @code{<pre-subrelease>} is to allow
"release candidate" or "pre-release" version.

A trick: If you want ``version 1.2 release or later'', you
can say @code{(version<=? "1.2" v)}.  This excludes prerelease
versions such as @code{1.2_pre3}.
If you want ``version 1.2 release or later'',
you can say @code{(version<=? "1.2_" v)}, which includes
@code{1.2_pre1} etc., but excludes anything below, such as
@code{1.1.99999}.
@c JP
@code{<pre-subrelease>} があるのは、「リリース候補」あるいは
「プリリリース」のバージョンをつかえるようにするためです。

ヒント: 「1.2正式リリースもしくはそれ以降」をチェックした場合は
@code{(version<=? "1.2" v)} とします。これは、
@code{1.2_pre3}といったプレリリース版を除外します。一方、
「プレリリース版も含めて1.2もしくはそれ以降」としたい場合は
@code{(version<=? "1.2_" v)}と書けます。これは、
@code{1.2_pre1}等は含み、それ以前の例えば@code{1.1.99999}等は除外します。
@c COMMON

@c EN
It is common if you want to specify acceptable versions with
combination of conditions, e.g. ``version 1.3 or later, except
version 1.4.1'' or ``greater than version 1.1 and below 1.5''.
A @emph{version spec} is an S-expression to represent that condition.
You can use @code{version-satisfy?} to check if given version
satisfies the spec.
@c JP
許容できるバージョンを条件の組み合わせで指定したいことはよくあります。
例えば「バージョン1.3以降、ただし1.4.1を除く」とか、
「バージョン1.1以上で、1.5より前」等。
バージョン指定 (version spec) は、S式でバージョンに関する条件を表現する手段です。
@code{version-satisfy?}手続きで、バージョンがバージョン指定を満たしている
かどうかチェックできます。
@c COMMON

@c EN
The syntax of version spec is as follows.
@c JP
バージョン指定の構文は以下の通りです。
@c COMMON

@example
<version-spec> : <version>
               | (<op> <version>)
               | (and <version-spec> ...)
               | (or <version-spec> ...)
               | (not <version-spec>)

<version> : version string
<op>      : = | < | <= | > | >=
@end example

@end deftp

@defun version=? ver1 ver2
@defunx version<? ver1 ver2
@defunx version<=? ver1 ver2
@defunx version>? ver1 ver2
@defunx version>=? ver1 ver2
@c MOD gauche.version
@c EN
Returns a boolean value depending on the order of two version number
string @var{ver1} and @var{ver2}.  If the arguments contain invalid
strings as the defined version number, an error is signaled.
@c JP
ふたつのバージョン番号文字列 @var{ver1} と @var{ver2} の順序関係によって
真偽値を返します。もし引数が、バージョン番号を定義するのに不正な文字列を
含んでいた場合、エラーが上ります。
@c COMMON
@end defun

@defun version-compare ver1 ver2
@c MOD gauche.version
@c EN
Compares two version number strings @var{ver1} and @var{ver2},
and returns either -1, 0, or 1, depending whether @var{ver1} is
prior to @var{ver2}, @var{ver1} is the same as @var{ver2}, or
@var{ver1} is after @var{ver2}, respectively.
@c JP
ふたつのバージョン番号文字列 @var{ver1} と @var{ver2} を比較し、
@var{ver1} のほうが @var{ver2} より前、@var{ver1} と @var{ver2} は同じ、
@var{ver1} が @var{ver2} の後、の3つの場合によって、それぞれ、
-1、0、1 を返します。
@c COMMON
@end defun

@defun relnum-compare rel1 rel2
@c MOD gauche.version
@c EN
This is lower-level procedure of @code{version-compare}.  Compares
two release numbers (relnums) @var{rel1} and @var{rel2},
and returns either -1, 0, or 1 depending whether  @var{rel1} is
prior to @var{rel2}, @var{rel1} is the same as @var{rel2}, or
@var{rel1} is after @var{rel2}, respectively.
@c JP
これは @code{version-compare}の下位レベルの手続きです。
ふたつのリリース番号 (relnum) @var{rel1} と @var{rel2} を比較し、
@var{rel1} が @var{rel2} より前、@var{rel1} と @var{rel2} が同じ、
@var{rel1} が @var{rel2} より後、の3つの場合によって、それぞれ、
-1、0、1 を返します。
@c COMMON
@end defun

@c EN
The following procedures are to check if a given version
satisfies a version specification.
@c JP
以下の手続きは、与えられたバージョンがバージョン指定を満たすかどうかを
検査するためのものです。
@c COMMON

@defun valid-version-spec? spec
@c MOD gauche.version
@c EN
This is a syntax checker.  Returns @code{#t} if @var{spec} is
a valid version specification, @code{#f} otherwise.
See @code{gauche.version} module description for the definition of
version specification.
@c JP
構文チェッカです。@var{spec}がバージョン指定として正当なフォームであれば
@code{#t}を、そうでなければ@code{#f}を返します。
バージョン指定フォームについてはモジュール@code{gauche.version}の記述を参照してください。
@c COMMON
@end defun

@defun version-satisfy? spec version
@c MOD gauche.version
@c EN
Returns @code{#t} if @var{version} satisfies
a version specification @var{spec}, @code{#f} otherwise.
See @code{gauche.version} module description for the definition of
version specification.
@c JP
バージョン番号@var{version}がバージョン指定@var{spec}を満たせば@code{#t}を、
そうでなければ@code{#f}を返します。
バージョン指定フォームについてはモジュール@code{gauche.version}の記述を参照してください。
@c COMMON
@end defun



@c ----------------------------------------------------------------------
@node Virtual ports,  , Comparing version numbers, Library modules - Gauche extensions
@section @code{gauche.vport} - Virtual ports
@c NODE 仮想ポート, @code{gauche.vport} - 仮想ポート

@deftp {Module} gauche.vport
@mdindex gauche.vport
@c EN
@emph{Virtual ports}, or procedural ports, are the ports
whose behavior can be programmed in Scheme.
@c JP
@emph{仮想ポート}あるいは手続き的ポートとは、その振舞いを
Scheme でプログラム可能なポートです。
@c COMMON

@c EN
This module provides two kinds of virtual ports:
Fully virtual ports, in which every I/O operation invokes
user-provided procedures, and virtual buffered ports,
in which I/O operations are done on an internal buffer and
user-provided procedures are called only when the buffer
needs to be filled or flushed.
@c JP
このモジュールは 2 種類の仮想ポートを提供します。ひとつは、
完全仮想ポートで、すべての I/O 操作でユーザが提供する手続きが
呼出されるものです。もうひとつは、仮想バッファポートで、
I/O 操作は内部バッファ上で行われ、ユーザが提供する手続きは
バッファを一杯にするかフラッシュする必要がある場合にのみ
呼出されます。
@c COMMON

@c EN
This module also provides virtual buffered ports backed up
by a uniform vector, as an example of the feature.
@c JP
このモジュールはさらに、ユニフォームベクタにより
バックアップされる仮想バッファポートも提供します。
これは仮想ポートの使用例でもあります。
@c COMMON
@end deftp

@c EN
@subsubheading Fully virtual ports
@c JP
@subsubheading 完全仮想ポート
@c COMMON

@c EN
This type of virtual ports are realized by classes
@code{<virtual-input-port>} and @code{<virtual-output-port>}.
You can customize the port behavior by setting
appropriate slots with procedures.
@c JP
このタイプの仮想ポートは、@code{<virtual-input-port>} クラス
および @code{<virtual-output-port>} クラスで実現されています。
適切なスロットに手続きをセットすることでポートの振舞いをカスタマイズ
可能です。
@c COMMON

@deftp {Class} <virtual-input-port>
@clindex virtual-input-port
@c MOD gauche.vport
@c EN
An instance of this class can be used as an input port.
The behavior of the port depends on the settings of the
instance slot values.
@c JP
このクラスのインスタンスは入力ポートとして使えます。
このポートの振舞いはインスタンスのスロットに設定された値に依存します。
@c COMMON

@c EN
To work as a meaningful input port, at least either one of
@code{getb} or @code{getc} slot must be set.  Otherwise,
the port returns EOF for all input requests.
@c JP
まともな入力ポートとして動かすためには、少くとも、@code{getb} スロット
あるいは @code{getc} スロットのどちらか一方は設定しなければなりません。
さもなければ、このポートはすべての入力要求に対して EOF を返します。
@c COMMON

@defivar {<virtual-input-port>} getb
@c EN
If set, the value must be a procedure that takes no arguments.
Every time binary input is required, the procedure is called.
@c JP
設定されているのなら、その値は、引数を取らない手続きでなければなりません。
バイナリ入力の要求のたびに、この手続きが呼ばれます。
@c COMMON

@c EN
The procedure must return an exact integer between 0 and 255
inclusive, or @code{#f} or an EOF object.  If it returns an
integer, it becomes the value read from the port.  If it returns
other values, the port returns EOF.
@c JP
この手続きは、0 から 255 までの正確な整数を返すか、@code{#f}あるいは
EOF オブジェクトを返さなければなりません。整数を返す場合には、
それがこのポートから読みとられる値となります。それ以外の値を返す
場合は、このポートは EOF を返します。
@c COMMON

@c EN
If the port is requested a character input and it doesn't have
the @code{getc} procedure, the port calls this procedure, possibly
multiple times, to construct a whole character.
@c JP
このポートが文字入力を要求され、かつ、@code{getc} 手続きを持たない場合、
このポートはこの手続きを呼び(複数回の可能性もある)文字全体を構築します。
@c COMMON
@end defivar

@defivar {<virtual-input-port>} getc
@c EN
If set, the value must be a procedure that takes no arguments.
Every time character input is required, the procedure is called.
@c JP
設定されているのなら、その値は、引数を取らない手続きでなければなりません。
文字入力の要求のたびに、この手続きが呼ばれます。
@c COMMON

@c EN
The procedure must return a character,
@code{#f} or an EOF object.  If it returns a character,
it becomes the value read from the port.  If it returns
other values, the port returns EOF.
@c JP
この手続きは文字を返すか、または@code{#f}あるいはEOFオブジェクトを返さなければ
なりません。文字を返した場合には、それがこのポートから読みとられる値と
なります。それ以外の値を返す場合は、このポートは EOF を返します。
@c COMMON

@c EN
If the port is requested a binary input and it doesn't have
the @code{getb} procedure, the port calls this procedure, then converts
a character into a byte sequence, and use it as the binary
value(s) read from the port.
@c JP
このポートがバイナリ入力を要求され、かつ、@code{getb} 手続きを持たない場合、
このポートはこの手続きを呼び、文字をバイト列に変換し、それをこのポートから
読みだされる値として使います。
@c COMMON
@end defivar

@defivar {<virtual-input-port>} gets
@c EN
If set, the value must be a procedure that takes one argument,
a positive exact integer.  It is called when the block binary
input, such as @code{read-uvector}, is requested.
@c JP
設定されているなら、その値は、正の正確な整数の引数をひとつだけとる手続き
でなければなりません。ブロックバイナリ入力、たとえば、
@code{read-uvector}などが要求された場合に、呼出されます。

@c EN
It must return a (maybe incomplete) string up to the specified size,
or @code{#f} or EOF object.  If it returns a null string, @code{#f}
or EOF object,
the port thinks it reached EOF.  If it returns other string,
it is used as the result of block read.
It shouldn't return a string larger than the given size
(Note: you must count size (bytes), not the number of characters).
@c JP
そしてそれは文字列、 不完全文字列、 @code{#f}、 EOF オブジェクトを
返さなくてはなりません. 文字列を返す場合は上記正の正確な整数によって
指定された大きさを越えてはなりません。空文字列、 @code{#f}、EOF を
返した場合はポートの終端にたどり着いたものとみなされます。
(注意: 文字列大きさは文字数でなく文字列が占めるバイト数で指定されます。)

@c EN
The reason of this procedure is efficiency; if this procedure
is not provided, the port calls @code{getb} procedure repeatedly
to prepare the block of data.  In some cases, providing block input
can be much more efficient (e.g. suppose you're reading from
a block of memory chunk).
@c JP
この手続きは効率のためにあります。もし、この手続きが用意されて
いなければ、このポートは、データブロックを準備するのに @code{getb}を
繰り返し呼びます。場合によっては、ブロック入力を用意するほうが
はるかに効率的です。(たとえば、メモリチャンクのブロックからの読みだし
を行なうような場合です。)
@c COMMON

@c EN
You can leave this slot unset if you don't need to take such
advantage.
@c JP
こうした利点を必要としないのなら、このスロットは未設定のままにして
おいてもかまいません。
@c COMMON
@end defivar

@defivar {<virtual-input-port>} ready
@c EN
If set, the value must be a procedure that takes one boolean argument.
It is called when @code{char-ready?} or @code{byte-ready?} is
called on the port.   The value returned from your procedure will
be the result of these procedures.
@c JP
設定されているなら、その値は、真偽値をひとつだけとる手続きでなければ
なりません。この手続きは、このポートに対して、@code{char-ready?}
あるいは @code{byte-ready?} が呼ばれたときに呼出されます。設定した手続き
が返す値が、これらの手続きの結果になります。
@c COMMON

@c EN
The boolean argument is @code{#t} if
@code{char-ready?} is called, or @code{#f} if @code{byte-ready?} is called.
@c JP
@code{char-ready?} が呼ばれたのなら、真偽値引数は @code{#t} です。
@code{byte-ready?} が呼ばれたのなら、真偽値引数は @code{#f} になります。
@c COMMON

@c EN
If unset, @code{char-ready?} and @code{byte-ready?}
always return @code{#t} on the port
@c JP
未設定なら、@code{char-ready?} および @code{byte-ready?} は
このポートに対して常に、@code{#t} を返します。
@c COMMON
@end defivar

@defivar {<virtual-input-port>} close
@c EN
If set, the value must be a procedure that takes no arguments.
It is called when the port is closed.  Return value is discarded.
You can leave this unset
if you don't need to take an action when the port is closed.
@c JP
設定されているのなら、その値は引数を取らない手続きでなければなりません。
その手続きはこのポートがクローズされるときに呼びだされ、返り値は
捨てられます。このポートをクローズするときになんらかのアクションが
必要でないのなら、未設定にしておけます。
@c COMMON

@c EN
This procedure may be called from a finalizer, so you have to be
careful to write it.   See the note on finalization below.
@c JP
この手続きはファイナライザから呼ばれることもあり得ます。したがって、
この手続きは慎重に書く必要があります。後述のファイナライズに
関する注意を参照してください。
@c COMMON
@end defivar

@defivar {<virtual-input-port>} seek
@c EN
If set, the value must be a procedure that takes two arguments,
offset and whence.  The meaning of them is the same as the arguments
to @code{port-seek} (@pxref{Common port operations}).
The procedure must adjust the port's internal read pointer
so that the next read begins from the new pointer.
It should return the updated pointer (the byte offset from the
beginning of the port).
@c JP
設定されているのなら、その値は、オフセット引数とそれがどこからかを示す引数
の 2つの引数をとる手続きでなければなりません。これらの引数の意味は、
@code{port-seek} (@ref{Common port operations} 参照) のそれと同じです。
この手続きは、次の読み出しが新しい位置から始められるように
内部のリードポインタを調整しなければなりません。そして
更新されたポインタ(ポート先頭からのバイトオフセット)
を返さなければなりません。
@c COMMON

@c EN
If unset, call of @code{port-seek} and @code{port-tell} on this
port will return @code{#f}.
@c JP
未設定なら、このポートに対する @code{port-seek} および @code{port-tell}
の呼び出しは @code{#f} になります。
@c COMMON

@c EN
Note that this procedure may be called for the purpose of merely
querying the current position, with 0 as @code{offset} and @code{SEEK_CUR}
as @code{whence}.  If your port knows the read pointer but cannot move it,
you can still provide this procedure, which returns the current pointer
position for such queries and returns @code{#f} for other arguments.
@c JP
この手続きは単に現在の位置を問合せるために、
@code{offset} として 0 を、@code{whence} として @code{SEEK_CUR} を与えて
呼び出すこともあることに注意してください。リードポインタの位置は知って
いるが、動かすことができないという場合にも、この手続きを提供することが
できます。上のような問合せには、現在位置を返し、そうでない場合には、
@code{#f} を返します。
@c COMMON
@end defivar

@end deftp


@deftp {Class} <virtual-output-port>
@clindex virtual-output-port
@c MOD gauche.vport
@c EN
An instance of this class can be used as an output port.
The behavior of the port depends on the settings of the
instance slot values.
@c JP
このクラスのインスタンスは出力ポートとして使えます。
このポートの振舞いはインスタンスのスロットに設定された値に依存します。
@c COMMON

@c EN
To work as an output port, at least either one of @code{putb} or
@code{putc} slot has to be set.
@c JP
まともな出力ポートとして動かすためには、少くとも、@code{putb} スロット
あるいは @code{putc} スロットのどちらか一方は設定しなければなりません。
@c COMMON

@defivar {<virtual-output-port>} putb
@c EN
If set, the value must be a procedure that takes one argument,
a byte value (exact integer between 0 and 255, inclusive).
Every time binary output is required, the procedure is called.
The return value of the procedure is ignored.
@c JP
設定されているなら、その値は、バイト値(0 から 255までの正確な整数)を
ひとつだけ引数としてとる手続きでなければなりません。バイナリ出力
の要求のたびに、この手続きが呼ばれます。この手続きの返り値は無視
されます。
@c COMMON

@c EN
If this slot is not set and binary output is requested,
the port may signal an @code{<io-unit-error>} error.
@c JP
このスロットが未設定の場合、バイナリ出力を要求されると、このポートは
@code{<io-unit-error>} エラーを発生させることがあります。
@c COMMON
@end defivar

@defivar {<virtual-output-port>} putc
@c EN
If set, the value must be a procedure that takes one argument,
a character.
Every time character output is required, the procedure is called.
The return value of the procedure is ignored.
@c JP
設定されているなら、それは文字をひとつ引数にとる手続きでなければなりません。
文字出力の要求があるたびにこの手続きがよばれます。この手続きの返り値は
無視されます。
@c COMMON

@c EN
If this slot is not set but @code{putb} slot is set,
the virtual port decomposes the character into a sequence of bytes
then calls @code{putb} procedures.
@c JP
このスロットが未設定であっても、@code{putb} スロットが設定されていれば、
この仮想ポートは文字をバイト列に展開してから、@code{putb} を呼びだします。
@c COMMON
@end defivar

@defivar {<virtual-output-port>} puts
@c EN
If set, the value must be a procedure that takes a
(possibly incomplete) string.
The return value of the procedure is ignored.
@c JP
設定されていれば、その値は、文字列(不完全なものである可能性もある)を
ひとつ引数としてとる手続きでなければなりません。この手続きの返り値は
無視されます。
@c COMMON

@c EN
This is for efficiency.  If this slot is not set, the virtual port
calls @code{putb} or @code{putc} repeatedly to output a chunk of data.
But if your code can perform chunked output efficiently,
you can provide this procedure.
@c JP
これは、効率のためにあります。このスロットが未設定であれば、この
仮想ポートは、データのかたまりを出力するために、@code{putb}
あるいは @code{putc} を繰り返し呼びます。もし、ひとかたまりの
出力を効率的に実行可能なコードであれば、この手続きを提供できます。
@c COMMON
@end defivar

@defivar {<virtual-output-port>} flush
@c EN
If set, the value must be a procedure that takes no arguments.
It is called when flushing a port is required (e.g. @code{flush}
is called on the port, or the port is being closed).
@c JP
設定されていれば、その値は引数をとらない手続きでなければなりません。
ポートのフラッシュを要求されたときに呼ばれます(たとえば、@code{flush}
がこのポートに対して呼ばれたとき、あるいは、このポートがクローズ
されるとき)。
@c COMMON

@c EN
This procedure is useful that your port does some sort of buffering,
or needs to keep some state.  If your port doesn't do stateful operation,
you can leave this unset.
@c JP
この手続きは、ポートが何らかのバッファリングをおこなうか、なんらかの
状態を持つような場合に便利です。ポートが状態をともなう操作を行わない
のなら、これは未設定にしておけます。
@c COMMON

@c EN
This procedure may be called from a finalizer, and needs a special
care.  See notes on finalizers below.
@c JP
この手続きはファイナライザから呼ばれることがあります。したがって、
特別な注意が必要です。後述のファイナライザに関する注意を
参照してください。
@c COMMON

@end defivar

@defivar {<virtual-output-port>} close
@c EN
The same as @code{<virtual-input-port>}'s @code{close} slot.
@c JP
@code{<virtual-input-port>} の @code{close} スロットと同様です。
@c COMMON
@end defivar

@defivar {<virtual-output-port>} seek
@c EN
The same as @code{<virtual-input-port>}'s @code{seek} slot.
@c JP
@code{<virtual-input-port>} の @code{seek} スロットと同様です。
@c COMMON
@end defivar

@end deftp

@c EN
@subsubheading Virtual buffered ports
@c JP
@subsubheading 仮想バッファポート
@c COMMON

@c EN
This type of virtual ports are realized by classes
@code{<buffered-input-port>} and @code{<buffered-output-port>}.
You can customize the port behavior by setting
appropriate slots with procedures.
@c JP
このタイプの仮想ポートは @code{<buffered-input-port>} クラス
および @code{<buffered-output-port>} クラスで実現されています。
適切なスロットに手続きを設定するこでポートの振舞いをカスタマイズ
することができます。
@c COMMON

@c EN
Those ports have internal buffer and only calls Scheme procedures
when the buffer needs to be filled or flushed.  Generally it is
far more efficient than calling Scheme procedures for every
I/O operation.   Actually, the internal buffering mechanism is
the same as Gauche's file I/O ports.
@c JP
これらのポートは、内部バッファを持っており、そのバッファを満たすか
フラッシュするかの必要があるときにのみ、Scheme の手続きが呼ばれます。
通常、I/O毎に Scheme の手続きを呼ぶよりも遥かに効率がいいものです。
実際の内部バッファリング機構は、GaucheのファイルI/Oポートと同じです。
@c COMMON

@c EN
These ports uses @code{u8vector} as a buffer.  See @ref{Uniform vectors}
for the details.
@c JP
これらのポートはバッファとして @code{u8vector} を使います。詳細は、
@ref{Uniform vectors} を参照してください。
@c COMMON

@deftp {Class} <buffered-input-port>
@clindex buffered-input-port
@c MOD gauche.vport
@c EN
An instance of this class behaves as an input port.
It has the following instance slots.  For a meaningful input
port, you have to set at least @code{fill} slot.
@c JP
このクラスのインスタンスは、入力ポートとして振舞います。
これは以下のようなインスタンススロットを持ちます。
意味のある入力ポートとして使うには少くとも、@code{fill} スロットを
設定しなければなりません。
@c COMMON

@defivar {<buffered-input-port>} fill
@c EN
If set, it must be a procedure that takes one argument,
a @code{u8vector}.  It must fill the data from the
beginning of the vector.  It doesn't need to fill the entire
vector if there's not so many data.  However, if there are remaining
data, it must fill at least one byte; if the data isn't readily
available, it has to wait until some data becomes available.
@c JP
設定されているなら、@code{u8vector} の引数を一つとる手続きでなければ
なりません。そのベクタの最初からデータを満たさなければなりません。
要求されたものよりデータの残りが少ない場合には、
ベクタ全体を満たす必要はありません。しかしながら、
データが残っている場合には少くとも1バイトは満たさなければなりません。
もしデータがまだ利用可能になっていなければ、なにがしかのデータが利用可能に
なるまで待たなければなりません。
@c COMMON

@c EN
The procedure must return a number of bytes it actually filled.
It may return 0 or an EOF object to indicate the port has reached EOF.
@c JP
この手続きは実際に満されたバイト数を返さなければなりません。ポートが
EOFに達したことを示すために、0 または EOFオブジェクトを返すこともできます。
@c COMMON
@end defivar

@defivar {<buffered-input-port>} ready
@c EN
If set, it must be a procedure that takes no arguments.
The procedure must return a true value if there are some data
readily available to read, or @code{#f} otherwise.
Unlike fully virtual ports, you don't need to distinguish
binary and character I/O.
@c JP
設定されているなら、引数をとらない手続きでなければなりません。
この手続きは、なにがしかの読み込み用データが利用可能になっていれば
真の値を返し、そうでなければ、@code{#f}を返します。完全仮想ポートとはちがい、
バイナリI/Oと文字I/Oを区別する必要はありません。
@c COMMON

@c EN
If this slot is not set, the port is regarded as it always has data ready.
@c JP
このスロットが未定義の場合、このポートは常にデータが利用可能になっている
とみなされます。
@c COMMON
@end defivar

@defivar {<buffered-input-port>} close
@c EN
If set, it must be a procedure that takes no arguments.
The procedure is called when the virtual buffered port is closed.
You don't need to set this slot unless you need some cleaning up
when the port is closed.
@c JP
設定されていれば、引数をとらない手続きでなければなりません。この手続きは
仮想バッファポートがクローズされるときに呼出されます。ポートがクローズ
されるときに、なにがしかのクリーンアップを行うのでなければ、設定する必要
はありません。
@c COMMON

@c EN
This procedure may be called from a finalizer, and
needs special care.  See the note on finalization below.
@c JP
この手続きは、ファイナライザから呼ばれる可能性がありますので、特別な
注意が必要です。後述のファイナライズに関する注意書きを参照してください。
@c COMMON
@end defivar

@defivar {<buffered-input-port>} filenum
@c EN
If set, it must be a procedure that returns underlying
file descriptor number (exact nonnegative integer).
The procedure is called when @code{port-file-number} is called
on the port.
@c JP
設定されているなら、このポートの使っているファイルディスクリプタ番号(正確な非負整数)
を返す手続きでなければなりません。この手続きは @code{port-file-number}
をこのポートに対して呼出したときに呼ばれます。
@c COMMON

@c EN
If there's no such underlying file descriptor, you can
return @code{#f}, or you can leave this slot unset.
@c JP
そのようなファイルディスクリプタが存在していなければ、
@code{#f} を返すことができます。
あるいは、このスロットを未設定にしておくこともできます。
@c COMMON
@end defivar

@defivar {<buffered-input-port>} seek
@c EN
If set, it must be a procedure that takes two arguments,
@var{offset} and @var{whence}.
It works the same way as @code{<virtual-input-port>}'s seek procedure;
see above.
@c JP
設定されているなら、オフセット引数とどこからかを示す引数の2つをとる
手続きでなければなりません。これは、前述の
@code{<virtual-input-port>}のseek 手続きと同じように動作します。
@c COMMON

@c EN
This procedure may be called from a finalizer, and
needs special care.  See the note on finalization below.
@c JP
この手続きはファイナライザから呼ばれる可能性があり、特別な注意が
必要です。後述のファイナライズに関する注意を参照してください。
@c COMMON
@end defivar

@c EN
Besides those slot values, you can pass an exact nonnegative integer
as the @code{:buffer-size} keyword argument to the @var{make} method
to set the size of the port's internal buffer.  If @code{:buffer-size}
is omitted, or zero is passed, the system's default buffer size
(something like 8K) is used.  @code{:buffer-size} is not an instance
slot and you cannot set it after the instance of the buffered port
is created.   The following example specifies the buffered port
to use a buffer of size 64K:
@c JP
これらのスロットの値以外に、当該ポートの内部バッファのサイズを設定する
のには@var{make}メソッドに@code{:buffer-size}というキーワード引数で非
負の正確な整数を渡します。@code{:buffer-size}が省略されるか、0 が渡さ
れた場合にはシステムのデフォルトのバッファサイズ(たとえば、8kとか)が使
われます。@code{:buffer-size}はインスタンススロットではないので、バッ
ファポートのインスタンスを生成したあとで設定することはできません。以下
は 64K のバッファを使うバッファの作り方の例です。
@c COMMON

@example
(make <buffered-input-port> :buffer-size 65536 :fill my-filler)
@end example
@end deftp

@deftp {Class} <buffered-output-port>
@clindex buffered-output-port
@c MOD gauche.vport
@c EN
An instance of this class behaves as an output port.
It has the following instance slots.
You have to set at least @code{flush} slot.
@c JP
このクラスのインスタンスは出力ポートとして振舞います。これは、以下のような
インスタンススロットを持ちます。少くとも @code{flush} は設定しなければ
なりません。
@c COMMON

@defivar {<buffered-output-port>} flush
@c EN
If set, it must be a procedure that takes two arguments,
an @code{u8vector} buffer and a flag.
The procedure must output data in the buffer to somewhere,
and returns the number of bytes actually output.
@c JP
設定されているなら、@code{u8vector}のバッファとフラグという2つの
引数をとる手続きでなければなりません。手続きはバッファ内のデータを
どこかへ出力しなければならず、実際に出力したバイト数を返します。
@c COMMON

@c EN
If the flag is false, the procedure may output less
than entire buffer (but at least one byte).  If the flag
is true, the procedure must output entire buffer.
@c JP
フラグが偽なら、この手続きはバッファ全体よりも少い(ただし、最低でも
1バイト)の出力を行ってもかまいません。もしフラグが真ならば、この手続きは、
バッファの内容をすべて出力しなければなりません。
@c COMMON
@end defivar

@defivar {<buffered-output-port>} close
@c EN
Same as @code{<buffered-input-port>}'s @code{close} slot.
@c JP
@code{<buffered-input-port>} の @code{close} スロットと同様です。
@c COMMON
@end defivar

@defivar {<buffered-output-port>} filenum
@c EN
Same as @code{<buffered-input-port>}'s @code{filenum} slot.
@c JP
@code{<buffered-input-port>} の @code{filenum} スロットと同様です。
@c COMMON
@end defivar

@defivar {<buffered-output-port>} seek
@c EN
Same as @code{<buffered-input-port>}'s @code{seek} slot.
@c JP
@code{<buffered-input-port>} の @code{seek} スロットと同様です。
@c COMMON
@end defivar

@c EN
Besides those slot values, you can pass an exact nonnegative integer
as the @code{:buffer-size} keyword argument to the @var{make} method
to set the size of the port's internal buffer.  See the description
of @code{<buffered-input-port>} above for the details.
@c JP
これらのスロットの値以外に、当該ポートの内部バッファのサイズを設定する
のには@var{make}メソッドに@code{:buffer-size}というキーワード引数で非
負の正確な整数を渡します。詳しくは前述 @code{<buffered-input-port>}
の項を見てください。
@c COMMON

@end deftp

@c EN
@subsubheading Uniform vector ports
@c JP
@subsubheading ユニフォームベクタポート
@c COMMON

@c EN
The following two procedures return a buffered input/output port
backed up by a uniform vector.    The source or destination vector
can be any type of uniform vector, but they will be aliased
to @code{u8vector} (see @code{uvector-alias} in
@ref{Uvector conversion operations}).
@c JP
以下の 2つの手続きは、ユニフォームベクタでバックアップされた、
バッファ入/出力ポートを返します。読み込み元のベクタあるいは
書き出し相手のベクタはどのようなユニフォームベクタであってもかまいませんが、
実際の入出力時には@code{u8vector} にaliasされます
(@ref{Uvector conversion operations} の @code{uvector-alias} 参照)。
@c COMMON

@c EN
If used together with @code{pack}/@code{unpack}
(see @ref{Packing binary data}), it is useful to parse
or construct binary data structure.  It is also an
example of using virtual ports; read @file{gauche/vport.scm}
(or @file{ext/vport/vport.scm} in the source tree) if you're
curious about the implementation.
@c JP
@code{pack}/@code{unpack}(@ref{Packing binary data}参照) と一緒に使うと
バイナリのデータ構造をパースしたり、構築したりするのに便利です。
また、仮想ポートの使い方の例でもあります。実装法に興味があれば、
ソースツリーの @file{gauche/vport.scm}(あるいは @file{ext/vport/vport.scm})
を読んでください。
@c COMMON

@defun open-input-uvector uvector
@c MOD gauche.vport
@c EN
Returns an input port that reads the content of the given
uniform vector @var{uvector} from its beginning.  If reading
operation reaches the end of @var{uvector}, EOF is returned.
Seek operation is also implemented.
@c JP
与えられたユニフォームベクタ @var{uvector}の最初からその内容を読む
入力ポートを返します。読み込み動作が、@var{uvector}の終端に到達したら
EOFが返されます。シーク操作も実装されています。
@c COMMON
@end defun

@defun open-input-bytevector u8vector
[R7RS base]
@c MOD gauche.vport
@c EN
Similar to @code{open-input-uvector},
but the argument must be an u8vector.
This is an R7RS base procedure.
@c JP
@code{open-input-uvector}と似ていますが、引数はu8vectorでなければなりません。
R7RS baseの手続きです。
@c COMMON
@end defun

@defun open-output-uvector :optional uvector :key extendable
@c MOD gauche.vport
@c EN
Returns an output port that uses the given uvector as the
storage for the data output to the port.

If @var{uvector} is completely filled, what happens after that
depends on @var{extendable} - if it is false (default), the rest
of data is discarded silently.  If it is true, the storage is
extended automatically to accommodate more data.

If you give true value to @var{extendable}, you have to retrieve
the result by @code{get-output-uvector} below, since the uvector
you passed in won't contain spilled data.

As a special case, you can omit @var{uvector} argument; then
@code{u8vector} is used as the storage.  In that case
you can't specify @var{extendable} keyword argument, but it is
assumed true, since it won't make sense otherwise.  Use
@code{get-output-uvector} to retrieve the stored result.

Seek operation is also implemented.  Note that the meaning
of @code{SEEK_END} whence differ between extendable and
fixed-size uvector ports.  For extendable ports,
the end whence placed next to the biggest offset of
the data ever written; if you open a port and just write
one byte, the end whence is the second byte, no matter
how big the existing buffer is.  On the other hand,
for fixed-size uvector ports, end whence is fixed to
the next to the end of the given buffer, no matter
how much data you've written to it.  In the latter case,
you can't seek on or past the end (you need to pass negative
number along @code{SEEK_END} to @code{port-seek}).
@c JP
与えられた uvector をデータの格納に使うような出力ポートを返します。

@var{uvector}が全て埋まった後、何が起きるかは、@var{extendable}引数によって
変わります。もし偽の値(デフォルト)では、更に送られてきたデータは黙って捨てられます。
@var{extendable}が真の値であった場合、追加のデータを保持するため
格納領域は自動的に拡張されます。

@var{extendable}に真の値を与えた場合、貯められたデータを取り出すには、
下で説明する@code{get-output-uvector}を使ってください。渡した@var{uvector}
引数には溢れたデータは格納されないので。

特別な場合として、@var{uvector}引数を省略することができます。
この場合、データストレージとして@code{u8vector}が使われます。
@var{uvector}引数を省略した場合、@var{extendable}引数を
与えることはできませんが、これは真の値を与えたものとみなされます。
でないと意味がないからです。@code{get-output-uvector}で
貯められたデータを取り出すことができます。

ポートに対してシーク操作も使うことができます。
ただし、whenceに@code{SEEK_END}を与えた場合の解釈が、@var{extendable}かどうかで
変わることに注意してください。@var{extendable}なポートでは、
末尾は「それまでに書き込まれたデータのうちもっとも大きなオフセット」の次に
設定されます。uvectorポートを開いてすぐに1バイト書き込んだ状態では、
@var{uvector}引数にどんなに大きなベクタを渡していたとしても、@code{SEEK_END}
の基準点は2バイト目です。一方、@var{extendable}でないポートでは、
末尾はそれまでに書き込んだデータによらず、常に与えた@var{uvector}の
末尾の次になります。その場合は、末尾やそれ以降にシークすることはできません
(@code{port-seek}に@code{SEEK_END}を渡す時、オフセットは必ず負数でなければ
なりません)。
@c COMMON
@end defun

@defun open-output-bytevector
[R7RS base]
@c MOD gauche.vport
@c EN
Same as @code{open-output-uvector} without arguments.
Uses extenable u8vector as the buffer.
This is an R7RS base procedure.
@c JP
@code{open-output-uvector}を引数なしで呼ぶのと同じです。
必要に応じて伸長するu8vectorをバッファに使います。
R7RS baseの手続きです。
@c COMMON
@end defun

@defun get-output-uvector port :key shared
@c MOD gauche.vport
@c EN
If @var{port} is a port created by @code{open-output-uvector}, returns
a @var{uvector} that contains accumulated data.
If @var{port} is not a port created by @code{open-output-uvector},
@code{#f} is returned.

The returned uvector is the same type as the one passed to
@code{open-output-uvector}, containing up to actually written data; it may
be smaller than the @var{uvector} passed to @code{open-output-uvector};
it can be larger if the port is extendable.

If the type of uvector is other than @code{s8vector} and @code{u8vector},
and the written data doesn't fill up the whole element won't be
in the result.
For example, if you use @code{s32vector} to create the port,
then write 7 bytes to it, @code{get-output-uvector} returns a
single element @code{s32vector}, for the last 3 bytes does not
consist a whole 32bit integer.

By default, the returned vector is a fresh copy of the contents.
Passing true value to @var{shared} may avoid copying and allow
sharing storage for the one being used by @var{port}.  If you do so,
keep in mind that if you seek back and write to @var{port} subsequently,
the content of returned vector may be changed.
@c JP
@var{port}が@code{open-output-uvector}で作られたポートであるなら、
これまでに蓄えられたデータを@var{uvector}として返します。
@var{port}がそうでない場合は@code{#f}が返されます。

返り値のベクタは、@code{open-output-uvector}に渡したuvector
と同じ型で、実際に書き込まれたデータの最後尾までの範囲になります。
それは@code{open-output-uvector}に渡された@var{uvector}より小さいかも
しれませんし、ポート作成時に@var{extendable}に真の値が渡されていた場合は
元の@var{uvector}よりも大きいかもしれません。

uvectorの型が@code{s8vector}や@code{u8vector}以外である場合、
書き込まれたデータのうち完全な要素に足りない部分は結果に含まれません。
例えば、@code{s32vector}でポートを作り7バイト書き込んでから
@code{get-output-uvector}を呼ぶと、返される@code{s32vector}は
1要素になります。最後の3バイトは完全な32bit整数を構成しないからです。

デフォルトでは、返り値のベクタは新たにアロケートされたものです。
しかし@var{shared}キーワード引数に真の値を渡すと、可能ならば、
@var{port}が使っている格納領域をそのまま参照するベクタが返されます。
このオプションによってコピーを減らすことができますが、
後で@var{port}をシークして前に戻って再書き込みすると、
返されたベクタの内容が書き換わってしまう可能性があることに注意してください。
@c COMMON
@end defun

@defun get-output-bytevector port
[R7RS base]
@c MOD gauche.vport
@c EN
Extract the data put to an bytevector output port as an u8vector.
The port must be created by @code{open-output-bytevector} or
@code{open-output-uvector}.
This is an R7RS base procedure.
@c JP
バイトベクタ出力ポートに出力されたデータをu8vectorとして取り出して返します。
@var{port}は@code{open-output-bytevector}か
@code{open-output-uvector}で作られたものでなければなりません。
R7RS baseの手続きです。
@c COMMON
@end defun


@c EN
@subsubheading List ports
@c JP
@subsubheading リストポート
@c COMMON

@c EN
The following procedures allow you to use list of characters
or octets as a source of an input port.  These are (a kind of)
opposite of @code{port->list} family
(@pxref{Input utility functions}) or @code{port->char-lseq} family
(@pxref{Lazy sequences}).
@c JP
以下の手続きは、文字またはオクテットのリストを入力ポートのソースとして利用するものです。
ある意味、@code{port->list}系の手続き(@ref{Input utility functions}参照)や
@code{port->char-lseq}系の手続き(@ref{Lazy sequences}参照)の逆であると
言えます。
@c COMMON

@defun open-input-char-list char-list
@defunx open-input-byte-list byte-list
@c MOD gauche.vport
@c EN
Creates and returns an input port that uses
the given list of characters and bytes as the source.
@c JP
与えられた文字もしくはオクテットのリストをデータ源とする
入力ポートを作って返します。
@c COMMON

@example
(read (open-input-char-list '(#\a #\b)))
 @result{} ab
@end example
@end defun

@defun get-remaining-input-list port
@c MOD gauche.vport
@c EN
If @var{port} is the one created by @code{open-input-char-list}
or @code{open-input-byte-list}, returns a list of remaining data
that hasn't been read yet.  If the port already read everything,
or the port is not the one created by @code{open-input-char-list}
or @code{open-input-byte-list}, an empty list is returned.

A caveat: Gauche allows mixing binary input and textual input from
the same port.  If you read or even peek a byte from a port
created from a character list, the port buffers a character
and disassembles it to bytes; the disassembled character
may not be included in the remaining input list.
@c JP
@var{port}が@code{open-input-char-list}か@code{open-input-byte-list}で
作られたものであった場合、ポート中のまだ読まれていない部分のリストを返します。
既に全てのデータが読まれていたり、ポートが
@code{open-input-char-list}か@code{open-input-byte-list}で作られたもので
なかった場合は、空リストが返されます。

注意: Gaucheは一つのポートからのバイナリ読み出しと文字読み出しを混ぜて使うことを
許しています。文字のリストで作られたリストポートからバイトを読み出したり、
あるいは@code{peek-byte}した場合、ひとつ文字がデータ源から取り出され、
バイト列に分解されてポート内部の一時バッファに置かれます。
その状態でこの手続きを呼び出した場合、バッファ内のバイト列は戻り値には含まれません。
@c COMMON
@end defun

@c EN
@subsubheading Generator ports
@c JP
@subsubheading ジェネレータポート
@c COMMON

@c EN
The following procedures allow you to use character generators
or byte generators as a source of an input port.  These are (a kind of)
opposite of @code{port->char-generator} family
(@pxref{Generator constructors}).
@c JP
以下の手続きは、文字あるいはオクテットのジェネレータ
入力ポートのソースとして利用するものです。
ある意味、@code{port->char-generator}系の手続き
(@ref{Generator constructors}参照)の逆であると言えます。
@c COMMON

@defun open-input-char-generator cgen
@defunx open-input-byte-generator bgen
@c MOD gauche.vport
@c EN
Creates and returns an input port that uses
the given generators as the source.  The @var{cgen} argument
must be a generator that yields characters.  The @var{bgen} argument
must be a generator that yields bytes (exact integers between 0 and
255, inclusive).
An error will be raised if the given generator yields
incorrect type of objects.
@c JP
与えられたジェネレータをデータ源とする入力ポートを作って
返します。@var{cgen}は文字を生成するジェネレータ、
@var{bgen}はバイト(オクテット、0から255の間の正確な整数)を
生成するジェネレータでなけばなりません。
ジェネレータが想定される値以外のものを返した場合はエラーが通知されます。
@c COMMON

@example
(read (open-input-char-generator (string->generator "foo")))
 @result{} foo
@end example

@c EN
Since the generators are objects relying on side effects,
you shouldn't use @var{cgen} or @var{bgen} after you pass them
to those procedures; if you use them afterwards, the result
is undefined.
@c JP
ジェネレータは本質的に副作用に依存しているオブジェクトなので、
この手続きに@var{cgen}や@var{bgen}を渡したら、その後で
それらのジェネレータに触ってはなりません。
もしそれらのジェネレータを使ってしまった場合、以降の動作は未定義となります。
@c COMMON
@end defun

@defun get-remaining-input-generator port
@c MOD gauche.vport
@c EN
If @var{port} is the one created by @code{open-input-char-generator}
or @code{open-input-byte-generator}, returns a generator that
yields the characters or bytes that haven't been read yet.
If the port already read everything, an empty generator
is returned.

Once you take the remaining input generator, you should no longer
read from the input generator ports; they share internal states and
mixing them will likely to cause unexpected behaviors.
If side-effects safe behavior is desired, use lazy sequence and
input list ports.
@c JP
@var{port}が@code{open-input-char-generator}か
@code{open-input-byte-generator}で作られたものであった場合、
残りのデータを生成するジェネレータを返します。
ポートが既にデータを全て消費していた場合は、空のジェネレータが返されます。

残りのデータを生成するジェネレータを取り出したら、
ジェネレータポートからはも読み出してはなりません。
内部状態を共有しているため、予期せぬ結果がもたらされることになるでしょう。
副作用に頼らず安全な振る舞いが必要な場合は、遅延シーケンスと
リストポートを使うのが良いでしょう。
@c COMMON
@end defun

@c EN
@subsubheading Accumulator ports
@c JP
@subsubheading アキュムレータポート
@c COMMON

@c EN
Accumulators are dual to generators; it's a procedure that accepts a value
at a time, and the end of the value is indicated by EOF.
@xref{R7RS generators}, for the basic operations of accumulators.

The following procedures turns an accumulator that accepts characters
or octets into an output port.
@c JP
アキュムレータはジェネレータの双対です。値を一回にひとつづつ受け取る手続きで、
値の末端はEOFで示されます。
アキュムレータの操作については@ref{R7RS generators}を参照してください。

以下の手続きは、文字またはバイトを受け取るアキュムレータを出力ポートに変換します。
@c COMMON

@defun open-output-char-accumulator acc
@c MOD gauche.vport
@c EN
Returns an output port that sends the output characters to an
accumulator @code{acc}, which takes a character as the argument.
When the returned output port is closed, EOF is passed to @var{acc}.

Note: The behavior is undefined if you try to perform binary output
to the returned output port.
@c JP
@var{acc}は文字を受け取るアキュムレータです。
出力される文字を@var{acc}に送る出力ポートを返します。
出力ポートがクローズされると、@var{acc}にEOFが渡されます。

註: 返される出力ポートにバイナリ出力を行った場合の動作は未定義です。
@c COMMON
@end defun

@defun open-output-char-accumulator acc
@c MOD gauche.vport
@c EN
Returns an output port that sends the output bytes to an
accumulator @code{acc}, which takes a byte as the argument.
When the returned output port is closed, EOF is passed to @var{acc}.

A character sent to the output port is converted to octets in
the Gauche's native encoding.
@c JP
@var{acc}はバイト(オクテット)を受け取るアキュムレータです。
出力されるバイトを@var{acc}に送る出力ポートを返します。
出力ポートがクローズされると、@var{acc}にEOFが渡されます。

文字が出力された場合は、Gaucheの内部エンコーディングにしたがってオクテット列に
変換されて@var{acc}に送られます。
@c COMMON
@end defun

@defun open-output-accumulator acc
@c MOD gauche.vport
@c EN
The accumulator @var{acc} must accept a byte, a character or a string.
Returns an output port that sends the output data to the @var{acc}.
When the returned output port is closed, EOF is passed to @var{acc}.
@c JP
@var{acc}はバイト(オクテット)、文字、文字列を受け取るアキュムレータです。
出力データを@var{acc}に送る出力ポートを返します。
出力ポートがクローズされると、@var{acc}にEOFが渡されます。
@c COMMON
@end defun

@c EN
@subsubheading Note on finalization
@c JP
@subsubheading ファイナライズに関する注意
@c COMMON

@c EN
If an unclosed virtual port is garbage collected, its close procedure
is called (in case of virtual buffered ports, its flush procedure
may also be called before close procedure).  It is done by
a finalizer of the port.  Since it is a part of garbage-collection
process (although the Scheme procedure itself is called outside of
the garbage collector main part), it requires special care.
@c JP
クローズされていない仮想ポートがガベージ・コレクションされると、
クローズ手続きが呼ばれます(仮想バッファポートの場合は、
フラッシュ手続きがクローズ手続きの前に呼ばれます)。これは、
そのポートのファイナライザによって行われます。これはガベージ・コレクション
処理の一部ですから(Scheme 手続きそのものはガーベッジ・コレクタの
メインパートの外側で呼ばれているのですが、それでも)特別な注意が必要です。
@c COMMON

@itemize @bullet
@item
@c EN
It is possible that the object the virtual port has a reference
may already be finalized.  For example, if a virtual port @var{X}
holds the only reference to a @emph{sink} port @var{Y}, to which
the output goes.  @var{X}'s @code{flush} procedure sends its output to
@var{Y}.  However, if @code{flush} procedure can be called from a
finalizer, it may be possible that @var{Y}'s finalizer has already been
called and @var{Y} is closed.   So @var{X}'s @code{flush} procedure
has to check if @var{Y} has not been closed.
@c JP
仮想ポートが参照しているオブジェクトが既にファイナライズされて
しまっているということがあり得ます。たとえば、仮想ポート @var{X}
は、@emph{流し込み用}のポート @var{Y} への唯一の参照を保持しており、それに
出力するものとします。@var{X}の @code{flush} 手続きは、その出力を
@var{Y}へ送ります。もし@code{flush} 手続きがファイナライザから
呼ばれた場合、@var{Y} のファイナライザが既に
呼ばれていて、@var{Y} がクローズしてしまっていることがあるのです。
従って @var{X} の @code{flush} 手続きは、@var{Y} が既にクローズして
いるかどうかをチェックする必要があります。
@c COMMON

@item
@c EN
You cannot know when and in which thread the finalizer runs.
So if the procedure like @code{close} or @code{flush} of virtual ports
need to lock or access the global resource, it needs to take
extra care of avoiding dead lock or conflict of access.
@c JP
いつ、どのスレッドでファイナライザが走るかを知ることはできません。
それゆえ、仮想ポートの @code{close} あるいは @code{flush} などの
手続きが、グローバルなリソースをロックしたり、アクセスしたりする
必要のある場合には、デッドロックやアクセスの衝突を回避するために
特に注意する必要があります。
@c COMMON

@c EN
Even in single thread programs, the finalizer can run anywhere
in Scheme programs, so effectively it should be considered as
running in a different thread.
@c JP
単一スレッドのプログラムにおいても、ファイナライザは、Schemeの
プログラムのいたるところで走る可能性があります。したがって、実質的に
それは別のスレッドで走っていると考えておくべきです。
@c COMMON
@end itemize

@c Local variables:
@c mode: texinfo
@c coding: utf-8
@c end:
