タイトル/名前 | 更新者 | 更新日 |
---|---|---|
Perl/codepiece/manupilate_INC | msakamoto-sf | 2008-12-28 23:03:13 |
Perl/codepiece/flock01 | msakamoto-sf | 2008-12-28 23:01:35 |
Perl/codepiece/interface01 | msakamoto-sf | 2008-12-28 22:56:15 |
Perl/codepiece/count_array1 | msakamoto-sf | 2008-12-28 22:46:37 |
Perl/codepiece/OOPメモ | msakamoto-sf | 2008-12-28 22:44:29 |
日記/2007/06/11/"Linux Kernel in a Nutshell"PDF版 | msakamoto-sf | 2008-12-28 22:40:22 |
日記/2008/12/28/「開発現場の天国と地獄」第5回・6回@IT | msakamoto-sf | 2008-12-28 22:33:37 |
日記/2007/06/26/PHPのメモリ管理参考記事 | msakamoto-sf | 2008-12-28 22:10:26 |
日記/2006/01/14/Log4perlとかPerlでINIファイルを読むメモ | msakamoto-sf | 2008-12-28 20:30:46 |
日記/2006/01/05/PerlのテンプレートエンジンとかDBI/DBDとかメモ | msakamoto-sf | 2008-12-28 20:29:13 |
#!/usr/bin/perl use strict; use warnings; use File::Basename; # adjustment for include path (terminate with path separator) BEGIN { my (undef, $__base_dir, undef) = fileparse($0); # File::Basename push(@INC, $__base_dir); } use test::Test1; print $test::Test1::msg, "\n";
package test::Test1; use strict; use warnings; our $msg = "Hello, test::Test1!";
$ perl ./manip_inc01.pl Hello, test::Test1!
<?php $__basedir = realpath(dirname(__FILE__)); set_ini("include_path", get_ini("include_path").PATH_SEPARATOR.$__basedir); ...
use Fcntl(:flock); or use Fcntl(:DEAFULT :flock);
しておく必要がある。FcntlはシステムのCライブラリのfcntl.hをh2xsで取り込んで利用できるようにしてくれたモジュール。基本的に#defineされたものが取り込まれている。
以下、参考。
flockのperldocにもしっかり太字で記載されていますが、Perlのflockは"advisory"ロックです。つまり、flockを使用しているもの同士であればロックは機能しますが、flockを使用せずに読み書きを行うプロセスに対しては機能しません。
実際、下のコードピースを使うと明らかです。コードピース同士でのロックは、同じflockを使用しているので、排他ロックは「その通りに」動作します。(戻り値がそのように見えます。)
しかしechoやviなどの読み書きプロセスと同時に動かして実験してみると、Perl側でLOCK_EXをかけているのに、echoシェルリダイレクトでファイルに書き込めますし、viの編集も何の問題もなく上書き保存可能です。
Perl同士でしか読み書きしないCGIのロックファイルについては有効ですが、別のプログラミング言語やプログラムなどで同時に読み書きするときは、Perlのflockが機能しない場合も有る点に注意が必要です。
標準入力からLOCK_*を受付け、コマンドラインで指定されたファイルに対してflock操作を行う。
異なる端末から二つ以上立ち上げていろいろ遊んでみる事を想定。
ここではローカルファイルシステム上のファイルをロック・アンロックする実験を行いたい為、flockで問題ない。
ファイルロックの他に、標準入力からのreadlineやswitch構文、他参考リンク。
#!/usr/bin/perl use strict; use warnings; use Data::Dumper; use Switch; use Fcntl qw(:flock); if(@ARGV < 1) { die "usage: $0 <lock_file>\n"; } my $file = $ARGV[0]; my $lock_nb = 0; if(! -e $file ) { die "$file is not exist!\n"; } print "Lock target file is '$file'.\n"; ## 通常のファイルハンドルを使用した書き方 # open my $fh, "<$file" or die "Open failure '$file'.($!)\n"; ## IO::Fileを用いた書き方 my $fh = IO::File->new("+<$file"); # エラーハンドリングは$fhがdefinedか否かで判別する。 # エラーコードはシステムのerrnoなので $! を参照する。 die "Open file failure '$file' ($!).\n" unless defined($fh); sub help { my ($msg) = @_; print "unrecognized statement: $msg\n"; print "statement are: LOCK_SH, LOCK_EX, LOCK_UN, LOCK_NB.\n"; print "(LOCK_NB switches LOCK_NB mode.)\n"; } my $line = undef; for(;;) { undef $!; unless (defined($line = <STDIN>)) { # if reached EOF, break loop. die $! if $!; last; } if($line !~ /^([A-Z_]+)/ ) { &help($line); next; } switch($1) { my $ret = 0; case "LOCK_SH" { $ret = flock($fh, LOCK_SH | $lock_nb); print "LOCK_SH results $ret.\n"; } case "LOCK_EX" { $ret = flock($fh, LOCK_EX | $lock_nb); print "LOCK_EX results $ret.\n"; } case "LOCK_UN" { $ret = flock($fh, LOCK_UN); print "LOCK_UN results $ret.\n"; } case "LOCK_NB" { $lock_nb = ($lock_nb) ? 0 : LOCK_NB; print "LOCK_NB is ". (($lock_nb) ? "ON" : "OFF") . ".\n"; } else { &help($1); } } } # open my $fh の場合 #close $fh; # IO::File の場合 $fh->close;
JavaはC++はコンパイル時にinterfaceをチェックしてくれる。しかし、実行時にコンパイルされるPerlやPHPなどのスクリプティング言語の場合、interfaceが実装されていることの確認も実行時である。そのため、特に動的なローディングを用いている場合、本当にinterface、Perlの場合はサブルーチンが実装されているのか。実装されていない場合、どういう状況になるのかを前もって確認しておきたい。
#!/usr/bin/perl use strict; use warnings; use File::Basename; BEGIN { my (undef, $__base_dir, undef) = fileparse($0); push(@INC, $__base_dir); } use Hoge::Moge; print __PACKAGE__, " - 1\n"; &Hoge::Moge::moge(); print __PACKAGE__, " - 2\n";
package Hoge::Moge; use strict; use warnings; 1; __END__
$ perl -c ./test03.pl test03.pl syntax OK
$ ./test03.pl main - 1 Undefined subroutine &Hoge::Moge::moge called at test03.pl line 16.
このように、やはりコンパイル時はチェックされず、実行時に初めてチェックされ、エラーとなることが確認できた。
use interface (http://search.cpan.org/~swalters/interface-0.02/interface.pm)を使用すれば、コンパイル時にもチェックできるらしいが、BUGSには「Damian Conwayの書いたコードの殆どで動かない」とか、「mainパッケージには適用できない」とか書いてあって、一歩引いてしまう。
まあ、いくらコンパイル時にチェックできても、結局はそれも実行時ではあるので(*1)、まあ、これは しょうがないので諦める というのも一つの手である。
・・・これ、%SIG{DIE}で拾えないのかなあ?try-catchの実験の時に、リベンジしてみよう。
#!/usr/bin/perl use Data::Dumper; my @ary = (1, 2, 3, 4); print Dumper(@ary), "\n"; # 一昔前の入門書で見かけた配列サイズの取得方法。 # 正確にはサイズでなく、最後の添字を返す。 print "count = ", $#ary, "\n"; # PerlのCOP(Context Oriented Programming)を活かしたサイズの取得方法。 # Perlが勝手にスカラーに直す。このとき、Perl側で良い案配に配列サイズとして # 評価してくれる。 $sz = @ary; print "count = $sz\n"; print '4 > @ary = ', (4 > @ary), "\n"; print '4 == @ary = ', (4 == @ary), "\n"; print '4 < @ary = ', (4 < @ary), "\n"; print "\n"; # COPのおかげで、違和感のない見栄え。 for(my $i = 0; $i < @ary; $i++) { print @ary[$i], "\n"; } print "\n"; foreach my $i (@ary) { print $i, "\n"; }
$VAR1 = 1; $VAR2 = 2; $VAR3 = 3; $VAR4 = 4; count = 3 count = 4 4 > @ary = 4 == @ary = 1 4 < @ary = 1 2 3 4 1 2 3 4
Perlのコンテキスト判別のおかげで、エディタにとっても優しい書き方ができた。
PerlのOOPについてのメモ。
いろんなモジュールが公開されているが、2006 - 2007 の現状の潮流としては、Catalystが使用しているClass::Data::Inheritable, Class::Accessor など、というのと、Class::Std系列と、その他、の3種類くらいになっているようだ。
それぞれオブジェクト指向の要求に対する内部実装が違う為、相互共存できるのかは不安。
変数の内部隠蔽を徹底するのであればClass::Stdを用いることになるかも知れない。
内部隠蔽が徹底されなくとも良いので、Data::Dumperで普通にダンプできるクラスを、簡単に継承したいのであればCatalyst系の組み合わせになるのかも知れない。
いずれにしても、各モジュールは未実験。
過去のPukiWiki日記では 2005年11月01日の日記に書き留めていた記事。
当時の日記では、人員の適材適所の配置やフレームワークなどの基礎部分を手作りした点に感銘を受けていた。
今改めて読み直してみると、3年も前の記事なのに古さが全く感じられない。
・・・っていうか、先日ヘルプにピンポイントで放り込まれた現場がまさにこれの正反対。
まぁ基幹システムとの結合とかじゃなくて、お役所/一般公開共用のWebシステムなんだけど。
我ながら恥ずかしい話で、3年前の記事が未だに参考になるということは、3年前にこの記事を読んでおきながら、現場への適用をさぼっていたということで、情けない。
PHPメモリ管理の参考記事。
"Extending and Embedding PHP"( http://www.informit.com/store/product.aspx?isbn=067232704X )の著者である Sara Golemon による2006/07時点でのPHPメモリ管理の内部挙動解説。
http://www.informit.com/articles/article.aspx?p=516587
大変参考になる。
PerlからINIファイルを読み取らせてみるためにCPANを探してみる。
とか。
Log4perlとか。
Perlでメール送信しようと思った。で、メール本文で変数を埋め込みたい。
PHPでやるなら、Smartyでfetchしたのをmb_convert_encodingでISO-2022-JPに変換して、それをBODYに詰めるところなんだけど、Perlでそういったテンプレートは無いかと探す。
Template-Toolkitというのが、CatalystというPerlのMVC(というよりはRuby on Rails系?)のフレームワークでも利用されている様で、Name Valueが便利そうなのでこれにするか。
あと、DBのインターフェイスをまともにしたい・・・。というわけで、DBI/DBDを勉強してみたい。