Go to the previous, next section.

演算子 & 関数

指数

`**'
指数演算子。
`**='
指数演算 & 代入演算子。

ヌルリスト

`()'
配列を初期化するために使う、ヌルリスト。

文字列結合

`.'
2 つの文字列の結合演算子。
`.='
結合 & 代入演算子。

比較演算子

`eq'
文字列の同値性( == は数値の同値性)。 (もし、状況に応じて == が 文字列および数値の両方の同値性を表す awk に慣れているなら、注意せよ!)
`ne'
文字列の非同値性( != は数値の非同値性)。

`lt'
文字列の less than 。
`gt'
文字列の greater than 。
`le'
文字列の less than or equal 。
`ge'
文字列の greater than or equal 。
`cmp'
文字列の比較。-1、0、または 1 を返す。
`<=>'
数値の比較。-1、0、または 1 を返す。

操作対象文字列の指定

`=~'
演算には、検索・変更をデフォルトで文字列 $_ に対して行うものがある。 =~ 演算子を用いると、別の文字列に対してその演算が行われる。 右の引数は検索パターン・置換・変換(translation) であり、 左の引数はデフォルトの $_ の代わりに 検索・置換・変換の対象となる文字列である。返り値は演算の成否を返す。 (右引数が検索パターン・置換・変換 ではなくてある expression である場合は、 実行時に検索パターンとして解釈される。 その expression が評価される度にパターンがコンパイルされるので、 これはパターンを明示した検索に比べて非効率的である。)

この演算子は -(単項マイナス演算子)、++-- を除く 他の演算よりも優先度が高い。

`!~'
返り値が否定されることを除いて =~ と同じである。

繰り返し

`x'
繰り返し演算子。左引数を右引数回分繰り返した文字列を返す。 配列のコンテキストでは、左引数が括弧に入ったリストの場合、リストを繰り返す。

print '-' x 80;     # ダッシュの列を出力する
print '-' x80;      # 正しくない、なぜなら x80 は識別子だから

print "\t" x ($tab/8), ' ' x ($tab%8);  # タブに変換

@ones = (1) x 80;      # 80 個 1 が並んだ配列
@ones = (5) x @ones;   # 全要素を 5 にする

`x='
繰り返し & 代入演算子。スカラーに対してのみ働く。

`..'
範囲指定演算子。コンテキストによって異なる二つの演算を表す。

配列のコンテキストでは、 左の値から右の値まで(1 ずつ)増やした値を持つ配列を返す。 これは for (1..10) ループや配列の一部を切り出す操作には便利である。

スカラーのコンテキストでは .. は論理値を返す。 演算子はフリップフロップのように 2 通りの値をとる。 .. はそれぞれが自分だけの論理状態を持っていて、左引数が偽である限り、 偽の値を持つ。いったん左引数が真になると、右引数が真になるまで真である。 その後、範囲指定演算子は再び偽になる。 (次に範囲指定演算子が評価されるまで、偽にはならない。 真になったのと同じ評価を行った時に偽になることがありうるが、 それでも一度は真を返す。)演算子が偽の間は右引数は評価されず、 演算子が真の間は左引数は評価されない。

スカラー .. 演算子はもともと sed や awk にならって 行番号範囲指定をするためのものである。

優先度は ||&& よりも少し低い。返り値は偽ならばヌル文字列、 真ならば(1 から始まる)連続した数字である。 この数字は範囲指定に出会う毎にリセットされる。 範囲の最後の数字には文字列 `E0' がつけられるので、数値に影響はないが、 最後の点を除きたい場合に検索のきっかけとなる。 数字が 1 より大きくなるのを待つことで最初の点を除くことができる。 スカラーの .. の引数のどちらかの値が静的な場合は、 引数は暗黙のうちに変数 $. と比較される。

スカラー演算子としては:

if (101 .. 200) { print; }     # 200 行出力する

next line if (1 .. /^$/); # ヘッダー行をスキップ

s/^/> / if (/^$/ .. eof());    # 本体を引用する

配列演算子としては:

for (101 .. 200) { print; }    # $_ を 100 回出力する

@foo = @foo[$[ .. $#foo]; # 高価なノーオペレーション
@foo = @foo[$#foo-4 .. $#foo]; # 最後の 5 要素を取り出す

ファイルテスト演算子

この演算子はファイル名かファイルハンドルを引数として一つとり、 そのファイルについて何かが真かどうかを見る。 引数を省略すると、$_ をテストする。 例外は -t で、STDIN をテストする。

真の場合は 1、偽の場合は '' か、 ファイルが存在しない場合は undefined value を返す。

優先度は論理演算子、関係演算子よりも高いが、数学演算子よりは低い。

演算子の種類は、以下の通りである。

-r        ファイルを実効 uid で読むことができる。
-w        ファイルに実効 uid で書くことができる。
-x        ファイルを実効 uid で実行することができる。
-o        ファイルの所有者が実効 uid である。

-R        ファイルを実 uid で読むことができる。
-W        ファイルに実 uid で書くことができる。
-X        ファイルを実 uid で実行することができる。
-O        ファイルの所有者が実 uid である。

-e        ファイルが存在する。

-z        ファイルサイズが 0 である。
-s        ファイルサイズが 0 でない(ファイルサイズを返す)。

-f        ファイルはプレーンファイルである。
-d        ファイルはディレクトリである。
-l        ファイルはシンボリックリンクである。
-p        ファイルは名前つきパイプ(FIFO)である。
-S        ファイルはソケットである。
-b        ファイルはブロック特殊ファイルである。
-c        ファイルはキャラクター特殊ファイルである。

-u        ファイルに setuid ビットがセットされている。
-g        ファイルに setgid ビットがセットされている。
-k        ファイルに sticky ビットがセットされている。

-t        ファイルハンドルが tty にオープンされている。

-T        ファイルはテキストファイルである。
-B        ファイルはバイナリファイルである。(-T の逆)
-M        スクリプトの実行を開始した時点でのファイルの古さ(age)(単位は日)
-A        スクリプトの実行を開始した時点でのファイルのアクセス時間
-C        スクリプトの実行を開始した時点でのファイルの inode 変更時間

演算子 -r,-R,-w,-W,-x,-X の判断は、 ファイルのモードとユーザの uid、gid のみによる。 実際に読み/書き/実行できない場合があるかもしれない。

また、スーパーユーザの場合は、 -r,-R,-w,-W は常に 1 を返し、 -x,-X については ファイルモードにいずれかの実行許可がついていれば 1 を返す。

このため、スーパーユーザが実行するスクリプトにおいて 実際のファイルモードを得るためには、stat() を行うか、 一時的に uid を他のものにセットする必要がある。

while (<>) {
     chop;
     next unless -f $_;  # 特殊ファイルは無視する
     ...
}

(注意)

ファイルテストにおいて `_'(下線)だけからなる 特殊なファイルハンドルを指定すると、 前回のファイルテスト(または stat() )での stat 構造体が用いられ、 システムコールを行わない。 (-t は除く。また、lstat()-l は 実際のファイルではなくシンボリックリンクの情報を stat 構造体に残すことを 覚えておく必要がある。)

print "Can do.\n" if -r $a || -w _ || -x _;

stat($filename);
print "Readable\n" if -r _;
print "Writable\n" if -w _;
print "Executable\n" if -x _;
print "Setuid\n" if -u _;
print "Setgid\n" if -g _;
print "Sticky\n" if -k _;
print "Text\n" if -T _;
print "Binary\n" if -B _;

演算子その他

perl になくて C にだけある演算子は以下の通り。

`単項演算子 &'
"〜のアドレス"演算子。
`単項演算子 *'
"アドレスを通しての参照"演算子。
`(型)'
型変換演算子。

perl は C と同じく、演算子に対する引数が全て静的であり、 副作用もないと判断した時は expression の評価をコンパイル時に行う (特に、コンパイル時に変数置換を行わない文字列間の結合を発見した場合)。 バックスラッシュの解釈もコンパイル時に行われる。

'Now is the time for all' . "\n" .
'good men to come to.'

これは一つの文字列になってしまう。

++ 演算子にはちょっとした細工をしている。 数字や、数値のコンテキストで使った変数をインクリメントすると、 通常のインクリメントを行う。 しかし、セットしてから文字列のコンテキストでしか使っておらず、 ヌルでない値を持っていて、 パターン /^[a-zA-Z]*[0-9]*$/ にマッチするような変数の場合、 文字列としてのインクリメントを文字列の範囲はそのまま、 キャリー付きで行う。

print ++($foo = '99');   # prints '100'
print ++($foo = 'a0');   # prints 'a1'
print ++($foo = 'Az');   # prints 'Ba'
print ++($foo = 'zz');   # prints 'aaa'

-- 演算子にはこのような細工はない。

(配列のコンテキストにおける)範囲演算子は、 最小値と最大値が文字列の場合は ++ 演算子の細工を利用している。 アルファベット文字の全てを得るためには次のように記述できる。

@alphabet = ('A' .. 'Z');

また、16 進の値を得るためには、

$hexdigit = (0 .. 9, 'a' .. 'f')[$num & 15];

そして、最初に 0 がついた日付を得るためには、

@z2 = ('01' .. '31');  print @z2[$mday];

と書ける。 (指定した最終値が ++ の細工が処理する順番になっていない場合は、 次の値が指定した最終値より長くなるまで繰り返される。)

||&& は C のそれとは異なり、 0 や 1 を返す代わりに最後に評価した値を返す。このため、 ホームディレクトリを探すための移植性の高い方法は次のようになる。

$home = $ENV{'HOME'} || $ENV{'LOGDIR'} ||
        (getpwuid($<))[7] || die "You're homeless!\n";

前章までに述べた文字や変数と同じく、 次章以降で述べる演算子は expression 中の"語"として機能する。 演算子の中にはリストを引数に取るものがある。 このリストはスカラーの引数や配列値が任意に結合されたものである。 配列値は、 リストのその位置に個々の要素を書いて 1 次元の配列値をたくさん生成したような形で リストに吸収される。

リストの要素はコンマで区切る必要がある。

演算子をリストすると、引数の前後に括弧がある場合ない場合共に、 その演算子を単項演算子または関数呼び出しとして使うことができる。

関数呼び出しとして使う場合は、 同じ行の次のトークンは左括弧でなくてはならない(間にスペースがあってもよい)。 このような関数は期待通りの最も高い優先度を持つ。

左括弧以外のトークンが続く場合は、単項演算子として扱われ、 リストを引数に取る演算子かそうでないかのみにより優先度が決まる。 リストを引数に取る場合は最も低い優先度になる。 他の全ての単項演算子は関係演算子よりは高いが数値演算子よりは低い優先度になる。 優先度の章を参照のこと。See section 優先度.

フロー制御

do

`do BLOCK'

do BLOCK は、BLOCK で指示されるコマンド群の 最後のコマンドの値が返る。ループ修飾子で修飾された場合は、 ループ条件をテストする前に一回実行される。 (他の文ではループ修飾子は条件テストを最初に行う。)

`do SUBROUTINE (LIST)'

do SUBROUTINE は、 sub で宣言された SUBROUTINE を実行し、 SUBROUTINE で評価された最後の expression の値を返す。 その名前のサブルーチンがない場合は、致命的エラーとなる (サブルーチンが存在するかどうか知るには、 defined 演算子を使用すれば良い。)。 LIST の一部として配列を渡す場合、 各配列の前に配列の長さを渡してもいいだろう。 (後で出てくる subroutines の章を参照。See section サブルーチン.) `do EXPR' との混乱を防ぐため、括弧は必要である。

SUBROUTINE は一スカラー変数であってもよい。 この場合実行すべきサブルーチンの名前はその変数から取り出される。

別の書き方として(そして望ましい書き方として)、 名前の前に & をつけてサブルーチンをコールしても良い。 例: &foo(@args)

引数を渡さないのであれば、括弧を使う必要はない。 括弧を省略した場合、サブルーチンには配列 @_ は渡されない。 & 形式は defined および undef に サブルーチンを指示するのにも使える。

if (defined &$var) { &$var($parm); undef &$var; }

`do EXPR'

do EXPR は、EXPR をファイル名として、 そのファイルの内容を perl スクリプトとして実行する。 その主たる使用法は、 perl サブルーチンライブラリからサブルーチンをインクルードすることである。

do 'stat.pl';
は、
eval `cat stat.pl`;

と全く同じである。 (より効率的で、より簡潔で、エラーメッセージでのファイル名は正しく、 カレントディレクトリになければ -I で指定されたライブラリを 全て検索する点が異なる。See section @INC : perl スクリプトを探す場所のリスト for @INC.)

しかし、コールする毎に parse し直すのは同じなので、 ループの中で使用する際には -P オプション および #include を使った方がよい(若干立ち上げ時間が増えるが)。 #include の問題点は、cpp# がコメントであることを わかってくれないことである -- コメントだけからなる行には `;#' を 使うことになる。

注意:
次の 2 文は同等ではない

do $foo;	# ファイルを評価する
do $foo();	# サブルーチンを呼ぶ

ライブラリルーチンをインクルードするには `require' オペレータがよい。 See section require.

goto

`goto LABEL'

LABEL というラベル宣言を検索し、そこから実行を再開する。 現在は do {} 構造の中を除く プログラムの本体内のラベルにしか goto できない。 goto はあまり効率的にはインプリメントされておらず、 sed-to-perl 変換を容易にしているだけである。私がいつ、 sed スクリプトのサポートは残したままこのセマンティクスを変更するかわからない。 使いたければ自らの責任で使うこと。全く使わないのが一番良い。

last

`last LABEL'
`last'

last コマンドは C での break(ループ中で使用される) と似ている。現在実行中のループから直ちに抜け出す。 LABEL を省略すると、最も奥のループを構成する囲みの最後にとぶ。 continue がもしあっても、実行されない。

line: while (<STDIN>) {
     last line if /^$/;  # ヘッダーが終わったら抜ける
     ...
}

next

`next LABEL'
`next'

next コマンドは C における continue に似ていて、 ループの次の繰り返しを行う。

line: while (<STDIN>) {
     next line if /^#/;  # コメントは捨てる
     ...
}

注意:
もし continue ブロックが上例にあれば、 無視される行であっても実行される。LABEL を省略した場合、 next は括弧で囲まれたループの最後にとぶ。

redo

`redo LABEL'
`redo'

redo コマンドは条件を評価することなくループブロックを再び実行する。 continue ブロックがもしあっても、実行されない。 LABEL を省略すると、最も内側の閉じたループを用いる。 このコマンドは通常、 入力された内容について自分自身に嘘をつくようなプログラムで用いる。

# 単純な Pascal コメント除去プログラム
# (注意: 文字列中に {} がないと仮定している)
line: while (<STDIN>) {
     while (s|({.*}.*){.*}|$1 |) {}
     s|{.*}| |;
     if (s|{.*| |) {
        $front = $_;
        while (<STDIN>) {
             if (/}/) {     # コメントの終わり?
               s|^|$front{|;
                redo line;
             }
        }
     }
     print;
}

return

`return LIST'

指定した値でサブルーチンから返る。

注意:
サブルーチンからは、最後に評価した expression の値で自動的に返る。 それがお勧めである -- return を明示すると、若干遅くなる。

数学関数

atan2

`atan2(X,Y)'

Y/X の arctangent を -π から π までの範囲で返す。

cos

`cos(EXPR)'
`cos EXPR'

EXPR はラジアン。省略すると $_ を使う。

sin

`sin(EXPR)'
`sin EXPR'

EXPR (ラジアン) のサインを返す。 EXPR を省略すると、$_ のサインを返す。

exp

`exp(EXPR)'
`exp EXPR'

e の EXPR 乗を返す。 EXPR を省略すると、exp($_) を返す。

sqrt

`sqrt(EXPR)'
`sqrt EXPR'

EXPR のルート(2 乗根)を返す。 EXPR を省略すると、$_ のルートを返す。

int

`int(EXPR)'
`int EXPR'

EXPR を整数に変換した値を返す。 EXPR を省略すると、$_ を使用する。

log

`log(EXPR)'
`log EXPR'

EXPR の(基 e の)log を返す。 EXPR を省略すると、$_ の log を返す。

rand

`rand(EXPR)'
`rand EXPR'
`rand'

0 から EXPR の間のランダムな小数点の数値を返す (EXPR は正でなくてはならない)。 EXPR を省略すると、0 と 1 の間の値を返す。srand() も参照。

srand

`srand(EXPR)'
`srand EXPR'

rand 演算子で用いる乱数の seed をセットする。 EXPR を省略すると、srand(time) を実行する。

time

`time'

1970 年 1 月 1 日 0 時 0 分 0 秒(UTC)からの秒数を返す。

gmtime()localtime() に指定することができる。

See section 変換関数, and See section 変換関数.

変換関数

gmtime

`gmtime(EXPR)'
`gmtime EXPR'

time 関数が返す時間を Greenwich timezone として 要素数 9 の配列に変換する。典型的に以下のように使用される。

($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) =
        gmtime(time);

配列の全要素は数値であり、 struct tm から直接得られたものである。 このため、$mon は 0 から 11 まで、 $wday は 0 から 6 までの値を取る。 EXPR を省略すると、gmtime(time) を実行する。

localtime

`localtime(EXPR)'
`localtime EXPR'

time 関数が返す形式の時間を local timezone として 要素数 9 の配列に変換する。典型的に以下のように用いる。

($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) =
        localtime(time);

配列の要素はすべて数値で、struct tm から直接得られるものである。 このため、$mon は 0 から 11、$wday は 0 から 6 の値を取る。 EXPR を省略すると、localtime(time) を実行する。

See section 数学関数.

hex

`hex(EXPR)'
`hex EXPR'

EXPR を 16 進文字列であると見なして 10 進値を返す (0 または 0x で始まる文字列の変換については oct() を参照。)。 EXPR を省略すると、$_ を使用する。

oct

`oct(EXPR)'
`oct EXPR'

EXPR の値を 8 進文字列であると解釈してその 10 進値を返す。 (EXPR0x で始まる場合は代わりに 16 進文字列であると解釈する。) 次の例では、標準的な記述による 10、8、16 進を扱うことができる。

$val = oct($val) if $val =~ /^0/;

EXPR を省略した場合、 $_ を使用する。

ord

`ord(EXPR)'
`ord EXPR'

EXPR の最初の文字の ascii value を数値で返す。 EXPR を省略すると、$_ を使用する。

vec

`vec(EXPR,OFFSET,BITS)'

文字列を unsigned integer のベクトルとして扱い、指定した bitfield の値を返す。 代入もできる。BITS は 2 の 1 乗から 32 乗まででなければならない。

vec() が返すベクトルは論理演算子 |&^ を用いて 操作できる。両オペランドが文字列の場合はビットベクトル演算であると仮定する。 この解釈はプログラムに少なくとも一つの vec() がないとなされない。 (古いプログラムを守るため)

ビットベクトルを文字列や 0 と 1 の配列に変換するには、 次のようにすればよい。

$bits = unpack("b*", $vector);
@bits = split(//, unpack("b*", $vector));

正確なビット長がわかっているなら、 * の代わりにそれを使うことができる。

データ構造変換関数

pack

`pack(TEMPLATE,LIST)'

配列または値のリストを引数にとり、バイナリ構造体に pack する。 構造体を含む文字列を返す。TEMPLATE はひと続きの文字列で、 各文字は以下のように値のオーダーおよびタイプを表す。

A    アスキー文字列(スペースが pad される)
a    アスキー文字列(ヌルが pad される)
c    signed char
C    unsigned char
s    signed short
S    unsigned short
i    signed integer
I    unsigned integer
l    signed long
L    unsigned long
n    short( "network" オーダー)
N    long( "network" オーダー)
f    単精度浮動小数点(native format)
d    倍精度浮動小数点(     〃      )
p    string へのポインタ
x    null byte
X    back up a byte(?)
@    絶対位置までヌルで埋める
u    uuencode された文字列
b    ビット文字列
     (vec() のような、昇順のビットオーダー(ascending bit order))
B    ビット文字列(降順のビットオーダー(descending bit order))
h    16進文字列(低 nybble が先に来る)
H    16進文字列(高 nybble が先に来る)

オプションとして数字を各文字の後につけて、繰り返し数を指定することができる。 `a'`A'`b'`B'`h'`H' 以外のタイプでは、 指定された数の値を LIST から取る。 リピート値として * を使うと残り全部を示す。 `a'`A' では、値は一つで、指定された長さの一つの文字列として、 必要ならヌルやスペースを pad する。 (unpack の際には、 `A' は後に続くスペースやヌルを取り除くが、 `a' の場合はそうではない。) 同様に、`b'`B' は指定したビット数分の文字列を pack する。 `h'`H' は指定した数の nybbles を pack する。

実数(単精度、倍精度)は native machine format のみである。 浮動小数点のフォーマットにはいろいろあり、 標準の network 表現がないので、交換することはできない。 このため、あるマシンで pack された浮動小数点データは 他のマシンでは読むことができない --- たとえ両方共 IEEE の floating point arithmetic を使っていたとしても (メモリ表現の endian-ness は IEEE のスペックにはないから)。 perl は内部の全数値計算に倍精度を用いているので、 double -> float -> double という変換をすると精度が悪くなる (すなわち、unpack("f", pack("f", $foo)) は 普通 $foo と一致しない)ことに注意。

$foo = pack("cccc",65,66,67,68);
# foo は "ABCD" となる
$foo = pack("c4",65,66,67,68);
# 同じこと

$foo = pack("ccxxcc",65,66,67,68);
# foo は "AB\0\0CD" となる

$foo = pack("s2",1,2);
# リトル・エンディアンでの "\1\0\2\0"
# ビッグ・エンディアンでの "\0\1\0\2"

$foo = pack("a4","abcd","x","y","z");
# "abcd"

$foo = pack("aaaa","abcd","x","y","z");
# "axyz"

$foo = pack("a14","abcdefg");
# "abcdefg\0\0\0\0\0\0\0"

$foo = pack("i9pl", gmtime);
# 実際の構造体 tm (私のシステムでは)

sub bintodec {
    unpack("N", pack("B32", substr("0" x 32 . shift, -32)));
}

unpack 関数でも、同じ template を用いることができる。

unpack

`unpack(TEMPLATE,EXPR)'
unpackpack の逆を行う:
ある構造体を示す文字列から配列値を取り出す。 (スカラーコンテキストでは、生成した最初の値のみを返す。)

TEMPLATEpack関数 と同じフォーマットである。 以下は substring を行うサブルーチンの例である。

sub substr {
     local($what,$where,$howmuch) = @_;
     unpack("x$where a$howmuch", $what);
}

そして、

sub ord { unpack("c",$_[0]); }

さらに、フィールドに %<数字> という添え字をつけると、 アイテムそのものの代わりに、アイテムの<数字>ビットのチェックサムが得られる。 デフォルトは 16 ビットチェックサムである。 例えば、次の例では System V の sum プログラムと同じ値が得られる。

while(<>) {
    $checksum += unpack("%16C*", $_);
}
$checksum %= 65536;

See section pack.

文字列関数

chop

`chop(LIST)'
`chop(VARIABLE)'
`chop VARIABLE'
`chop'

文字列の最後の文字を落としてその文字列を返す。 入力文字列から最後の改行文字を除くのに使ったりする。 文字列を省略した場合、$_ を使う。

while (<>) {
     chop;     # 最後の \n を取る
     @array = split(/:/);
     ...

左辺値であれば引数は何でもいい。

chop($cwd = `pwd`);
chop($answer = <STDIN>);

リストを chop した場合は、全リストを chop し、 最後に chop した文字を返す。

crypt

`crypt(PLAINTEXT,SALT)'

文字列を C ライブラリの crypt() と全く同じように encrypt する。 パスワードファイル中のくだらないパスワードをチェックするのに便利である。 白い帽子を被った奴だけがこれをするべきだ。(?) (Only the guys wearing white hats should do this.)

eval

`eval(EXPR)'
`eval EXPR'
`eval BLOCK'

EXPR を parse し、perl プログラムであるとみなして実行する。

現在の perl プログラムの環境で実行されるので、 変数、サブルーチン、フォーマット定義は後まで残る。 サブルーチンと同じく、評価した最後の expression の値が返る。

syntax error または runtime error があった場合、 または die 文が実行された場合、 eval は undefined value を返し、 $@ にはエラーメッセージがセットされる。

エラーがなければ $@ はヌルであることが保証されている。

EXPR が省略された場合は、$_ を評価する。 expression の最後にセミコロンがもしあれば、expression から除かれる。 See section $@ : 最後に行った eval のシンタックスエラーメッセージ for $@.

eval は致命的エラーをトラップするので、 ある機能(例えば dbmopensymlink)が インプリメントされているかどうかを決定するのに便利である。

また、eval は、perl の例外トラップ機構(exception trapping mechanism) でもある。この例外を起こすためには die 演算子を用いる。

実行するコードが変化しないのであれば、 eval-BLOCK 形式を使うことにより、 毎回コンパイルし直す不利益を被ることなく 実行時のエラーをトラップすることができる。

エラーは、もしあれば、同様に $@ にセットされる。

シングルクォートされた文字列(EXPR)を eval するのも同様の効果があるが、 eval-EXPR はシンタックスエラーを実行時に $@ に返すのに対し、 eval-BLOCK はシンタックスエラーをコンパイル時に返す点が異なる。 eval-EXPR 形式は、 その実行が最初に成功した時点で eval-BLOCK 形式に最適化される。 (文字列置換において e 修飾子を用いた場合、 置換側はシングルクォートされた文字列であると見なされるので、 同様の最適化がこの場合にもなされる。)

例:

# 0 除算を致命的エラーにしない
eval { $answer = $a / $b; }; warn $@ if $@;

# 最初に使った後、同じものに最適化される
eval '$answer = $a / $b'; warn $@ if $@;

# コンパイル時エラー
eval { $answer = };

# 実行時エラー
eval '$answer =';	# $@ をセットする

index

`index(STR,SUBSTR,POSITION)'
`index(STR,SUBSTR)'

STR 内で SUBSTRPOSITION 文字目 またはそれ以降に最初に現れる位置を返す。

POSITION を省略した場合は文字列の最初から検索する。 返り値のベースは 0 または $[ にセットされていればその値である。 SUBSTR が見つからなければ、ベースから 1 を引いた値を返す。 通常 -1 である。

See section $[ : 配列の最初の要素や、サブストリングの最初の文字の添え字.

length

`length(EXPR)'
`length EXPR'

EXPR の値の文字列長を返す。 EXPR を省略すると、$_ の長さを返す。

rindex

`rindex(STR,SUBSTR,POSISION)'
`rindex(STR,SUBSTR)'

index と同じような動作をするが、 違いは STR 内に 最後に現れる SUBSTR の位置を返すことである。

POSITION を指定すると、 その位置またはそれより前で最後に現れる位置を返す。 See section index.

substr

`substr(EXPR,OFFSET,LEN)'
`substr(EXPR,OFFSET)'

EXPR から文字列を取り出し返す。1 文字目はオフセット 0 であるが、 $[ にセットすることで変えることができる。OFFSET が負の場合は、 文字列の終わりからその数分戻った所から始める。

LEN を省略すると、文字列の残り全部を返す。

substr() 関数は左辺値として使うこともできるが、 この場合 EXPR が 左辺値でなくてはならない。 LEN よりも短いものを代入すると、その文字列は短くなり、 LEN よりも長いものを代入するとそれに合わせて長くなる。 文字列の長さを変えない場合は sprintf を用いて パディングまたは切捨てをしなければならない。

See section $[ : 配列の最初の要素や、サブストリングの最初の文字の添え字.

配列 & リストを扱う関数

delete

`delete $ASSOC{KEY}'

指定した連想配列から、指定した値を削除する。 削除された値を返すか、何も削除されなかった場合は undefined value を返す。 dbm ファイルに bind された連想配列を削除すると、 dbm ファイルのエントリを削除する。

以下の例では連想配列の全ての値を削除する。

foreach $key (keys %ARRAY) {
     delete $ARRAY{$key};
}

(が、reset コマンドを使った方が速いだろう。 undef %ARRAY はもっと速いだろう。)

each

`each(ASSOC_ARRAY)'
`each ASSOC_ARRAY'

連想配列の、キーと次の値への値?からなる 2 要素の配列を返す。

従って、繰り返しができる。エントリーはランダムな順序で返ってくる。

全配列を読み終えると、 ヌル配列が返る(これは代入された場合は FALSE すなわち 0 になる)。 この後続けてコールすると繰り返しを再び始める。 繰り返し情報は全ての配列を読むことによってのみ初期化される。

繰り返しの途中では配列を変更してはいけない。 繰り返し情報は各連想配列に一つずつあり、 プログラム中の 全ての each(), key(), values() 関数コールで共有される。 次の例では printenv のように環境をプリントアウトするが、順番が異なる。

while (($key,$value) = each %ENV) {
     print "$key=$value\n";
}

See section keys, and See section values.

grep

`grep(EXPR,LIST)'

LIST の全要素について EXPR を評価し (各要素を $_ にセットしながら)、 expression が true であると評価された要素からなる配列を返す。

スカラーのコンテキストでは、expression が true となった回数を返す。

@foo = grep(!/^#/, @bar);    # コメントを無視する

注意: $_ は配列値への参照となっているので、 配列要素を変更するのに用いることができる。これは便利である一方、 LIST が名前のついた配列でない場合には、ちょっと変な結果を返すことがある。

join

`join(EXPR,LIST)'
`join(EXPR,ARRAY)'

LIST または ARRAY の個々の文字列を EXPR の値で区切った 一つの文字列にする。

$_ = join(':',$login,$passwd,$uid,$gid,$gcos,$home,$shell);

See section split.

keys

`keys(ASSOC_ARRAY)'
`keys ASSOC_ARRAY'

指定された連想配列の全てのキーからなる通常の配列を返す。 キーは全くランダムな順序で返されるが、 values()each() 関数の出力と同じである (連想配列が変更されていなければ)。 以下は環境を出力するまた別の方法である。

@keys = keys %ENV;
@values = values %ENV;
while ($#keys >= 0) {
     print pop(@keys), '=', pop(@values), "\n";
}

または、キーでソートしてみると、

foreach $key (sort(keys %ENV)) {
     print $key, '=', $ENV{$key}, "\n";
}

See section each, and See section values.

pop

`pop(ARRAY)'
`pop ARRAY'

配列の最後の値を返し、配列を 1 減らす。

$tmp = $ARRAY[$#ARRAY--];

と同じ効果がある。配列に要素が一つもない場合は undefined value を返す。

See section push.

push

`push(ARRAY,LIST)'

ARRAY(@ は付けなくてよい)をスタックのように扱い、 LIST の値を ARRAY の最後に追加する。 ARRAY の長さは LIST の長さ分増える。

for $value (LIST) {
     $ARRAY[++$#ARRAY] = $value;
}

と同じ効果を持つが、より効率がよい。

See section pop.

reverse

`reverse(LIST)'
`reverse LIST'

配列のコンテキストでは、LIST の要素を逆順にした配列値を返す。

スカラーのコンテキストでは、 LIST の最初の要素のバイト列を逆にした文字列を返す。

shift

`shift(ARRAY)'
`shift ARRAY'
`shift'

配列の最初の値を取り出してそれを返す。 そして、配列の長さを 1 減らして全要素をずらす。 配列に要素がない場合、undefined value を返す。

ARRAY を省略すると、 メインプログラムでは @ARGVshift し、 サブルーチンでは @_ を shift する。 (これは lexically(?) に決定される。)

unshift()push()pop() も参照のこと。 shift()unshift() は、 push()pop() が配列の右について行うのと同じことを 配列の左について行う。

See section unshift, See section push, and See section pop.

sort

`sort(SUBROUTINE LIST)'
`sort(LIST)'
`sort SUBROUTINE LIST'
`sort BLOCK LIST'
`sort LIST'

LIST をソートし、ソートされた配列を返す。 配列中の存在しない値は除かれる。 SUBROUTINE または BLOCK を省略すると、 標準的な文字列比較の順でソートする。

SUBROUTINE を指定するときは、配列の要素の並べ替えかたに応じて、 0 より小、0、0 より大の整数値を返すサブルーチンの名前を指定する。 (このためのサブルーチンにおいては、 <=>cmp といった演算子が大変便利である。) SUBROUTINE はスカラー変数の名前でもよい。 この場合その変数の値が使用するサブルーチンの名前を表す。

サブルーチン名の代わりに任意の BLOCK を指定して、 インラインのソートサブルーチンとすることができる。

効率を良くするため、通常のサブルーチンコールをとばしている。 このため、次の影響がある。

サブルーチンは再帰的であってはならない。 また、比較される 2 要素は @_ を通じてではなく、 $a$b を通じてサブルーチンに渡される。(以下の例を参照。) これらは参照渡しであるので、$a$b を変更してはいけない。

例:

# 辞書順でソート
@articles = sort @files;

# 同様のものでソートルーチンを明示したもの
@articles = sort {$a cmp $b;} @files;

# 同様のもので逆順
@articles = sort {$b cmp $a;} @files;

# 数値的に昇順にソート
@articles = sort {$a <=> $b;} @files;

# 数値的に降順にソート
@articles = sort {$b <=> $a;} @files;

# 明示的なサブルーチン名でソート
sub byage {
    $age{$a} <=> $age{$b}; # 整数であると仮定している
}
@sortedclass = sort byage @class;

sub reverse { $b cmp $a; }
@harry = ('dog','cat','x','Cain','Abel');
@george = ('gone','chased','yz','Punished','Axed');
print sort @harry;
     # 出力は AbelCaincatdogx
print sort reverse @harry;
     # 出力は xdogcatCainAbel
print sort @george, 'to', @harry;
     # 出力は AbelAxedCainPunishedcatchaseddoggonetoxyz

splice

`splice(ARRAY,OFFSET,LENGTH,LIST)'
`splice(ARRAY,OFFSET,LENGTH)'
`splice(ARRAY,OFFSET)'

ARRAY から OFFSETLENGTH で示された要素を除き、 LIST があればそれと入れ替える。配列から除かれた要素を返す。 配列は必要に応じて大きくなったり小さくなったりする。 LENGTH を省略すると、OFFSET 以降の要素が全て除かれる。 次の例は全てそれぞれ同等である。($[ == 0 であると仮定している。)

push(@a,$x,$y)	        splice(@a,$#a+1,0,$x,$y)
pop(@a)                splice(@a,-1)
shift(@a)              splice(@a,0,1)
unshift(@a,$x,$y)      splice(@a,0,0,$x,$y)
$a[$x] = $y            splice(@a,$x,1,$y);

次の例は、配列の長さが配列の前に渡されると仮定している。

sub aeq { # 2 つの配列値を比較する
     local(@a) = splice(@_,0,shift);
     local(@b) = splice(@_,0,shift);
     return 0 unless @a == @b;     # 同じ長さ?

     while (@a) {
         return 0 if pop(@a) ne pop(@b);
     }
     return 1;
}
if (&aeq($len,@foo[1..$len],0+@bar,@bar)) { ... }

split

`split(/PATTERN/,EXPR,LIMIT)'
`split(/PATTERN/,EXPR)'
`split(/PATTERN/)'
`split'

文字列を文字列の配列に split し、その配列を返す。 (配列のコンテキストでない場合は、フィールドの数を返し、 split の結果を @_ に格納する。 (配列のコンテキストでも、パターン delimiter に ?? を指定することで @_ への代入を強制することができるが、返り値は配列値のままである。))

EXPR を省略すると、文字列 $_split する。 PATTERN も省略すると、 whitespace (/[ \t\n]+/)split する。 PATTERN にマッチする文字は、 全てフィールドを分ける delimiter であると解釈される (注意: delimiter は 1 字を超えてもよい)。

LIMIT を指定すると、それを超えない数に split する (少ない場合もある)。LIMIT を指定しない場合は、 余分なヌルフィールドが除かれる (pop() を使おうというユーザはこのことを覚えておいた方が良いのでは?)。

ヌル文字列にマッチするパターン(ヌルパターン // と混同しないように。 // はヌル文字列にマッチするパターン群の一つにすぎない)は そのパターンがマッチする全ての点で EXPR の値を文字に分割する。

print join(':', split(/ */, 'hi there'));

`h:i:t:h:e:r:e' を出力する。

LIMIT パラメータは行の一部を split するのに使用できる。

($login, $passwd, $remainder) = split(/:/, $_, 3);

(リストに代入する時に LIMIT が省略されていると、 perl はリスト中の変数の数より 1 多い数を LIMIT とする。 これは不必要な作業を無くすためである。 上のリストでは、LIMIT はデフォルトで 4 であったはずである。 時間にクリティカルなアプリケーションでは 本当に必要なフィールド以上に分割しないようにするべきである。)

PATTERN が括弧を含んでいる場合、 delimiter 中でマッチする文字列からさらに配列要素が作り出される。

split(/([,-])/,"1-10,20");

が作る配列の値は

(1,'-',10,',',20)

/PATTERN/ は 実行時に変化するパターンを指定する expression であってもよい。 (実行時コンパイルを 1 回だけ行うには、/$variable/o を用いる。)

特殊な場合として、スペース (' ') を指定すると、 何も指定しない場合と同じように white space で split するが、 文字列の始めに whitespace があっても一番目にヌルフィールドを作らない。 すなわち、 split(' ') は awk のデフォルトの動作をエミュレートするのに使える。

しかし、 split(/ /) は文字列の最初のスペースの数だけヌルフィールドが得られる。

open(passwd, '/etc/passwd');
while (<passwd>) {
     ($login, $passwd, $uid, $gid, $gcos, $home, $shell)
          = split(/:/);
     ...
}

注意: 上の例で $shell は改行文字を含む。chop() を参照。
また、join も参照のこと。

See section chop, and See section join.

unshift

`unshift(ARRAY,LIST)'

視点により、shift または push の逆を行う。 LISTARRAY の前に付け、できた配列の要素数を返す。

unshift(ARGV, '-e') unless $ARGV[0] =~ /^-/;

See section shift, and See section push.

values

`values(ASSOC_ARRAY)'
`values ASSOC_ARRAY'

指定した連想配列の全ての値からなる通常の配列を返す。 値は全くランダムな順序で返るが、 keys()each() 関数が同じ配列に対して返すものと同じ順序である。

See section each, and See section keys.

ファイル操作関数

chmod

`chmod(LIST)'
`chmod LIST'

属性は最初の引数において数値で指定する。 属性を変更するのに成功したファイルの数を返す。

$cnt = chmod 0755, 'foo', 'bar';
chmod 0755, @executables;

chown

`chown(LIST)'
`chown LIST'

uidgid を最初の引数二つで(この順で)数値で指定する。 変更するのに成功したファイルの数を返す。

$cnt = chown $uid, $gid, 'foo', 'bar';
chown $uid, $gid, @filenames;

(例: passwd ファイルから数値でない uid を検索する)
print "User: ";
$user = <STDIN>;
chop($user);
print "Files: "
$pattern = <STDIN>;
chop($pattern);
open(pass, '/etc/passwd')
     || die "Can't open passwd: $!\n";
while (<pass>) {
     ($login,$pass,$uid,$gid) = split(/:/);
     $uid{$login} = $uid;
     $gid{$login} = $gid;
}
@ary = <${pattern}>;     # ファイル名を得る
if ($uid{$user} eq ") {
     die "$user not in passwd file";
}
else {
     chown $uid{$user}, $gid{$user}, @ary;
}

link

`link(OLDFILE,NEWFILE)'

old filename にリンクされた new filename を作成する。 成功なら 1、失敗なら 0 を返す。

lstat

`lstat(FILEHANDLE)'
`lstat FILEHANDLE'
`lstat(EXPR)'
`lstat SCALARVARIABLE'

stat() 関数と同じことをするが、 シンボリックリンクが指すファイルではなく、 シンボリックリンクそのものの stat を返す。 シンボリックリンクをインプリメントしていないシステムでは、 stat と同じである。

See section stat.

mkdir

`mkdir(FILENAME,MODE)'

FILENAME で指定されるディレクトリを作成する。 permissionMODE(umask で修飾される)で指定する。 成功すれば 1 を返し、失敗すれば 0 を返すと共に $! をセットする(errno)。

readlink

`readlink(EXPR)'
`readlink EXPR'

シンボリックリンクがインプリメントされている場合、 シンボリックリンクの値を返す。そうでない場合は致命的エラーとなる。 システムエラーが起こった場合は undefined value を返し、 $! をセットする(errno)。 EXPR を省略すると、$_ を用いる。

rename

`rename(OLDNAME,NEWNAME)'

ファイルの名前を変更する。成功すれば 1、そうでなければ 0 を返す。 ファイルシステムを超えては働かない。

rmdir

`rmdir(FILENAME)'
`rmdir FILENAME'

FILENAME で指定されたディレクトリが空ならば消去する。 成功すれば 1、そうでなければ 0 を返し、$! (errno) をセットする。 FILENAME を省略すると、$_ を用いる。

select

`select(FILEHANDLE)'
`select'

現在 select されているファイルハンドルを返す。 FILEHANDLE を指定すれば出力のデフォルトファイルハンドルをセットする。 これには二つの効果がある。 write または print をファイルハンドルなしで用いると、 デフォルトのこの FILEHANDLE が用いられる。

また、出力に関連づけられた変数への参照は、 この(select で指定した)出力チャンネルを参照する。 例えば、 1 以上の出力チャンネルについてフォーマットの先頭行をセットしなければならない時は、

select(REPORT1);
$^ = 'report1_top';
select(REPORT2);
$^ = 'report2_top';

のようにすればよい。

FILEHANDLE は 実際のファイルハンドルの名前を値として持つ expressionでもよい。 したがって、以下のように使える。

$oldfh = select(STDERR); $| = 1; select($oldfh);

`select(RBITS,WBITS,EBITS,TIMEOUT)'

bitmasks を指定してシステムコール select をコールする。 bitmasksfileno()vec() を用いて 以下のようにして得ることができる。

$rin = $win = $ein = ";
vec($rin,fileno(STDIN),1) = 1;
vec($win,fileno(STDOUT),1) = 1;
$ein = $rin | $win;

多くのファイルハンドルを select したい時は サブルーチンを書いた方がいいかもしれない。

sub fhbits {
    local(@fhlist) = split(' ',$_[0]);
    local($bits);
    for (@fhlist) {
     vec($bits,fileno($_),1) = 1;
    }
    $bits;
}
$rin = &fhbits('STDIN TTY SOCK');

通常の使い方は、

($nfound,$timeleft) =
  select($rout=$rin, $wout=$win, $eout=$ein, $timeout);

または何かが ready になるまでブロックするには、

$nfound = select($rout=$rin, $wout=$win,
    $eout=$ein, undef);

である。

bitmasks はいずれも undef にすることができる。 TIMEOUT を指定する時は秒単位で、小数点も可能である。

注意:

インプリメントによっては $timeleft を返す機能は利用できない場合がある。
その場合は常に指定した $timeout と同じ値で $timeleft が返る。

stat

`stat(FILEHANDLE)'
`stat FILEHANDLE'
`stat(EXPR)'
`stat SCALARVARIABLE'

FILEHANDLE でオープンされているか、 ファイルネームが EXPR である ファイルの statistics を表す 13 要素の配列を返す。 典型的には以下のように使用する。

($dev,$ino,$mode,$nlink,$uid,$gid,$rdev,$size,
   $atime,$mtime,$ctime,$blksize,$blocks)
       = stat($filename);

stat に特殊なファイルハンドルとしてアンダーラインを指定すると、 stat を行わず、 最後の stat または ファイルテストの結果である stat 構造体の内容を返す。

if (-x $file && (($d) = stat(_)) && $d < 0) {
     print "$file is executable NFS file\n";
}
(この例は NFS のデバイス番号が負になるようなマシンでのみ動作する。)

symlink

`symlink(OLDFILE,NEWFILE)'

OLDFILE にシンボリックリンクされた NEWFILE を作成する。 成功すれば 1、それ以外では 0 を返す。 シンボリックリンクをサポートしないシステムでは、実行時に致命的エラーとなる。 それをチェックするには、eval を用いる。

$symlink_exists = (eval	'symlink("","");', $@ eq ");

truncate

`truncate(FILEHANDLE,LENGTH)'
`truncate(EXPR,LENGTH)'

FILEHANDLE にオープンされたファイル または EXPR という名前のファイルを指定する長さに切り詰める。 システムに truncate がインプリメントされていなければ致命的エラーとなる。

unlink

`unlink(LIST)'
`unlink LIST'

リストされたファイルを消去する。消去に成功したファイルの数を返す。

$cnt = unlink 'a', 'b', 'c';
unlink @goners;
unlink <*.bak>;

注意: unlink はスーパーユーザであって かつ perl に -U フラグを指定していないかぎりディレクトリは消去しない。 これらの条件にあてはまっている場合でも、 ディレクトリを unlink することは ファイルシステムにダメージを与えることに注意せよ。 かわりに rmdir を使うこと。

utime

`utime(LIST)'
`utime LIST'

リストしたファイルの全てについてアクセス時刻と変更時刻を変更する。 リストの最初の 2 要素は数値でなくてはならず、アクセス時刻、変更時刻の順である。 変更に成功したファイルの数を返す。 各ファイルの inode の変更時刻は現在時刻にセットされる。

`touch' コマンドの例:

#!/usr/bin/perl
$now = time;
utime $now, $now, @ARGV;

ディレクトリ読み込み関数

closedir

`closedir(DIRHANDLE)'
`closedir DIRHANDLE'

opendir()open されたディレクトリを close する。

opendir

`opendir(DIRHANDLE,EXPR)'

EXPR という名前のディレクトリを open し、 readdir()telldir()seekdir()
rewinddir()closedir() を可能にする。 成功すれば true を返す。
DIRHANDLEs には FILEHANDLEs とは別の名前空間がある。

readdir

`readdir(DIRHANDLE)'
`readdir DIRHANDLE'

opendir() でオープンしたディレクトリの次のエントリを返す。 配列のコンテキストで用いると、ディレクトリの残りのエントリを全て返す。 エントリが残っていない場合は、スカラーのコンテキストでは undefined value、 配列のコンテキストではヌルリストを返す。

rewinddir

`rewinddir(DIRHANDLE)'
`rewinddir DIRHANDLE'

readdir() で用いる、 DIRHANDLE のカレント位置をディレクトリの最初にセットする。

seekdir

`seekdir(DIRHANDLE,POS)'

readdir() で用いる DIRHANDLE のカレント位置をセットする。 POStelldir() が返す値でなくてはならない。 directory compaction については 対応するシステムライブラリ関数と同様の注意が必要である。

telldir

`telldir(DIRHANDLE)'
`telldir DIRHANDLE'

DIRHANDLE に対する readdir() の現在の位置を返す。 ディレクトリのある位置にアクセスするために この値を seekdir() に指定することができる。 directory compaction については 対応するシステムライブラリルーチンと同じ注意が必要である。

入出力関数

以下の項目の説明における FILEHANDLE は、 open でオープンされたファイルハンドルか、 ファイルハンドルの名前を値に持つスカラー変数である。

binmode

`binmode(FILEHANDLE)'
`binmode FILEHANDLE'

バイナリファイルとテキストファイルを区別する OS において、 ファイルをバイナリモードで読むようにする。 バイナリモードでない場合は入力の際に CR LFLF に、 出力の際に LFCR LF に変換される。 Unix の下では何の効果もない。 FILEHANDLE がexpression の場合は、 その値がファイルハンドルの名前として解釈される。

close

`close(FILEHANDLE)'
`close FILEHANDLE'

ファイルハンドルに結び付けられているファイルやパイプをクローズする。

同じ FILEHANDLE を用いてすぐにまた open する場合は、 close する必要は無いが(openclose する)、 入力ファイルに対して明示的に close を行うと ラインカウンタ($.)がリセットされる (open の行う close ではそうならない)。

また、パイプを close する時には そのパイプを用いて実行されているプロセスが終わるのを待つ (あとでパイプの出力を見ることができるように)。 パイプを明示的に close するとコマンドの status が $? に入る。

open(OUTPUT, '|sort >foo');   # pipe to sort
...  # print stuff to output
close OUTPUT;       # wait for sort to finish
open(INPUT, 'foo'); # get sort's results

FILEHANDLE はファイルハンドルの名前を値として持つ expression でもいい。

dbmclose

`dbmclose(ASSOC_ARRAY)'
`dbmclose ASSOC_ARRAY'

dbm ファイルと連想配列の bind を終了する。 連想配列に残っている値は意味がない。 この関数は ndbm がある場合にのみ便利である。

dbmopen

`dbmopen(ASSOC,DBNAME,MODE)'

dbm または ndbm ファイルと連想配列を bind する。 ASSOC は連想配列の名前である(似てはいるけれど、 普通の open と違い、最初の引数はファイルハンドルではない)。 DBNAME はデータベースの名前から `.dir'または `.pag' の拡張子をとったものである。 データベースが存在しなければ、 MODE で指定される protection で作成される。 古い dbm 関数しかサポートしていないシステムの場合は、 プログラム中で dbmopen は一回しか実行することができない。 dbmndbm もないシステムで dbmopen をコールすると 致命的エラーとなる。

dbmopen の前の連想配列の値は失われる。 dbm ファイルの値の一部はメモリにキャッシュされる。 これはデフォルトでは 64 個であるが、 dbmopen に先立って連想配列にダミーの値を代入することで増やすことができる。 必要なら、reset コマンドでキャッシュをフラッシュすることができる。

dbm ファイルに書き込み許可がない場合、 連想配列の値を読むことはできても、代入はできない。 書き込みができるかどうかテストするのなら、ファイルテストを使うか、 eval 中でダミーの配列をセットしてみて、 エラーが起こるかどうかで判断することができる。 大きな dbm ファイルの場合、 keys()values() といった関数は巨大な配列を返すことがある。 each() を用いて 大きな dbm ファイルについて繰り返しを行いたい場合は、次の例を参照。

# ヒストリーファイルのオフセットを出力
dbmopen(HIST,'/usr/lib/news/history',0666);
while (($key,$val) = each %HIST) {
     print $key, ' = ', unpack('L',$val), "\n";
}
dbmclose(HIST);

eof

`eof(FILEHANDLE)'
`eof()'
`eof'

FILEHANDLE に対する次の読み込みが end of file を返すか、 FILEHANDLEopen されていない場合、1 を返す。 FILEHANDLE は ファイルハンドルの名前を値に持つ expression でもよい。 (注意: この関数は実際には 1 文字読み込んでそれを ungetc するので、 インタラクティブなコンテキストではあまり有用ではない。)

引数なしの eof は最後に読み込んだファイルの eof status を返す。 空の括弧 () は、コマンドラインで指定されたファイルから作られる 擬似ファイルを指定するのに使われる。 即ち、eof()while (<>) の中で 最後のファイルの終わりを検出するために使う時のみ意味がある。 while (<>) ループの全てのファイルの終わり検出のためには、 eof(ARGV) か 括弧のない eof を使うべきである。

# 最後のファイルの最後の 1 行前にダッシュを入れる
while (<>) {
     if (eof()) {
          print "--------------\n";
     }
     print;
}

# 各入力ファイルごとに行番号をリセットする
while (<>) {
     print "$.\t$_";
     if (eof) {     # eof() ではない。
          close(ARGV);
     }
}

fcntl

`fcntl(FILEHANDLE,FUNCTION,SCALAR)'

ioctl(2) 関数をインプリメントする。正しく関数を定義するにはおそらく

require "fcntl.ph";  # たぶん /usr/local/lib/perl/fcntl.ph

を最初に行う必要があるだろう。 `fcntl.ph' がなかったり正しく定義されていなければ、
`<sys/fcntl.h>' などに基づいて自分で定義する必要がある。 (perl キットにはこの作業を助けるための `h2ph' という perl スクリプトがある。)

引数の処理や返り値は ioctl と全く同じである。

注意: fcntl(2) をインプリメントしていないマシンで使用すると 致命的エラーとなる。

fileno

`fileno(FILEHANDLE)'
`fileno FILEHANDLE'

ファイルハンドルに対するファイルディスクリプタを返す。 select()bitmap を構築するのに便利である。 FILEHANDLE が expression の場合は、 その値がファイルハンドルの名前であると解釈される。

flock

`flock(FILEHANDLE,OPERATION)'

FILEHANDLE について flock(2) をコールする。 OPERATION の定義については flock(2) のマニュアルを参照のこと。 成功すると true、失敗すると false を返す。 flock(2) をインプリメントしていないマシンで使用すると 致命的エラーとなる。以下は BSD システム用 mailbox appender である。

$LOCK_SH = 1;
$LOCK_EX = 2;
$LOCK_NB = 4;
$LOCK_UN = 8;

sub lock {
    flock(MBOX,$LOCK_EX);
    # そして、待っている間に誰かが追加する場合に備えて...
    seek(MBOX, 0, 2);
}

sub unlock {
    flock(MBOX,$LOCK_UN);
}

open(MBOX, ">>/usr/spool/mail/$ENV{'USER'}")
     || die "Can't open mailbox: $!";

do lock();
print MBOX $msg,"\n\n";
do unlock();

getc

`getc(FILEHANDLE)'
`getc FILEHANDLE'
`getc'

FILEHANDLE に結び付いている入力ファイルの次の character を返す。 EOF の場合はヌル文字列を返す。 FILEHANDLE を省略すると、STDIN から読む。

ioctl

`ioctl(FILEHANDLE,FUNCTION,SCALAR)'

ioctl(2) 関数をインプリメントする。正しく関数を定義するにはおそらく

require "ioctl.ph";  # probably /usr/local/lib/perl/ioctl.ph

を最初に行う必要があるだろう。 `ioctl.ph' がなかったり正しく定義されていなければ、
`<sys/ioctl.h>' などに基づいて自分で定義する必要がある。 (perl キットには、 この作業を助けるための h2ph という perl スクリプトがある。)

SCALARFUNCTION により、 参照かつまたは代入される -- SCALAR の文字列値へのポインタが 実際の ioctl コールの三番目の引数として渡される。 (SCALAR が文字列値でなくて数値の場合は、 文字列値へのポインタではなくその値が渡される。 これを常に保証するには、SCALAR にあらかじめ 0 を足せば良い。)

ioctl() で使用される構造体の値を操作するには、 pack()unpack() 関数が便利である。 次の例では、erase character を DEL にセットする。

do 'ioctl.ph';
$sgttyb_t = "ccccs";          # char 4 つと short
if (ioctl(STDIN,$TIOCGETP,$sgttyb)) {
     @ary = unpack($sgttyb_t,$sgttyb);
     $ary[2] = 127;
     $sgttyb = pack($sgttyb_t,@ary);
     ioctl(STDIN,$TIOCSETP,$sgttyb)
          || die "Can't ioctl: $!";
}

ioctl(および fcntl)の返り値は次のようになる。

OS の返り値:            perl の返り値
    -1                  undefined value
    0                   string `0 but true'
    それ以外             その値

つまり、perl は成功すれば真、失敗すれば偽を返すが、 OS が返す実際の値を簡単に得ることもできる。

($retval = ioctl(...)) || ($retval = -1);
printf "System returned %d\n", $retval;

open

`open(FILEHANDLE,EXPR)'
`open(FILEHANDLE)'
`open FILEHANDLE'

ファイル名が EXPR で指定されるファイルを open し、 FILEHANDLE と結び付ける。

FILEHANDLE が expression の場合は、 その値が実際のファイルハンドルの名前として用いられる。 EXPR を省略した場合、 FILEHANDLE と同名のスカラー変数がファイル名を持つ。

成功すれば non-zero を返し、そうでない場合は undefined を返す。 open がパイプを含む場合、返り値はサブプロセスの pid になる。

$article = 100;
open article || die "Can't find article $article: $!\n";
while (<article>) { ...

open(LOG, '>>/usr/spool/news/twitlog');
                # (log は予約語である)

open(article, "caesar <$article |");
                # 記事を decrypt する

open(extract, "|sort >/tmp/Tmp$$");
                # $$ は現在のプロセス #

# 引数のファイルリストについて
# それがインクルードするファイルも含めて処理する

foreach $file (@ARGV) {
     do process($file, 'fh00');    # no pun intended
}

sub process {
     local($filename, $input) = @_;
     $input++;      # これは文字列のインクリメントである
     unless (open($input, $filename)) {
          print STDERR "Can't open $filename: $!\n";
          return;
     }
     while (<$input>) {       # 間接指定に注意
          if (/^#include "(.*)"/) {
               do process($1, $input);
               next;
          }
          ...       # whatever
     }
}

Bourne shell の慣習で、EXPR`>&' で始めても良い。 この場合、残りの文字列は ファイルハンドル (または数値ならば ファイルディスクリプタ)と解釈され、 dup され、open される。 `&'`>', `>>', `<', `+>', `+>>', `+<' の後で用いて良い。 指定するモードは元のファイルハンドルと同じでなければならない。 以下のスクリプトは STDOUT および STDERR を保存し、 リダイレクトし、元に戻す。

#!/usr/bin/perl
open(SAVEOUT, ">&STDOUT");
open(SAVEERR, ">&STDERR");

open(STDOUT, ">foo.out") || die "Can't redirect stdout";
open(STDERR, ">&STDOUT") || die "Can't dup stdout";

select(STDERR); $| = 1;       # バッファリングなしにする
select(STDOUT); $| = 1;       # バッファリングなしにする

print STDOUT "stdout 1\n";    # これはサブプロセスでも
print STDERR "stderr 1\n";    # 働く

close(STDOUT);
close(STDERR);

open(STDOUT, ">&SAVEOUT");
open(STDERR, ">&SAVEERR");

print STDOUT "stdout 2\n";
print STDERR "stderr 2\n";

コマンド `-' を用いてパイプを open する場合、 すなわち `|-' または`-|' の場合、 暗黙の内に fork がなされ、 open の返り値は親プロセスでは子プロセスの pid、 子プロセスでは 0 になる。 (open が成功したかどうかは defined($pid) で確かめる。) ファイルハンドルの挙動は親プロセスでは通常と同じであるが、 そのファイルハンドルへの i/o は 子プロセスの STDOUT/STDIN にパイプされる。

子プロセスではファイルハンドルは open されていない --- i/o は新たな STDOUTから/STDIN に なされる。

良く使われるのは、例えば setuid で走らせているときなど、 パイプコマンドの実行状態をコントロールしたい時や、 シェルコマンドにメタキャラクターがあるかどうかをチェックしたくない時である。

次の 2 つのペアはそれぞれある程度(more or less)同等である。

open(FOO, "|tr '[a-z]' '[A-Z]'");
open(FOO, "|-") || exec 'tr', '[a-z]', '[A-Z]';

open(FOO, "cat -n '$file'|");
open(FOO, "-|") || exec 'cat', '-n', $file;

明示的にパイプされたファイルハンドルを close すると 親プロセスは子プロセスが終了するのを待ち、status 値 $? が返り値となる。

注意:
fork を行う操作においては、 フラッシュされていないバッファは両方のプロセスにおいてフラッシュされずに残る。 つまり、二重に出力されるのを避けるには、 $| をセットしなければならない。See section $| : write または print の後にフラッシュを行うか否か for $|.

open に渡されるファイル名は最初や最後のスペースを取り除かれる。 名前におかしな文字が含まれるファイルを open するには、 次のようにして前後のスペースが取り除かれないようにしなければならない。

$file =~ s#^(\s)#./$1#;
open(FOO, "< $file\0");

pipe

`pipe(READHANDLE,WRITEHANDLE)'

対応するシステムコールと同様、接続されたパイプのペアをオープンする。 パイプでつながったプロセスのループは、 注意深くやらないとデッドロックを起こすので注意。 さらに、perl のパイプは stdio のバッファリングを使うので、 アプリケーションによっては、 WRITEHANDLE をコマンド毎にフラッシュするために、 $| をセットする必要があるかもしれない。 See section $| : write または print の後にフラッシュを行うか否か for $|.

[perl 3.0 パッチレベル 9 以上が必要。]

print

`print(FILEHANDLE LIST)'
`print(LIST)'
`print FILEHANDLE LIST'
`print LIST'
`print'

文字列またはコンマで区切られた文字列のリストを出力する。 成功すれば non-zero を返す。 FILEHANDLE は ファイルハンドルの名前を値として持つスカラー変数名でもよい。 こうすると、1 レベルの間接的な出力ができる。 (注意: FILEHANDLE が変数で、次のトークンが文の終わりの場合は それが演算子と誤解釈される可能性があるので、間に + を入れるか、 引数に括弧をつけるかしなければならない。)

FILEHANDLE を省略すると、 デフォルトでは標準出力(または最後に select された出力チャンネル --- select() 参照 See section select.)に出力する。 LIST も省略すると、$_STDOUT に出力する。 デフォルトの出力チャンネルを STDOUT 以外のものにするには、 select演算子を使用する。

注意:
printLIST を引数に取るので、 LIST の要素は全て配列のコンテキストで評価され、 またサブルーチンをコールすると その 1 つ以上の expression は配列のコンテキストで評価される。?

また、キーワード print の後に左括弧はつけないように注意する必要がある (print への引数を区切る --- + を間に入れるか全引数を括弧で囲む --- ために対応した右括弧をつけたい場合を除いて)。

printf

`printf(FILEHANDLE LIST)'
`printf(LIST)'
`printf FILEHANDLE LIST'
`printf LIST'

print FILEHANDLE sprintf(LIST) と同等である。

See section print, and See section sprintf.

read

`read(FILEHANDLE,SCALAR,LENGTH,OFFSET)'
`read(FILEHANDLE,SCALAR,LENGTH)'

指定した FILEHANDLE から、 LENGTH バイトのデータを読んで SCALAR に格納する。 実際に読み込んだバイト数、またはエラーがあれば undef を返す。 SCALAR は実際に読んだバイト数に合わせてサイズが変わる。

OFFSET を指定すると、 読んだデータを文字列の先頭ではなく他の場所に格納する。 これは実際には、 stdiofread コールを用いてインプリメントしている。 本当の read システムコールを使いたければ、sysread を参照せよ。See section sysread.

seek

`seek(FILEHANDLE,POSITION,WHENCE)'

FILEHANDLE のファイルポインタを任意の位置に移動する。 stdiofseek() と同じである。 FILEHANDLE はファイルハンドルの名前を値として持つ expression でもよい。 成功すれば 1、そうでなければ 0 である。

sprintf

`sprintf(FORMAT,LIST)'

通常の printf の習慣でフォーマットされた文字列を返す。
文字 `*' はサポートしていない。

sysread

`sysread(FILEHANDLE,SCALAR,LENGTH,OFFSET)'
`sysread(FILEHANDLE,SCALAR,LENGTH)'

システムコール read(2) を用いて、 指定したファイルハンドルから 変数 SCALARLENGTH バイトのデータを読み込む。

これは stdio を経由しないので、 他の種類の読み込みと一緒に使うと混乱することがある。

実際に読んだバイト数を返す。エラーがあった場合は undef を返す。

読み込んだデータを文字列の先頭からではなく別の位置に格納するために、 OFFSET を指定してもよい。

syswrite

`syswrite(FILEHANDLE,SCALAR,LENGTH,OFFSET)'
`syswrite(FILEHANDLE,SCALAR,LENGTH)'

システムコール write(2) を用いて、 指定したファイルハンドルに 変数 SCALAR から LENGTH バイトのデータを書き込む。

これは stdio を経由しないので、 print と一緒に使うと混乱することがある。

実際に書き込んだバイト数を返す。エラーがあった場合は undef を返す。

書き込むデータを文字列の先頭からではなく別の位置から取り出すために、 OFFSET を指定してもよい。

tell

`tell(FILEHANDLE)'
`tell FILEHANDLE'
`tell'

FILEHANDLE の現在のファイル位置を返す。 FILEHANDLE は 実際のファイルハンドルの名前を値として持つ expression であってもよい。 FILEHANDLE を省略すると、最後に読んだファイルを仮定する。

write

`write(FILEHANDLE)'
`write(EXPR)'
`write'

レコードをフォーマットして(複数行でもよい)指定したファイルに出力する。 その際、そのファイルに指定されているフォーマットを用いる。 デフォルトではファイルのフォーマットはファイルハンドルと同名のものだが、 カレント出力チャンネル(select 参照)のフォーマットは フォーマットの名前を $~ に指定することで明示できる。 See section $ ̄ : 出力チャンネルの現在のレポートフォーマット名 for $~.

整形操作は自動的に行われる。 現在のページにフォーマットしたレコードに対して充分な余裕がない場合は 改頁を出力して次のページに移り、 新しいページのヘッダーをフォーマットするには 特殊なページ先頭フォーマットが使われ、 こうしてレコードが出力される。

デフォルトではページ先頭フォーマットは ファイルハンドル名に "_TOP" をつけたものであるが、 ファイルハンドルが select されている時に $^ に代入することで 好みのフォーマットに動的に変更することができる。 See section $^ : 出力チャンネルの現在のページトップ名 for $^.

現在のページに残っている行数は変数 $- に入っており、 これを 0 にセットして強制的に新しいページに入ることができる。

FILEHANDLE を指定しない場合は、 出力は現在のデフォルト出力チャンネルになされる。 これは最初は STDOUT で、select を用いて変更可能である。

FILEHANDLE が expression の場合は、実行時に expression が評価され、 その結果の文字列が FILEHANDLE の名前として用いられる。

format についての詳細は、Format の章を参照のこと。
See section フォーマット.

注意: writeread の反対ではない

検索・置換関数

/パターン/

m/パターン/ と同じ。次項を参照。

m/パターン/

`m/PATTERN/gio'
`/PATTERN/gio'

文字列中のパターンマッチを検索し、 true(1) または false ('') を返す。 =~!~ で文字列を指定しない場合は $_ 文字列を検索する。 (=~ で指定される文字列は左辺値である必要はない --- expression 評価の結果でも良いが、 =~ の方が優先度が高いことに注意。) Regular Expression の章も参照のこと。 See section 正規表現.

/ が delimiter であるなら、最初の m は省略可能である。 m を使うと、 アルファベット・数字でない任意の文字のペアを delimiter として使える。 これは Unix のパス名(/ を含む)のマッチングをするのに便利である。

二つ目のdelimiter の後にオプション i をつけると、 case insensitive でマッチングを行う。

PATTERN はスカラー変数を含んでいても良いが、 パターン検索を行う毎に置き換えが行われる(そしてパターンが再コンパイルされる)。 (注意:$)$| は文字列の終わりのチェックに使われるであろうから、 置き換えは行われない。)

パターンを最初の一回だけコンパイルさせたい時は、 最後のオプションに o を指定する。 こうすると実行時の再コンパイルを避けることができるので、 変数で置き換えている値がスクリプト実行中に変わらないのであれば、便利である。 PATTERN がヌル文字列に評価された場合、 直前に成功した正規表現が代わりに用いられる。

配列値が必要な文脈で使うと、パターンマッチはパターンを括弧でくくったもの、 すなわち ($1, $2, $3 ...) にマッチする subexpression からなる 配列を返す。実際には $1$2 などをセットせず、 この場合だと、$+$`$&$' もセットしない。

マッチングが失敗した場合、ヌル配列が返る。
マッチングが成功した場合、括弧が一つもなければ、配列値 (1) が返る。

open(tty, '/dev/tty');
<tty> =~ /^y/i && do foo();    # y と答えたら do foo

if (/Version: *([0-9.]*)/) { $version = $1; }

next if m#^/usr/spool/uucp#;

# poor man's grep
$arg = shift;
while (<>) {
     print if /$arg/o;    #  1 回だけコンパイルする
}

if (($F1, $F2, $Etc) = ($foo =~ /^(\S+)\s+(\S+)\s*(.*)/))

最後の例は、$foo を二つの word と残りに分け、 これら三つのフィールドを $F1, $F2, $Etc に代入する。 どの変数が変更されても、すなわち、パターンがマッチすれば、条件は真である。

修飾子 "g" はグローバルパターンマッチを指定する -- すなわち、 文字列中で可能なかぎりマッチを行なう。 コンテキストによりどのように振舞うか。 配列のコンテキストでは、 正規表現中のすべての括弧とマッチする substring からなるリストを返す。 括弧が一つもない場合、パターン全体の回りに括弧があるかのように扱い、 マッチした全文字列のリストを返す。 スカラーのコンテキストでは、文字列全体について繰り返しを行い、 マッチする度に TRUE を返し、ついにマッチしなくなった時点で FALSE を返す。 (言い替えれば、前にどこまでマッチを行なったかを覚えておき、 その位置から検索を再開する。) 最後のマッチを行なってから文字列を変更していないということを仮定している。 マッチの間で文字列を変更すると未定義の動作を行なう可能性がある。 (実は、substr() を使って全文字列の長さを変えないで 文字列をその場で(in-place)変更する場合にはうまくいく。しかし、一般的には、 そのような変更を行なう場合は s//g を使うべきである。)

例:

# array context
($one,$five,$fifteen) = (`uptime` =~ /(\d+\.\d+)/g);

# scalar context
$/ = 1; $* = 1;
while ($paragraph = <>) {
    while ($paragraph =~ /[a-z]['")]*[.!?]+['")]*\s/g) {
     $sentences++;
    }
}
print "$sentences\n";

See section 正規表現.

?パターン?

`?PATTERN?'

reset から reset までで 1 回しかマッチしないことを除いて、 /パターン/ 検索と同じである。例えば、幾つかあるファイルの各々について、 あるものが最初に現れるのを調べるのに便利である。

現在のパッケージにローカルな ?? パターンのみリセットされる。

See section reset.

s/パターン/置き換え/

`s/PATTERN/REPLACEMENT/gieo'

PATTERN を持つ文字列を検索し、 見つかれば、REPLACEMENT テキストと置き換え、置換を行った数を返す。 見つからなければ false (つまり 0)を返す。

オプションとして `g' をつけると、 見つかった全てのパターンについて置換を行う。

`e' も同様にオプションで、 REPLACEMENT"" で括られた文字列ではなく、 expression として評価される。

スラッシュの代わりに アルファベット・数字でない任意の文字を delimiter としてよい。

=~ 演算子 や !~ 演算子を通して文字列を指定しなければ、 $_ について検索し、置換する。 (=~ を用いて指定する文字列はスカラー変数、配列の要素、 またはこれら 2 つへの代入、即ち、左辺値でなければならない。) PATTERN$ を含み、 "文字列最後"ではなくて"変数"に見える場合は、 実行時にその変数が PATTERN に書き込まれる。 パターンのコンパイルを最初の一回だけにし、変数の書き換えを行いたい時は、 `o' を最後につける。PATTERN がヌル文字列に評価された場合、 直前に成功した正規表現が代わりに用いられる。正規表現の項を参照。

s/\bgreen\b/mauve/g;      # wintergreen は変更しない

$path =~ s|/usr/bin|/usr/local/bin|;

s/Login: $foo/Login: $bar/; # 実行時に決まるパターン

($foo = $bar) =~ s/bar/foo/;

$_ = 'abc123xyz';
s/\d+/$&*2/e;        # 'abc246xyz' を出力
s/\d+/sprintf("%5d",$&)/e;     # 'abc  246xyz' を出力
s/\w/$& x 2/eg;      # 'aabbcc  224466xxyyzz' を出力

s/([^ ]*) *([^ ]*)/$2 $1/;     # 最初の 2 フィールドを入れ替え

注意:
最後の例で \ の代わりに $ を使用していることに注意。 正規表現の項を参照。See section 正規表現.

study

`study(SCALAR)'
`study SCALAR'
`study'

SCALAR(指定しなければ $_ )について、 それが次に変更される前に多くのパターンマッチをあらかじめ行う。

検索を行うパターンの性質や数、検索される文字列中の文字の頻度分布により 時間が節約されるかもしれないし、されないかもしれない。 多分これを使用するのとしないのと、 どちらが早く実行できるかを比較してみたいであろう。 数多くの短い定数文字列(より複雑なパターン中の定数部を含む)について 検索を行うループにおいて最も効果があるだろう。 同時に 1 つしか study できない。 別のスカラーを study すると、 最初に study した方は `unstudied' になってしまう。 (study の動作は次のようになる: 検索対象の文字列の全文字の linked list を作り、これにより、例えば、 全ての `k' という文字がどこにあるかがわかる。 C プログラムおよび英文から得た統計的な頻度テーブルに基づいて、 各検索文字列から最も稀な文字を選ぶ。 この"最も稀な"文字を含む位置のみを調べるのである。)

例えば、次のループは、あるパターンを含む行の前に、 インデックスを含むエントリを出力するものである。

while (<>) {
     study;
     print ".IX foo\n" if /\bfoo\b/;
     print ".IX bar\n" if /\bbar\b/;
     print ".IX blurfl\n" if /\bblurfl\b/;
     ...
     print;
}

/\bfoo\b/ を検索する時は、 $_ 中の `f' の位置のみを調べる。 なぜなら、`f'`o' よりも稀だからである。 一般的に、特殊な場合を除いてこれは効果がある。 唯一の問題は、これにより最初に linked list を作るのにかかった以上に 時間を節約できるかどうかである。

注意:
実行時まで決定できない文字列を検索する場合は、 ループを全部文字列としてそれを eval することで 何回も全パターンをコンパイルし直すのを防ぐことができる。 これと合わせて、$/ を全ファイルが 1 レコードになるように undef すると、 大変速く、専用のプログラム fgrep よりも速いことが多い。

以下の例では ファイル群(@files) から単語群(@words) を検索し、 マッチするファイルの名前を出力する。

$search = 'while (<>) { study;';
foreach $word (@words) {
    $search .= "++\$seen{\$ARGV} if /\b$word\b/;\n";
}
$search .= "}";
@ARGV = @files;
undef $/;
eval $search;       # これは大変(this screams)
$/ = "\n";          # 通常の delimiter に戻す
foreach $file (sort keys(%seen)) {
    print $file, "\n";
}

tr/検索リスト/置換リスト/

`tr/SEARCHLIST/REPLACEMENTLIST/cds'
`y/SEARCHLIST/REPLACEMENTLIST/cds'

SEARCHLIST に指定した全ての文字を、 REPLACEMENTLIST にしたがって変換する。 置換もしくは削除した文字数を返す。 =~!~ を使って文字列を指定しなかった場合は、 $_ 文字列が変換される。 (=~ を使って指定する文字列はスカラー変数、配列の 1 要素、 またはこれらへの代入でなくてはならない。即ち、左辺値。)

sed 信者のために、ytr の別名としてある。

修飾子 d を用いると、 REPLACEMENTLIST は常に指定したそのものとして解釈される。 それ以外の場合で、 REPLACEMENTLISTSEARCHLIST よりも短い場合は、 同じ長さになるまで最後の文字が繰り返される。 REPLACEMENTLIST がヌルの場合は、SEACHLIST がコピーされる。

この後者は、あるクラスに含まれる文字をカウントしたり、 あるクラスの文字の連続を縮めたりするのに便利である。

$ARGV[1] =~ y/A-Z/a-z/;   # 小文字に統一する

$cnt = tr/*/*/;           # $_ 内の * を数える

$cnt = tr/0-9//;          # $_ 内の数字を数える

tr/a-zA-Z//s;             # bookkeeper -> bokeper

($HOST = $host) =~ tr/a-z/A-Z/;

y/a-zA-Z/ /cs;            # アルファベット以外を 1 文字のスペースに置換

tr/\200-\377/\0-\177/;    # 8 ビット目を消す

y/検索リスト/置換リスト/

`y/SEARCHLIST/REPLACEMENT/'

tr/検索リスト/置換リスト/ と同じ。前項を参照。

システム関数

alarm

`alarm(SECONDS)'
`alarm SECONDS'

指定した秒数(実際は 1 を引いたもの)が経過した後、 SIGALRM をプロセスに伝える。 つまり、 `alarm(15)' はそれから 14 秒以上経ったある時点で SIGALRM を起こす。

同時には一つのタイマーしかカウントできない。 コールする度に前のタイマーを使えなくするし、 また引数として 0 を与えると 新しいタイマーを開始せずに前のタイマーをキャンセルする。

返り値は前のタイマーに残っていた時間である。

chdir

`chdir(EXPR)'
`chdir EXPR'

成功なら 1、失敗なら 0。EXPR 省略時はホームディレクトリ。

chroot

`chroot(FILENAME)'
`chroot FILENAME'

同名のシステムコールと同じ。 成功/失敗により true/false が返る。 FILENAME が省略された場合、$_chroot する。

die

`die(LIST)'
`die LIST'

eval の外では、LIST の値を STDERR に出力し、 現在の $! (errno) で exit する。

もし $! が 0 なら、 ($? >> 8 ) (`command` のステータス) で exit する。 もし ($? >> 8 ) が 0 なら、255 で exit する。

eval の中では、エラーメッセージが $@ に入り、 eval が undefined value で終了する。

die "Can't cd to spool: $!\n"
    unless chdir '/usr/spool/news';
  
chdir '/usr/spool/news' || die "Can't cd to spool: $!\n"

EXPR の値が改行で終わらない場合は、 スクリプトの現在の行番号および(もしあれば)入力行番号も表示され、 改行が付け加えられる。

ヒント: メッセージに `, stopped' を付け加えておくと、 `at foo line 123' が付け加えられた時によりわかりやすい。

die "/etc/games is no good";
die "/etc/games is no good, stopped";

はそれぞれ次のように出力する。

/etc/games is no good at canasta line 123.
/etc/games is no good, stopped at canasta line 123.

See section exit.

exec

`exec(LIST)'
`exec LIST'

LIST の中に 1 以上の引数がある場合、 または LIST が 1 以上の値を持つ配列の場合、 LIST 中の引数で execvp() をコールする。

スカラー引数が 1 しかない場合、 引数にシェルのメタキャラクターがあるかどうかチェックされる。 もしあれば、parse するために全引数が `/bin/sh -c' に渡される。 もしなければ、引数は単語毎に分けられ、execvp() にそのまま渡される。 この方が効率的だからである。

注意:
exec(および system)は出力バッファをフラッシュしないので、 出力を失わないために $| をセットする必要があるかもしれない。

exec '/bin/echo', 'Your arguments are: ', @ARGV;
exec "sort $outfile | uniq";

本当は第一引数を実行したくないが、 プログラムをだましてその名前で実行しているように見せたい時は、 本当に走らせたいプログラム名を変数に代入し、 その変数を LIST の前にコンマと共に指定すれば良い (こうすると LIST にスカラーが一つしかなくても、 LIST が常に複数の値を持っていると解釈される)。

$shell = '/bin/csh';
exec $shell '-sh';       # ログインシェルのふりをする

exit

`exit(EXPR)'
`exit EXPR'

EXPR を評価し、その値で直接 exit する。

        $ans = <STDIN>;
        exit 0 if $ans =~ /^[Xx]/;

EXPR を省略すると、status 0 で exit する。

See section die.

fork

`fork'

fork() コールを行う。親プロセスには子供のプロセス ID を返し、 子プロセスには 0 を返す。

注意:
両方のプロセスにおいてフラッシュされていないバッファは フラッシュされずに残るので、 だぶって出力されるのを防ぐには、 $| をセットする必要がある。

See section $| : write または print の後にフラッシュを行うか否か for $|.

getlogin

`getlogin'

(もしあれば)`/etc/utmp' から、現在の login を読んで返す。 ヌルの場合は、getpwuid を使うこと。

$login = getlogin || (getpwuid($<))[0] || "Somebody";

See section システムファイルからデータを得る関数.

getpgrp

`getpgrp(PID)'
`getpgrp PID'

指定した PID のプロセスグループを返す。 getpgrp(2) をインプリメントしていないマシンで使用すると 致命的エラーとなる。 EXPR を省略すると、現プロセスのプロセスグループを返す。

getppid

`getppid'

親プロセスのプロセス ID を返す。

getpriority

`getpriority(WHICH,WHO)'

プロセス、プロセスグループ、またはユーザの現在の priority を返す。 (getpriority(2) を参照のこと。) getpriority(2) をインプリメントしていないマシンで使用すると 致命的エラーとなる。

kill

`kill(LIST)'
`kill LIST'

リストで示されるプロセスにシグナルを送る。 リストの第一要素は送るべきシグナルでなければならない。 シグナル送信に成功したプロセスの数を返す。

$cnt = kill 1, $child1, $child2;
kill 9, @goners;

シグナルが負の場合、プロセスではなくプロセスグループを kill する。 (System V では、 負のプロセス番号はプロセスグループも kill するが、互換性はない。) シグナル名を指定してもよい。

setpgrp

`setpgrp(PID,PGRP)'

カレントプロセスグループを指定した値 PID にセットし、 カレントプロセスを 0 にする。

setpgrp(2) をインプリメントしていないマシンでは致命的エラーとなる。

setpriority

`setpriority(WHICH,WHO,PRIORITY)'

あるプロセス、プロセスグループ、 またはユーザのカレントプライオリティをセットする。

setpriority(2) をインプリメントしていないマシンでは 致命的エラーとなる。

(setpriority(2) を参照。)

sleep

`sleep(EXPR)'
`sleep EXPR'
`sleep'

EXPR 秒の間(EXPR を省略すると、永久に)スクリプトを停止する。 プロセスに SIGALRM を送ると interrupt できるだろう。 実際に停止した時間を返す。

おそらく alarmsleep を混在させることはできないだろう。 sleep()alarm() を用いてインプリメントされている場合が 多いからだ。

syscall

`syscall(LIST)'
`syscall LIST'

LIST の最初の要素で指定するシステムコールを行う。 残りの要素はシステムコールの引数として渡される。 インプリメントされていない場合は致命的エラーとなる。 引数は以下のように解釈される。

文字列に書き込まれるどんな結果でも受け取れるように、 文字列の長さを充分取るのはプログラマの責任である。 整数の引数が数字ではなく、数であるというコンテキストで解釈されていない場合は、 数であることを示すために 0 を足す必要があるだろう。

require 'syscall.ph'; # h2ph の必要があるかもしれない
syscall(&SYS_write, fileno(STDOUT), "hi there\n", 9);

system

`system(LIST)'
`system LIST'

`exec LIST' と全く同じことをするが、 違いは最初に fork を行い、 親プロセスは子プロセスが完了するのを待つ点である。

注意: 引数の処理は引数の数によって変わる。

返り値はプログラムの exit status で、wait() と同じである。
実際の exit value を得るには、256 で割る必要がある。

See section exec.

times

`times'
現在のプロセスおよび子プロセスのユーザ、 システムタイム(秒)を持つ 4 要素の配列を返す。

($user,$system,$cuser,$csystem) = times;

umask

`umask(EXPR)'
`umask EXPR'
`umask'

プロセスの umask をセットし、変更前の値を返す。 EXPR を省略すると、現在の値を返すだけである。

wait

`wait'

子プロセスが terminate するのを待ち、 死んだプロセスの PID、または子プロセスがない時は -1 を返す。 status は $? に返る。See section waitpid.

waitpid

`waitpid(PID,FLAGS)'

ある子プロセスが terminate するのを待ち、 死んだプロセスの pid を返す。 そのような子プロセスがなければ、-1 を返す。 ステータスは $? に返る。次のようなコードを実行すると、

require "sys/wait.h";
...
waitpid(-1,&WNOHANG);

どんなプロセスに対しても non-blocking wait を実行できる。 non-blocking wait は waitpid (2) または wait4 (2) の どちらかのシステムコールをサポートしているマシンでのみ実行可能である。

しかし、ある pidFLAGS を 0 にして wait するのは どこででもインプリメントされている。(perl は、 exit したがまだ perl スクリプトが取り入れ(harvest)していないプロセスの ステータス値を覚えておくことで、システムコールのエミュレートをする。)

warn

`warn(LIST)'
`warn LIST'

`die' のようにメッセージを STDERR に出すが、exit しない。

ネットワーク関数

accept

`accept(NEWSOCKET,GENERICSOCKET)'

同名のシステムコールと同じ。成功/失敗により true/false が返る。

bind

`bind(SOCKET,NAME)'

同名のシステムコールと同じ。成功/失敗により true/false が返る。

connect

`connect(SOCKET,NAME)'

同名のシステムコールと同じことをする。 成功すれば真を、そうでなければ偽を返す。 NAME はソケットに適切な型のパッケージアドレスでなくてはならない。 プロセス間通信の章の例を参照のこと。See section プロセス間通信.

getpeername

`getpeername(SOCKET)'

SOCKET コネクションの もう一方のパックされた sockaddr アドレスを返す。

# インターネットソケットアドレス
$sockaddr = 'S n a4 x8';
$hersockaddr = getpeername(S);
($family, $port, $heraddr) =
        unpack($sockaddr,$hersockaddr);

getsockname

`getsockname(SOCKET)'

SOCKET コネクションの こちら側のパックされた sockaddr アドレスを返す。

# インターネットソケットアドレス
$sockaddr = 'S n a4 x8';
$mysockaddr = getsockname(S);
($family, $port, $myaddr) =
        unpack($sockaddr,$mysockaddr);

getsockopt

`getsockopt(SOCKET,LEVEL,OPTNAME)'

リクエストされたソケットオプションを返す。 エラーがある場合には undefined が返る。

listen

`listen(SOCKET,QUEUESIZE)'

listen システムコールと同じことをする。 成功すれば真、そうでなければ偽を返す。プロセス間通信の章の例を参照。 See section プロセス間通信.

recv

`recv(SOCKET,SCALAR,LEN,FLAGS)'

ソケットからメッセージを受け取る。 ファイルハンドル SOCKET からLENGTH バイトのデータを受け取り、 SCALAR に格納する。 sender のアドレスを返す。エラーがあると、undefined value を返す。 SCALAR は実際に読み込んだバイト数に合わせてサイズが変わる。 同名のシステムコールと同じフラグを用いる。

send

`send(SOCKET,MSG,FLAGS,TO)'
`send(SOCKET,MSG,FLAGS)'

SOCKET にメッセージを送る。同名のシステムコールと同じフラグを使う。 コネクトしていないソケットに対しては、 メッセージを送る送り先 TO を指定しなければならない。 送った文字数を返す。エラーがあった場合は undefined を返す。

setsockopt

`setsockopt(SOCKET,LEVEL,OPTNAME,OPTVAL)'

リクエストされたソケットオプションをセットする。 エラーがあった場合には undefined を返す。 引数を送りたくない時には OPTVALundef を指定することができる。

shutdown

`shutdown(SOCKET,HOW)'

HOW で示す manner でソケットコネクションをシャットダウンする。 HOW は同名のシステムコールと同じように解釈される。

socket

`socket(SOCKET,DOMAIN,TYPE,PROTOCOL)'

指定した種類のソケットをオープンし、 ファイルハンドル SOCKET に結び付ける。 DOMAINTYPEPROTOCOL には 同名のシステムコールと同じものを指定する。 perl ライブラリファイルから手軽に適切な値を得るためには、 `sys/socket.h' に対して h2ph を走らせる必要があるかも知れない。

成功すれば真を返す。プロセス間通信の章の例を参照。 See section プロセス間通信.

socketpair

`socketpair(SOCKET1,SOCKET2,DOMAIN,TYPE,PROTOCOL)'

指定した DOMAIN に、 指定した TYPE の無名のソケットのペアを作成する。 DOMAINTYPEPROTOCOL は 同名のシステムコールと同じものを指定する。 インプリメントされていない場合は、致命的エラーとなる。 成功すれば真を返す。

System V IPC 関数

msgctl

`msgctl(ID,CMD,ARG)'

System V IPC 関数 msgctl を呼ぶ。 CMD&IPC_STAT である場合は、 ARG は変数でなければならず、これに msqid_ds 構造体が返ってくる。

ioctl と同様の値を返す。 すなわち、エラーがあれば undefined の値、ゼロの場合は `0 だが真'、 その他の場合は実際の返り値が返る。

msgget

`msgget(KEY,FLAGS)'

System V IPC 関数 msgget を呼ぶ。 メッセージキュー ID を返す。エラーがあれば undefined の値を返す。

msgsnd

`msgsnd(ID,MSG,FLAGS)'

System V IPC 関数 msgsnd を呼び、 メッセージキュー ID が ID のメッセージにメッセージ MSG を送る。 MSG の始まりはメッセージ型が long integer でなければならない (これは `pack("L", $type)' で作成できる)。 成功すれば真、エラーがあれば偽を返す。

msgrcv

`msgrcv(ID,VAR,SIZE,TYPE,FLAGS)'

System V IPC 関数 msgrcv を呼び、 メッセージキュー ID からのメッセージを受け取って 変数 VAR に最大メッセージサイズ SIZE で格納する。

注意: メッセージを受け取った場合、 メッセージ型は VAR に格納した最初のものになる。 また、VAR の最大サイズは SIZE + メッセージ型のサイズになる。

成功すれば真を返し、エラーがあれば偽を返す。

semctl

`semctl(ID,SEMNUM,CMD,ARG)'

System V IPC 関数 semctl を呼ぶ。 CMD&IPC_STAT または &GETALL なら、 ARG は変数でなければならず、 これに semid_ds 構造体またはセマフォ値の配列が返る。

ioctl と同様の値を返す。 すなわち、エラーがあれば undefined の値、ゼロの場合は `0 だが真'、 その他の場合は実際の返り値が返る。

semget

`semget(KEY,NSEMS,SIZE,FLAGS)'

System V IPC 関数 semget を呼ぶ。セマフォ ID を返す。 エラーの場合は undefined の値を返す。

semop

`semop(KEY,OPSTRING)'

System V IPC 関数 semop を呼ぶ。 これにより、signalingwaiting などの セマフォ処理を行うことができる。 OPSTRING は、 semop 構造体の配列を pack したものでなければならない。 semop 構造体は、 `pack("sss", $semnum, $semop, $semflag)'で作ることができる。 セマフォ処理の数は OPSTRING の長さで暗黙の内に指定される。

成功すれば真、エラーがあれば偽を返す。
例: 次のコードはセマフォ ID $semid のセマフォ $semnum を待つ。

$semop = pack("sss", $semnum, -1, 0);
die "Semaphore trouble: $!\n" unless semop($semid, $semop);

セマフォにシグナルを送るには、`-1'`1' に置き換えればよい。

shmctl

`shmctl(ID,CMD,ARG)'

System V IPC 関数 shmctl を呼ぶ。 CMD&IPC_STAT である場合は、 ARG は変数でなければならず、 これに shmid_ds 構造体が返ってくる。

ioctl と同様の値を返す。 すなわち、エラーがあれば undefined の値、ゼロの場合は `0 だが真'、 その他の場合は実際の返り値が返る。

shmget

`shmget(KEY,SIZE,FLAGS)'

System V IPC 関数 shmget を呼ぶ。共有メモリ ID を返す。 エラーがあれば undefined の値を返す。

shmread

shmwrite

`shmread(ID,VAR,POS,SIZE)'
`shmwrite(ID,STRING,POS,SIZE)'

System V 共有メモリセグメント ID に、 位置 POS から サイズ SIZE にわたって attach し、 copy in/out し、detach することで読み込み/書き込みを行う。

読み込みの際には、VAR は変数でなければならず、 読み込まれるデータが格納される。

STRING が短い場合は、 SIZE バイトを満たすためヌルが書かれる。

成功すれば真、エラーがあれば偽を返す。

システムファイルからデータを得る関数

以下の * の部分には、各システムファイルに対応して、

/etc/passwd      →    pw
/etc/group       →    gr
/etc/hosts       →    host
/etc/networks    →    net
/etc/protocols   →    proto
/etc/services    →    serv

がそれぞれ入る。

これらのルーチンはシステムライブラリ内の同様の関数と同じ動作をする。 get ルーチンの返り値は以下の通りである。

($name,$passwd,$uid,$gid,
   $quota,$comment,$gcos,$dir,$shell) = getpw...
($name,$passwd,$gid,$members) = getgr...
($name,$aliases,$addrtype,$length,@addrs) = gethost...
($name,$aliases,$addrtype,$net) = getnet...
($name,$aliases,$proto) = getproto...
($name,$aliases,$port,$proto) = getserv...

getgr... が返す値 $members は グループのメンバーのログイン名のリストをスペースで区切ったものである。

gethost... が返す値 @addrs は 対応するシステムライブラリをコールして得られる raw address のリストである。 Internet の domain では、各アドレスは長さ 4 バイトで、 次のようにして unpack できる。

($a,$b,$c,$d) = unpack('C4',$addr[0]);

その他の関数

caller

`caller(EXPR)'
`caller'

サブルーチンコールの現在のコンテキストを返す。

($package,$filename,$line) = caller;

EXPR を指定すると、 デバッガがスタックトレースを出力するために使用する情報も返す。 EXPR の値が、 現在のサブルーチンの前に call フレームがいくつあるかを示す。

defined

`defined(EXPR)'
`defined EXPR'

左辺値 EXPR が real value を持つかどうかを示す boolean 値を返す。 ファイルの終わり、初期化されていない変数、 システムエラーなどの例外的な状況では、define されていない値を返す操作が多い。 この関数は本当のヌル文字列を返すかも知れない操作について、 define されていないヌル文字列と define されているヌル文字列を区別してくれる (特に配列の要素を参照する操作について)。

また、配列やサブルーチンが存在するかどうかチェックすることもできる。 予め define されていない変数を使用しても、期待された動作は保証されない。

print if defined $switch{'D'};
print "$val\n" while defined($val = pop(@ary));
die "Can't readlink $sym: $!"
     unless defined($value = readlink $sym);
eval '@foo = ()' if defined(@foo);
die "No XYZ package defined" unless defined %_XYZ;
sub foo { defined &$bar ? &$bar(@_) : die "No bar"; }

See section undef.

dump

`dump LABEL'

ただちにコアダンプする。 そもそもこの機能はコアダンプから undump プログラムを使って 実行可能なバイナリ(プログラムの先頭であらかじめ変数が初期化されている)を 作ることができるようにしたものである。 できたバイナリを実行すると `goto LABEL' を最初に実行する (goto がもつ制限は全て適用される)。

dump は コアダンプをはさんだ goto + 再スタート と考えればよい。 LABEL を省略すると、プログラムの先頭から再スタートする。

警告: dump の時点でオープンされていたファイルはすべて プログラムが再生した時にはオープンされない (perl の側からみると混乱するため)。 -u オプションも参照のこと。See section コマンドラインオプション.

#!/usr/bin/perl
require 'getopt.pl';
require 'stat.pl';
%days = (
    'Sun',1,
    'Mon',2,
    'Tue',3,
    'Wed',4,
    'Thu',5,
    'Fri',6,
    'Sat',7);

dump QUICKSTART if $ARGV[0] eq '-d';

QUICKSTART:
 do Getopt('f');

local

`local(LIST)'

リストアップした変数を、 括弧で囲まれた ブロック・サブルーチン・evaldo にローカルであると宣言する。リスト中の全要素は左辺値でなければならない。

localLIST 中の変数の値をスタックに保存し、 ブロック・サブルーチン・eval から抜ける時に元に戻す。 このため、呼ばれたサブルーチンではローカル変数は参照できるが、 グローバルな変数は参照できないことになる。

LIST は希望により値を代入することができる。 これによりローカル変数を初期化できる。 (ある変数について初期化を指示しない場合、値はundefined で作成される。) 通常、サブルーチンへのパラメータに名前を付けるのに用いる。

sub RANGEVAL {
     local($min, $max, $thunk) = @_;
     local($result) = ";
     local($i);

     # $thunk は $i を参照すると仮定している

     for ($i = $min; $i < $max; $i++) {
          $result .= eval $thunk;
     }

     $result;
}

if ($sw eq '-v') {
    # グローバルな配列でローカルな配列を初期化
    local(@ARGV) = @ARGV;
    unshift(@ARGV,'echo');
    system @ARGV;
}
# @ARGV は保存される

# 連想配列に一時的に数字を付加する
if ($base12) {
     # (注意: これが効率がよいわけではない!)
     local(%digits) = (%digits,'t',10,'e',11);
     do parse_num();
}

注意:
local() は run-time コマンドであり、ループでは毎回実行される。 このためループから抜けて解放するまで、毎回スタックを消費する。

q

`q/STRING/'
`qq/STRING/'
`qx/STRING/'

これらは本当の関数ではなく、単なるシンタックスシュガーであり、 引用する文字列に たくさんのバックスラッシュを入れなくてもすむようにするためのものである。 q は一般化されたシングルクォートであり、 qq は一般化されたダブルクォートである。 qx は一般化されたバッククォートである。

/ の代わりに 改行を含むアルファベット・数字でない任意の文字を delimiter として使える。 delimiter が ( または { の場合は、 最後の delimiter は対応する )} となる。 ( )} が文字列に埋め込まれる場合は 従来通りバックスラッシュをつける必要がある。)

    $foo = q!I said, "You said, 'She said it.'"!;
    $bar = q('This is it.');
    $today = qx{ date };
    $_ .= qq
*** The previous line contains the naughty word "$&".\n
    if /(ibm|apple|awk)/;      # :-)

require

`require(EXPR)'
`require EXPR'
`require'

EXPR、 または EXPR が指定されていない時は $_ で示される ライブラリファイルをインクルードする。 次のサブルーチンと同じ意味がある。

sub require {
    local($filename) = @_;
    return 1 if $INC{$filename};
    local($realfilename,$result);
    ITER: {
     foreach $prefix (@INC) {
        $realfilename = "$prefix/$filename";
        if (-f $realfilename) {
        $result = do $realfilename;
        last ITER;
        }
     }
     die "Can't find $filename in \@INC";
    }
    die $@ if $@;
    die "$filename did not return true value" unless $result;
    $INC{$filename} = $realfilename;
    $result;
}

注意: 同じ名前ではファイルを二度インクルードすることはできない。 See section @INC : perl スクリプトを探す場所のリスト for @INC.

reset

`reset(EXPR)'
`reset EXPR'
`reset'

通常、ループの最後の continue ブロックの中で、 変数を clear し、?? search をリセットして 再び使用可能にするために用いる。

EXPR は文字のリストとして解釈される(ハイフンは range を考慮する)。 この文字のどれかで始まる変数および配列は全て元の状態にリセットされる。 EXPR を省略すると、 one-match search (?pattern?)が match に再リセットされる。 カレントのパッケージ内の変数・検索のみをリセットする。 常に 1 を返す。See section ?パターン?.

reset 'X';      # reset all X variables
reset 'a-z';    # reset lower case variables
reset;          # just reset ?? searches

注意:
`A-Z' でリセットするのは勧められない。 なぜなら、配列 ARGVENV の内容を消すからである。 dbm 連想配列をリセットしても dbm ファイルを変更しない。 (が、perl がキャッシュした全エントリをフラッシュすれば、変更する。 こうすれば、dbm ファイルを共有している時に便利である。 便利でないかも知れないが。)

scalar

`scalar(EXPR)'

EXPR を強制的にスカラーのコンテキストで解釈させ、その値を返す。

undef

`undef(EXPR)'
`undef EXPR'
`undef'

EXPR(左辺値でなくてはならない)の値を undef する。

スカラー値、配列すべて、サブルーチン名(& を用いる) に対してのみ用いること。 (undef はおそらく定義されている変数や dbm 配列値の多くについて 期待する動作をしないであろう。) 常に undefined value を返す。 EXPR を省略しても良いが、この場合何も undefine されず、 例えばサブルーチンから返る時に undefined value を得ることができる。

undef $foo;
undef $bar{'blurfl'};
undef @ary;
undef %assoc;
undef &mysub;
return (wantarray ? () : undef) if $they_blew_it;

wantarray

`wantarray'

現在実行中のサブルーチンのコンテキストが配列値を要求していれば true を返す。 コンテキストがスカラーを要求していれば false を返す。

return wantarray ? () : undef;

Go to the previous, next section.