1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Perl Cheet Sheet v5

Last updated at Posted at 2016-11-22

Perl v5 自分用メモ

とかくperlは書き方が自由すぎる。いちいち調べていたら、小さなプログラムでも書くのに時間がかかる。また、はまるポイントも色々ある。
そのため、ここに文法と注意点をまとめます。自分のメイン言語がJavaのため、たまに比較します。
言語としては「Perl」、実行プログラムとしては「perl」として、この記事を書いたつもりです。また、「変数」とだけ書いてある場合は、大抵スカラー変数のことです。

実行環境のperl

v5.18.2

TL;DR

  • メモです
  • 今更ですがv5のPerlです
  • Nothing new here

言語思想

実用性と多様性

コメント

  • 単一行コメント(#)
    # This is a comment
    さすがUNIX上での作業が発端となった言語、シェルスクリプトと同じですね。
  • 複数行コメント(=pod / =cut)
    =pod
    multi-line comments
    =cut

print

  • カッコで囲っても囲わなくても良い。
print
print "hello\n";
print ("hello\n");
  • printの直後にカッコがあると閉じタグでその行の解釈が終わる。
print
print (2 * 3) /2 ; # 結果は6
print (2 * 3 / 2); # 結果は3
print  2 * 3 / 2 ; # 結果は3

累乗計算

** 演算子が使える。

**
print 2 ** 3 ; # 8

JavaならMath.pow(2.0, 3.0)ですね。
正の平方根を返すsqrt()関数はPerlにもある。というか、Perlの方がJavaより古い。(Wikipedia調べ、Perl=1987/Java=1995)

ワンライナー

-eをつけて実行

one-liner
perl -e 'print 2 ** 3;' # 8

桁が大きな数の、科学技術表記が可能

エクセルみたいに、「1e+200」という表記ができる
「1e+200」は、10の200乗です。

インクリメントは前置・後置ともに実行可能

複数変数への同時代入の仕方

Multi-Variable
perl -e '$a = $b = $c = 5; print "$a $b $c\n";' # 結果:5 5 5

Javaだとこう書けない。int a = 5, b = 5 , c = 5; となる。

おまじない

use
use strict;
use warnings;
  • strict
    変数などを使う前に宣言を必要とする
  • warnings
    初期化していない変数にアクセスした場合などに警告を出す
    チェックする内容としては、perl -wオプションと変わらないみたですが、use warningsの場合は、記述したファイルに適用範囲が限定されるみたです。また、use strict "vars"; やuse strict;
    no strict "vars"; のように適用する対象を分けることもできる。
  • プラグマ(pragma)
    strictやwarningsなどはPerlプラグマと呼ばれる、機能拡張モジュールです。小文字でプラグマ名を書く慣習らしいです。

参照:PerlPlus 厳密な構文チェック
   perldoc.jp 5.12.3 strict
   Perl/ライブラリ・モジュールとオブジェクト指向

文字列結合

. (ピリオド、ドット)で結合する。複合代入演算子としても使える。(.=)
Javaは+, Excel関数だと&ですか。
Perlは動的に変数の型を決める(というか数値も文字列も許容する)ので、. と + で色々使い分けることが可能です。

concatnate
$a = "a" ; $b = "b"; $one = 1; $two = 2;
print $a . $b;     # ab
print $a + $b;     # 0
print $one + $two; # 3
print $one . $two; # 12

undef

use warnings使っていればお目にかからないとは思いますが、初期化されていない変数に設定されている値です。

undefの取り扱い

  • 数値としてみた場合は0としてふるまい
  • 文字列としてみた場合は""としてふるまう
    (引用元:すぐわかるPerl 47P)

判定式・条件式

Perlには真偽値という型はないらしく、次のコードのifブロックは実行されます。

false
if ( false ) { 
  print "実行されます\n"; 
}

Perlで偽と判定される文字列や数値

  1. undef
  2. "" (空文字)
  3. "0" (文字列のゼロ)
  4. 0 (数値のゼロ)

参照:PerlPlus 論理値(ブール値)

文字列の一致はeq , 数値の一致は==

:rotating_light:シェルスクリプトと混ぜるな危険!
シェルスクリプトだと、eq,ne,gt,lt,ge,leを数値比較に使います。
一方、Perlはeq,ne,gt,lt,ge,leを文字列比較に使い、数値比較には、==,!=,<,>,<=,>=を使います。

if ~ elsif ~ else

各言語によって、else ifだったりelsifだったりしますが、Perlはelsifです。

馴染みのある言語のif ~ elsif ~ else

Lang State
Perl if (条件式1) {~;} elsif (条件式2) {~;} else {~;}
Java if (条件式1) {~;} else if (条件式2) {~;} else {~;}
bash if 条件式1 ; then ~ ; elif 条件式2 ; then ~ ; else ~ ; fi
Excel VBA If 条件式1 Then

ElseIf 条件式2 Then

Else
~
End If
Python if 条件式1:
タブ~
elif 条件式2:
タブ~
else:
タブ~

※ Mac OS用のExcel持っていないのでおうちで試せてませんが、Excel VBAは改行が必要な気がします。
※ 左詰めした表の中にスペースが入らないので、苦肉の「タブ」

unless

英語の意味のとおり、「〜しない・〜でない限り」実行するブロック。つまり、条件式が偽の時に実行される。elseブロックを追加できて、unlessのelseブロックは条件式が真の時に実行される。
参照:PerlPlus unless文

unless
unless ( 2 == 1 ) { print "unless"; } # こちらが実行されます
else { print "unless else" }          

if ( 2 == 1 ) { print "if"; }         
else { print "if else"; }             # こちらが実行されます

多分、他言語では実装されていないことが多いので、チームでの読みやすさを考慮するとunlessは書かないほうがいのかなと感じました。ifのelseブロックを使うか、ifの条件式を反転(!)させることで代用できるので、unlessである必要性はない。まぁ、好み・宗教問題ですね。

reversedIf
if ( ! (2 == 1) ) { print "if"; }       # こちらが実行されます  
else { print "if else"; }          

※ !==より優先順位が高いので、は(2==1)というように()でくくらないと判定式を反転できない
※ (追記)notは==より優先順位が低いので、()で囲う必要がない

Pythonだとif notでunlessと同じことができるみたいです。
(参照:Chat-blog 【python】unlessがないのでnotを使う

論理演算子

& <=> &&, | <=> || の描きわけで、短絡評価するかどうかを書き分けることが可能。
&&, || は短絡評価(ショートカット)するので、true/falseを判定した時点で、もし右側に判定式が続いてても評価しない。Javaと同じ。

論理演算子の種類

上にあるほうが評価の優先順位が高い。

結合方向 演算子 
左結合 項(丸括弧で囲った部分) リスト演算子 (左方向に対して)
右結合 !
非結合 == != <=> eq ne cmp
左結合 &
左結合 | ^
左結合 &&
左結合 ||
右結合 = += -= *= などの代入演算子
右結合 not
左結合 and
左結合 or xor

デフォルト値を設定する

結論からすると、defined関数を使って、undefかどうかでデフォルト値を設定しましょう。

default
$result = defined $results{$name} ? $results{$name} : "not taken" ;

参照:blog 20100901 / Perl 「 論理演算子 」論理 OR を利用したデフォルト値の設定とその問題点 (0x8c)

公式ドキュメント日本語訳に下記のような例が載っていました。

$a = $b || $c;
引用:論理和と排他論理和

=(代入演算子)より||の方が評価優先順位が高いので、$bまたは$cの結果を$aに代入できます。||と=でもデフォルト値を設定することがように見えますが、$bが下記の値の場合、予期せず$cが評価される場合があるみたいです。

  • "" (空文字)
  • "0" (文字列のゼロ)
  • 0 (数値のゼロ)

or die

die関数はプログラムを終了させる関数で、orは上記にもある論理演算子です。
ファイルのオープン時に組み合わせます。
こちらの記事になぜ「||」ではいけないかがわかりやすく説明されています。

while

while
while ( 条件式 ) { 処理 }
  • last;でループを抜けることができる

foreach

foreach
foreach $val ( @array ) { $valを使った処理; }

Javaとは違うのだよ、Javaとは。
for (データ型 変数名: コレクション) { 変数を使った処理; }

コアダンプ

coreという名前のファイルを出力しプログラムが異常終了すること。

メソッド(関数)一覧

メソッド名 動作 使い方
print 数値や文字列を出力する print "hogehoge";
last ループブロックの終了 last;
defined 引数がundefの場合、偽を返す $result = defined $results{$name} ? $results{$name} : "not taken" ;
die プログラムを終了させる リストを引数に取る
改行でdie関数が終わらない場合は、エラー位置を示すエラーメッセジが挿入される
eval 引数をperlで一度処理する
{}で囲うと一度変換する
※実行と変換は違う
eval 1+3; # 4
$temp = "1+2";
eval $temp; # 3
eval { $temp }; # 1+2

リスト

  • リスト=()で囲んだ複数の値を持つブロック ※ カンマ区切り
  • リストを用いることで中間変数が不要になるケースもある
    ($one, $two ) = ($two, $one)
  • スカラー変数のリストに代入する際、右側の個数が足りない時は、undefとなる
  • x..y を使うことで、xからyまでの数値リストとなる(x,yを含む整数値のリスト)
list
($one, $two, $three) = ( 1, 2 );
print "$one $two $three \n"; # 1 2 

配列

array
# 要素を一つずつ初期化する
$student[0]="tanaka";
$student[1]="suzuki";

# 要素をまとめて初期化する
@animals = ("panda", "kirin" );

# whileでアクセスする
$count = 0;
while ( $count < $#student + 1) {
  print $student[$count]. "\n";
  $count++;
}

# foreachでアクセスする
foreach $animal ( @animals ){
  print $animal . "\n";
}
  • 配列の要素数は動的に変化する
  • スカラー変数を格納している配列をリストに入れると展開される
  • @配列名は2通りの意味を持つ(リストコンテキスト,スカラーコンテキスト)
    • リストを代入する・リストに代入する・配列同士を代入する・printで@配列名のみでアクセスする
    • スカラー変数に代入する・数値と比較する・数式の一部として使う
  • $array[3] = 3;のように書いた場合
    • $array[0]から$array[2]はundefの状態で配列が作成される
  • $#配列名は最後の要素のインデックスを格納する
  • $配列名[-x]で末尾から要素を数えてアクセスできる  
    • $配列名[-1] = 最後の要素   
    • $配列名[-3] = 最後から3つ目の要素
  • 要素の指定
    • [0,1,2]
    • [0..2]

コマンドライン引数へのアクセス

  • 引数は文字列のリストとして認識される
  • $ARGV[0]
  • (シェルの話ですが)シングルクオートで囲まないと*(アスタリスク)へはアクセスできない

参照情報

参考書籍・Webサイト

perldoc.jp
すぐわかるPerl 初版第7刷

スカラーとベクトル

スカラー = 値を一つ持つ量
ベクトル = 値を複数持つ量

1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?