cperl-modeの配列、ハッシュ、配列ref、ハッシュrefのインデントスタイル

emacs cperl-modeで、複数行にまたがる配列、ハッシュ、配列ref、ハッシュref定義の
インデントがwhileや関数定義と同様のインデントスタイルになるようにしたい。


whileや関数定義と同様に

    while ($some_cond) {
        somefunc1();
        somefunc2();
    }

以下のようなスタイル定義にしたい。

    my @sample_array = (
        1, 5, 6,
        7, 8 ,9,
    );

    my $sample_href = {
        abc => 1, def=>2,
        ghi => 3,
    };

こうなるのがいや。

    my @sample_array = (
                        1, 5, 6,
                        7, 8 ,9,
                       );

[linux][network][tool] nettop

yum install nettop

networkの統計データをtopの用に表示してくれる

sudo /usr/bin/nettop

  %pkts  total    %size   total   sz/pkt    bit/s                          type
100.00%  284.0   100.00%   62.5k     225    12.8k           total
 71.12%  202.0    88.57%   55.3k     280    11.9k           |-ipv4
 36.26%  103.0    73.33%   45.8k     455     8.5k           | |-tcp
 30.98%   88.0    71.92%   44.9k     522     8.5k           | | |-ssh
  3.52%   10.0     0.93%  600.0       60     0.0            | | |-1025
  1.76%    5.0     0.46%  300.0       60     0.0            | | `-135
 31.69%   90.0    13.95%    8.7k      99     2.6k           | |-udp

結構便利

[perl] mapではまり中

二つの違いがよく分からない

0が返るときと返らないときの違いは何?

perl -le 'print map { $_ if (!$seen{$_}++) } qw(1 1 2 2);'
12
perl -le 'print map { $_ if ($_%2) } qw(1 1 2 2);'
1100


分かった! 単純に論理否定(!)演算子が値を返さないからだ

$ perl -le 'map {print !$seen{$_}++ } (2, 2, 1, 1);'
1

1

結論:空配列 () を返すのが無難。

 perl -le 'print map { !$seen{$_}++ ? $_:() } (2,2,1,1)'

[perl] プロセスグループの殺し方

コマンド起動プロセス以外のプロセスから子供含めて殺したい場合

1. 該当プロセスをプロセスグループリーダにしておく

 setpgrp(0,0);

2. 子プロセスなどを生成
3. 新しく作成したプロセスグループにシグナルを送出

   kill SIGNALNAME, -$$ # プロセスグループリーダにて

プロセスグループのpidは、リーダプロセスのpidにマイナスをつけた価になる。


実は、0に送れば、属しているプロセスグループ全体にシグナルを送ることができる。
これでもOKだが乱用すると間違って親プロセスを殺しかねないので注意。

  kill SIGNALNAME, 0

Ctrl-Cで送出するsignalの動作確認

Ctrl-Cだとプロセスグループ(リーダプロセスとその子供達)にSIGINTを送る。

$ perl get_signal.pl
fork child=24151 parent=24150
#Ctrl-Cを押す
get signal INT in 24150
get signal INT in 24151

これは、kill -INT -24150とした場合と同じ。
kill -INT 24150だと、24151にはSIGINTが伝わらない。

$ perl get_signal.pl
fork child=24151 parent=24150
get signal INT in 24150
get signal INT in 24151


src: perl get_singal.pl

#!/usr/bin/perl
use strict;
use warnings;

for my $sig (qw(TERM INT HUP KILL)){
  $SIG{$sig} = sub {
    print "get signal $sig in $$\n";
    exit(1);
  };
}

my $pid = fork;

if ($pid){
  print "fork child=$pid parent=$$\n";
}

while(1){}

[perl] mapで条件によってgrepの用に値をとばす。

空の配列 () を返せば、skipされる。

$ perl -e '@a = map { ($_%2) ? 1: () } (1..5);print "values=".join(",",@a)."\n"; print "count=".scalar @a."\n"'
values=1,1,1
count=3

0, undef, ""ではだめ。どれもその値になる。

[kenshin@house4 ~]$ perl -e '@a = map { ($_%2) ? 1: 0 } (1..5);print "values=".join(",",@a)."\n"; print "count=".scalar @a."\n"'
values=1,0,1,0,1
count=5
[kenshin@house4 ~]$ perl -e '@a = map { ($_%2) ? 1: undef } (1..5);print "values=".join(",",@a)."\n"; print "count=".scalar @a."\n"'
values=1,,1,,1
count=5
[kenshin@house4 ~]$ perl -e '@a = map { ($_%2) ? 1: "" } (1..5);print "values=".join(",",@a)."\n"; print "count=".scalar @a."\n"'
values=1,,1,,1
count=5

何もしないのは、0を返していることと同じ。
これは、if文が偽の時は $_%2 の演算結果である0が返っているだけ。

 perl -e '@a = map { if ($_%2){ 1 } } (1..5);print "values=".join(",",@a)."\n"; print "count=".scalar @a."\n"'
values=1,0,1,0,1
count=5


実は空文を返せばskipできる。0を返さないのがちょっと不思議。

perl -e '@a = map { if ($_%2){ 1 }else{} } (1..5);print "values=".join(",",@a)."\n"; print "count=".scalar @a."\n"'
values=1,1,1
count=3