Algorithm::Cluster

Algorithm::Clusterはちょっと面白そうかな。 まだちゃんといじってないからなんともいえんがexsample動かしてみた限りでは読みやすいし、出力もよさげな感じ。そして、Rを動かすよりも速い気がする。

マニュアルはココとかココ

発現プロファイルとかというよりは、文書中の単語の頻度プロファイルとか比べたりとか、タグを持っている文書群缶の距離を調べてそれを図にしたりとか。まぁそれってPCAでいいような気もするが。

SOMとかk-means clusteringが出来るのも嬉しいかも。あー試してみたい。

うーん。となると、データ収集のためのインフラが欲しいナァ。

perl - 勝手に添削は勉強になる

夕方、探しに本屋にいったんだけど、悲しいかな、ここは田舎。さすがにまだ発売されてなかった。でもvol31が置いてあったのでパラパラめくって帰ってきた。はやくこっちでも発売されんかな。

404 Blog Not Found:perl - 勝手に添削 - WEB DB Press Vol.32 pp.94

Damianも言っていたように、「ソースコードは未来の自分へのラブレター」なのだ。

上の勝手に添削エントリは勉強になった。

まずは定数の扱いから。オリジナルではuse constantを使っていたが、これは駄目である。use constantの「定数」は、実は定数を返すsubなので、sigil ($@%&*)が定数から消えてしまう。

PerlBestPracticeでもReadonly使えって書いてあったけど、理由がようやくわかった。ついでに両方ソースを眺めといた。TIE(SCALAR|ARRAY|HASH)の

my $whence = (caller 2)[3];    # Check if naughty user is trying to tie directly.

ここのとこがイマイチわかってないのであとでちゃんと調べる。

いつuse CGI qw/:standard/を使うかというのは、実はnon-trivialな質問なのだけど、このようにCGIモジュールの中だけで文字列生成が完結する場合には、use CGI qw/:standard/などを使って余計な$q->を省き、テンプレートなどを使って処理が別になっている場合は、$qを使って処理を渡すというのがきれいかつわかりやすい切り分けだと思う。

恥ずかしながら、use CGI qw/:standard/の使い方を初めて知った。昔から使ってるけど、そのころはperldoc読めなかったしナァ。

@data{@attrs} = @args{@attrs}

Perl Best Practicesがおもろいので、良書と噂のこれも読んでみてますヨ。

ProductName オブジェクト指向Perlマスターコース―オブジェクト指向の概念とPerlによる実装方法
ダミアン コンウェイ
ピアソンエデュケーション / ?円 ( 2001-02 )


のp.402で、こんなもんが

my ($class, %args) = @_;
my %data;
@data{@attrs} = @args{@attrs};

わからん ?!

そういえば、オーこれは!と思ってブックマークしてたっけなとか思い出したので探し出してきた。

のみまくし日記 - 配列を一気にハッシュへ変換

my %member;
@member{qw(name age)} = qw(takefumi 23);
print Dumper %member;

これやね。

Prototype ( デザパタPerl )

今回はperlのモジュール使って書いたヨ、というわけではなくインスタンスのコピーってどうやってつくんの?っていう話題だ。

naoyaのはてなダイアリー - prototype.js でデザインパターン - Prototype

登録されてるインスタンスを連想配列から取り出して返却するのですが、そのときにそのまま取り出して返却するんではなく、インスタンスに実装されてる createClone() を呼び出して返却すると。createClone() の中ではインスタンスのコピーが行われます。

で、PerlサンプルのProduct.pmみてみると

sub clone {
    my $self = shift;
    my $class = ref($self);
    bless {%{$self}}, $class;
}

sub createclone {
    my $self = shift;
    return $self->clone;
}

{%{$self}}がさっぱしわからん。なんでこれでインスタンス(ハッシュのリファレンス)のコピーが出来んの?

ってことを追求だ。

まず、インスタンスが異なるのかどうか、リファレンスをプリントして確認するためにmain.plをいじくる。

use strict;

use Manager;
use UnderlinePen;
use MessageBox;

my $manager = Manager->new;
my $upen = UnderlinePen->new('~');
$manager->register("strong message", $upen);

my $p11 = $manager->create("strong message");
my $p12 = $manager->create("strong message");

print $p11,"\n";
print $p12,"\n";

で実行。

$ perl main.pl 
UnderlinePen=HASH(0x8dc6604)
UnderlinePen=HASH(0x8dc78dc)

おー、かわっとる。うーん、、、、、

素直に考えると

  • $selfが%{$self}でリファレンスからハッシュへ
  • それをさらにbless {%{$self}},$classで無名ハッシュでブレスして戻す
  • だから、コピーされてる

んだろうなぁと思うんだけど。

試しにProduct.pmのcloneメソッドをこんな感じで変えてみる。

sub clone {
       my $self = shift;
       my $class = ref($self);
       bless \%{$self}, $class;
}

でさっきとおなじmain.plを実行

$ perl main.pl 
UnderlinePen=HASH(0x8491eb0)
UnderlinePen=HASH(0x8491eb0)

同じリファレンスだ。

ということはreturnされるときにコピーされるのかなぁ。うーん結局わからん。無名ハッシュ生成のメカニズムあたりをちゃんとチェックすれば解決するのか?

こういうメモリまわりを追っかける場合ってperl -dすればいいのかなぁ。

060412 追記

オブジェクト指向Perlマスターコースの3章に書いてあった

ProductName オブジェクト指向Perlマスターコース―オブジェクト指向の概念とPerlによる実装方法
ダミアン コンウェイ
ピアソンエデュケーション / ?円 ( 2001-02 )


refを使ってオブジェクトの型を調べつつ、新しく生成したオブジェクトをハッシュ間の単純代入をするといいらしい。

%{objref2 = ref($objref1)->new()} = %{$objref1}

だから、こんな感じでオブジェクトはコピーできるそうなんだ。

このエントリは結城浩さんの本と、それに載っているサンプルをPerlで書いた例をみながら考えたことをメモってます。あとは、はてなの伊藤さんのjavascriptでの例も参考にしてます。 間違いの指摘とか、もっといいやり方教授してくれたらとても嬉しいゾ。

ProductName 増補改訂版Java言語で学ぶデザインパターン入門
結城 浩
ソフトバンククリエイティブ / 3990円 ( 2004-06-19 )


XML::RSSで

XML::RSSでCDATAセクション埋め込むときは

my $rss = XML::RSS->new(encode_output => 0);

とencode_outputを0にしてやる。

YAPC行ってきたヨ (2)

楽だ

XSの話とCatalyst関連の話題が面白かった。XSのサンプルは後でいじってみる。科学技術計算系のゴリゴリやるやつはやっぱCとか書けるようにしといたほうが幅が出ていいのかナァなんて思っているのでこれをきっかけに少し頑張ってみるかな。

Catalystは最近プラグインつくってみたかったりするので今日の話はなるほどなところが多くて参考になった。

Larry WallのKeynoteは面白かったが、深すぎてついていけないところが多々あった。

ヤップク

そして、気になるといえばYAPC::Asia 2006 Tokyoも気になる。面子が、、、、

豪華すぎ

とってもとっても行きたいが平日なんだよね。

でYAPCの読みなんだけど、「ヤップクニセンロク」って勝手によんでるんだけどホントはどう読むのが正しいのだろか?

追記060330

ヤップシーって読むそうです。

  • × ヤップク
  • ○ ヤップシー

あとKwikiをケーウィキとよんでたんだけどクウィキって読むみたい。

Catalystのアクションの優先度(2)

Catalystのアクションの優先度でまたもはまったのでメモ。

最上位のコントローラー(要するにcatalyst.plでつくられる)にRegexでアクションを定義すると、script/xxxx_create.pl controller test とかでlib/Controllerの下に作成したtest.pmのデフォルトよりも優先されてしまう。

例えば

lib/Test.pm

sub Regex : Regex('^(¥w+)$'){ my ( $self, $c ) = @_; # Hello World $c->response->body($c->req->snippets->[0]); }

lib/Test/Controller/priv.pm

sub default : Private { my ( $self, $c ) = @_; $c->response->body( "Test::Controller::priv" ); }

とかやっておいて、/privにアクセスするとRegexが実行されてしまう。

色々悩んだ挙句、

sub priv : Path('/priv'){ my ( $self, $c ) = @_; $c->response->body( "Test::Controller::priv" ); }

みたいに、Pathでルートからの位置を指定して優先度をあげることで解決。せっかくControllerで別にしてるんだから、

コントローラー内のデフォルトはコントローラー内ではデフォルトの動作をしてほしいナァ

Regexに持ってかれちゃったりすると気持ち悪いなぁと思ったり。

あと試行錯誤してて気づいたんだけど最上位のコントローラーでLocalRegexを指定すると何にもマッチしないようなんだけどこの認識であってるのかな?

Template Method ( デザパタPerl )

naoyaのはてなダイアリー - prototype.js でデザインパターン - Template Method

Iterator と Adapter では interface に相当するものは省略してきましたが、今回は抽象クラスをちゃんと用意します。JavaScript での interface みたいなものは Perl とかと一緒で実質意味を持ちませんが、抽象クラスなら実装がスーパークラスにちょこっとあるので意味があります。

Perlのコードだと、これのことか。

sub display {
    my $self = shift;
    $self->open;
    for my $i (0..4) {
        $self->print;
    }
    $self->close;
}

なるほど。そうすると抽象クラスでopen,print,closeメソッドでdieしておくことに意味があるのかも。でも、javaにはあるfinal修飾子がperlにはないから、オーバーライドされてしまうという危険性は残るよなぁ。

このエントリは結城浩さんの本と、それに載っているサンプルをPerlで書いた例をみながら考えたことをメモってます。あとは、はてなの伊藤さんのjavascriptでの例も参考にしてます。 間違いの指摘とか、もっといいやり方教授してくれたらとても嬉しいゾ。

ProductName 増補改訂版Java言語で学ぶデザインパターン入門
結城 浩
ソフトバンククリエイティブ / 3990円 ( 2004-06-19 )


Class::HPLOO

Statistics::Rが気に入らなければ、少し手を入れれば的ナ発想で眺めてみると、

なんじゃこりゃ、さっぱりわかりませんぞ?

なコードだったんですヨ。ヘッダーみたら、Class::HPLOOというモジュールで書かれたコードっぽいのでちょっくらググってみるとJava風にPerlのクラスを定義するシンタックスを提供するクラスだそうだ。

extendsとか構文とかそこはかとなくjavaの香りがするような(しないような?) でも、Statistics::Rのコードはすっきりしていません。というのはモジュールをインストールするとbuild-hplooをというコマンドが一緒にインストールされて、それを通すとhplooがpmに変換されるらしい。その結果、非常に読みにくいコードが出来上がるわけで、Statistics::Rのコードはそれを通してあるのですヨ。

で、なんでそんなモジュールわざわざ使ってんのかな?とか思ったら作者一緒だったよ。