基本
たまに整理するけど、基本的にでたらめなメモ。
クォート
#'abc'
q{abc}
#"abc_$d"
qq{abc_$d}
#`uptime`
qx{uptime}
#(1, 2, 3)
qw{1 2 3}
#正規表現
qr/PATTERN/option
#/PATTERN/
m{PATTERN}
#s/PATTERN//
s{PATTERN}{}
#tr///
tr{}{}
数値
#四捨五入 my $res = int($num + 0.5); #サイコロ my $res = int(rand 6) + 1;
2進数/8進数/16進数
#2進数(先頭に0b) my $num_bin = 0b1111; #8進数(先頭に0) my $num_oct = 0777; #16進数(先頭に0x) my $num_hex = 0xFFFF;
#16進数→10進数
my $aaa = hex('fa7a');
#10進数→16進数
my $bbb = sprintf("%lx", '367156');
#文字→16進数
my $hex = unpack("H*", 'あ');
#asciiから
my $text = chr(29);
#asciiへ
my $ascii = ord('あ');
printf/sprintf
my $num = 37; my $formated = sprintf "%05d", $num; # --> 00037
#符号付き整数として解釈し、ゼロで埋めて8桁に %08d #浮動小数点として解釈し、小数点以下2位まで(ほぼ四捨五入=0.725が0.72499999…等) %.2f #文字列として解釈し、右詰めにしてスペースで埋める %5s #文字列として解釈し、左詰めにしてスペースで埋める %-5s #文字列として解釈し、右詰めにしてゼロで埋める %05s
配列
#要素数 my $count = @a; #最後の要素 my $last = $ary[-1];
#末尾に追加 push @ary, $a; #先頭を削除 shift @ary; #末尾を削除 pop @ary; #先頭に追加 unshift @ary;
my $first = shift @ary; my $last = pop @ary;
#スライス
my @res = @ary[3, 7];
my @res = @ary[0 .. 4];
#スライス(代入)
my @ary[2, 3] = ('b', 'c');
#splice(5要素目から3つ取得) my @res = splice @ary, 4, 3; #splice(5要素目に@addを追加) my @res = splice @ary, 4, 0, @add;
ハッシュ
#KeyとValueを入れ替え
%hash = reverse %hash;
#Keyの数
my @ary = %hash;
my $countPre = @ary;
my $count = $countPre / 2;
-or-
my $countPre = @ary = %hash;
-or-
my $count = scalar keys %hash;
#結合
my %ccc = (%aaa, %bbb);
#キーと値の削除
delete $hash{$key};
#キーの存在チェック
if(exists $hash{$key}){
}
#値の定義チェック(0は「定義」、undefは「未定義」)
if(defined $hash{$key}){
}
#ループ
foreach my $key(keys %hash){
}
foreach my $value(value %hash){
}
while( my($key, $value) = each %hash){
}
#キー順にループ
foreach my $key( sort {$hash{$b} <=> $hash{$a} } keys %hash ){
}
やり方
パスワード作成
sub makePassword{
my $num = shift;
my $pwd;
$pwd .= ('a' .. 'z', 0 .. 9)[int(rand(36))] while $num -- > 0;
return $pwd;
}
ヒアドキュメント中のプログラム
$out = <<HTML;
<html>
<head>
<title>${………}</title>
</head>
<body>
HTML
数字列とそれ以外の文字を"@"で分ける
my $text = 'あいうabcかきくdef'; $text =〜 s/(\D*)(\d+)(\D*)/$1@$2@$3/g;
文字変換
#すべて小文字へ $string =~ tr/A-Z/a-z/; #a-z以外の文字を削除 $string =~ tr/a-z//cd;
合計
$sum += $_ for @numbers;
substr
#先頭から2byte my $res = substr($a, 0, 2); #末尾5文字 my $res = substr($a, -5); #末尾5文字を削除 substr($a, -5) = ''; #末尾2byteを削除した残り my $res = substr($a, 0, -2); #先頭3文字を削除した残り my $res = substr($a, 3);
#19730307の場合 my $YY = substr $date, 0, 4; my $MM = substr $date, 4, 2; my $DD = substr $date, 6, 2;
grep
my @results = grep $expression, @inputList; my $count = grep $expression, @inputList;
my @results = grep $_ > 10, @in; my @results = grep /^\d$/, @in;
my @results = grep test($_), @in;
sub test{
…
return 1;
}
my @results = grep {…} @in;
#@inの前のカンマなし。{…}ではreturnは書かない。
#空要素削除 my @results = grep length $_, @in;
#空白要素削除
my @results = grep {
if(/^¥s+$/){
$_ = undef;
}
$_;
} @in;
map
my @results = map function($_), @in;
my @results = map {...} @in;
ソート
#ASCII
my @res = sort @list;
#数値
my @res = sort {$a <=> $b} @list;
#数値逆順
my @res = sort {$b <=> $a} @list;
#文字列
my @res = sort {$a cmp $b} @list;
#文字列逆順
my @res = sort {$b cmp $a} @list;
#インデックス値(ソート前の3番目はソート後には何番目?)
my @res = sort {$list[$a] <=> $list[$b]} 0 .. $#list;
#インデックス値(ソート前の3番目はソート後には何番目?)文字列
my @res = sort {$list[$a] cmp $list[$b]} 0 .. $#list;
ファイルを更新日時順にソート
古い順
my $dir = '/Users/officek/Desktop/test';
$dir =~ s/\/$//;
opendir DIR, $dir;
my @files =
map { $_->[0] }
sort { $b->[1] <=> $a->[1] }
map { [ $_, -M "$dir/$_" ] }
grep ( /^[^.]/, readdir DIR );
close DIR;
for my $file(@files){
my ($ss, $mm, $hh, $DD, $MM, $YY, $wday, $yday, $isdst) = localtime( ( stat qq|$dir/$file| )[9] );
$YY += 1900;
$MM ++;
printf "%s\t%d-%02d-%02d %02d:%02d:%02d\n", $file, $YY, $MM, $DD, $hh, $mm, $ss;
}
新しい順
sort { $a->[1] <=> $b->[1] }
変数
#Perlのバージョン(バージョン+パッチレベル/100) #use Englishした場合は、$PERL_VERSIONでアクセス可能。 $] #マッチング $`(前)←$&(そのもの)→$'(後) #実行中のファイル名 $0
マッチング
#後ろタブのある単語にマッチ($&にタブは含まれない) /\w+(?=\t)/ #後ろにbarがないfooにマッチ /foo(?!bar)/
#グループ化(後方参照用に記憶される) /Windows (Me|Xp)/ #後方参照を行なわないグループ化 /Windows (?:Me|Xp)/
($year, $month, $day) = (/^(\d\d\d\d)(\d\d)(\d\d)$/);
#下記よりも /a|b|c/ #下記の方が高速 /[abc]/
#マッチしたものが配列に入る my @match = ($text =〜 /^(\d+)\-(\d+)\-(\d+)$/);
#マッチした個数(例: タブの個数) my $count = ($text =~ tr/\t/\t/);
進数変換
#16進数→10進数
$dec = hex( 0x1AB );
#10進数→16進数
$hex = sprintf("%lx", 16);
#10進数→8進数
$oct = sprintf("%lo", 10);
#8進数→10進数
$dec = oct 10;
情報
#バージョン/パッチ情報等 $ perl -v
#モジュール検索 find `perl -e 'print "@INC"'` -name '*.pm' -print find `perl -e 'print "@INC"'` -name 'Jcode.pm' -print
特殊リテラル
#プログラムの論理的な終わり(この文字列以降は解釈されない) __END__ #現在のファイル名 __FILE__ #現在の行番号 __LINE__ #現在のパッケージ名 __PACKAGE__
__END__以降の行は<DATA>で読み込むことができる。
読み込み
#localで局所化して一気に読み込み
my $dat;
open IN, "<$in" or die "cat not open: $!";
{local $/; $dat = <IN>; }
close DAT;
リファレンス
調べる
ref $aaa; #返り値→SCALAR / CODE / ARRAY / HASH
スカラーのリファレンス/デリファレンス
#$scalar
my $ref = \$scalar;
#\$scalarのデリファレンス
${$ref}; $$ref;
配列のリファレンス/デリファレンス
#@aryのリファレンス
my $ref = \@ary;
#\@aryのデリファレンス
@{$ref}; @$ref;
#配列の要素へアクセス
${$ref}[1]; $$item[1]; $ref->[1];
#2次元、3次元なら
$ref->[1]->[3]->[0];
ハッシュのリファレンス/デリファレンス
#%hashのリファレンス
my $ref = \%hash;
#デリファレンス
my $name = ${$ref}{'name'}; $$ref{'name'}; $ref->{'name'};
#ハッシュ全体
my @key = keys %{$ref}; %$ref;
サブルーチンのリファレンス/デリファレンス
#⊂のリファレンス
$ref = \⊂
#デリファレンス
&{$ref}('yugo');
&$ref('yugo');
$ref->('yugo');
無名配列
my $fruits = ['pineapple', 'papaya', 'mango'];
#下記と同義
my $fruits;
{
my @secret_variable = ('pineapple', 'papaya', 'mango');
$fruits = \@secret_variable;
}
無名ハッシュ
my $ref_to_yugo_info = {
name => 'yugo',
hat => 'White',
shirt => 'Red',
};
#下記と同義
my $ref_to_yugo_info;
{
my %yugo_info = (
name => 'yugo',
hat => 'White',
shirt => 'Red',
);
$ref_to_yugo_info = \%yugo_info;
}
無名サブルーチン
my $ref_sum = sub{
my $total;
for my $num(@_){
$total += $num
}
return $total;
}
#使う
my $total = $ref_sum->( 1, 2, 3 );
リファレンスの中身
use Data::Dumper;
#リファレンスを渡す
print Dumper($ref);
#utf8対応
use Data::Dumper;
{ no warnings; package Data::Dumper; sub qquote { return shift; } }
$Data::Dumper::Useperl = 1;
print Dumper $k;
複数行コメントアウト
=for comment コメントアウトされる =cut
utf8対応
use strict; use warnings; #ソースがutf8 use utf8; use Encode; #IN/OUTをutf8 use open IO => ":utf8"; #標準出力をutf8 binmode STDOUT, ":utf8";
継承
use base qw/Yugo::Common Yugo::Html/;
メソッドのオーバーライド
sub speak{
my $class = shift;
$class->SUPER::speak(@_);
}
constant
use constant LIB_DIR => '/home/yugo/lib'; use lib LIB_DIR;
Perl with Macintiosh メモ
use Text::Iconv;
my $path = $ARGV[0];
#特殊なNFDなUTFから通常のUTF-8へ
my $path_nfc = Text::Iconv->new('UTF-8-MAC', 'UTF-8')->convert($path);
#UTF-8フラグが落ちてしまったので、再度たてる
my $path_nfc_flagged = Encode::decode('UTF-8', $path_nfc);
#まとめると以下
#$path = Encode::decode('UTF-8', Text::Iconv->new('UTF-8-MAC', 'UTF-8')->convert($path));
Windows ActivePerl メモ
ファイルの入出力は、UTF-8/LFにしたい。
ソースファイルは当然UTF-8にしたい。
use strict; use utf8; use open IO => ":unix:utf8"; #:unixでLFに、:utf8でUTF-8に。 binmode STDIN, ":crlf:encoding(cp932)"; binmode STDOUT, ":crlf:encoding(cp932)"; binmode STDERR, ":crlf:encoding(cp932)";
binmodeの指定は以下のようにしても。
map { binmode($_, ":crlf:encoding(cp932)") } qw/STDIN STDOUT STDERR/;
デバッグ
# 起動 perl -d test.pl
# ブレークポイント
$DB::single = 1;
# 条件付ブレークポイント
if ($num == 2) { $DB::single = 1 }
# 警告をキャッチしてブレークポイントしかける
$SIG{__WARN__} = sub {
$DB::single = 1;
};
- q : 終了
- n: 次の行実行
- s: 次のステップ実行(サブルーチンの中も)
- c: ブレークポイントまで実行
- c 5: 5行目の直前まで実行
- p $num: 変数の中身を表示
- x \%hash: 変数の中身を表示(リファレンス渡し)
- v: 周辺の行を表示
- .: 現在の行を表示
- (任意の文を実行させることも可能)
ホスト名の取得
use Sys::Hostname qw/hostname/; my $host = hostname();