11-5
- ファイルだったらその中身を、ディレクトリだったらファイル一覧を表示する
- 自分の解答
use strict;
use warnings;
my $hikisu = $ARGV[0];
unless (defined $hikisu){
print 'no HIKISU',"\n";
}
elsif ( -f $hikisu ) {
open( FILE, $hikisu );
while (<FILE>) {
print $_;
}
close FILE;
}
elsif ( -d $hikisu ) {
opendir( DIR, $hikisu );
while ( readdir DIR ) {
print $_, "\n";
}
closedir(DIR);
}
- 結城先生の解答は、引数が複数あった場合や、引数に指定したものが存在しない場合、に対処できるようにしていた。
- エラーをどこまで想定できるかが初心者と上級者の違いなんだろうか
use strict;
use warnings;
if ( @ARGV == 0 ) {
print "Usage: perl showit.pl file-or-dir ...\n";
exit(-1);
}
foreach my $name (@ARGV)
{
unless ( -e $name ) {
die "'$name' does not exist"
}
elsif ( -f $name ) {
open( FILE, $name ) or die "$name : $!";
foreach my $line (<FILE>) {
print $line;
}
close(FILE);
}
elsif ( -d $name ) {
opendir( DIR, $name ) or die "$name: $!";
foreach my $entry ( readdir(DIR) ) {
print $entry, "\n";
}
closedir(DIR);
}
else {
die "I cannot show '$name' to you.\n";
}
}
or die "$!"
- しかし、
"$"
って入れてtabtriggerを設定すると、入力が消えてしまう。
"\$!"
と設定して希望通りの動作をすることを確認。エスケープ重要。
11-6
- 3時間くらいかかった・・・
- しかも、結城先生の本には出てこないハッシュリファレンスまで使って
- 元データは
__DATA__
に設置。
use strict;
use warnings;
use Data::Dumper;
my $magazine;
my $num = 0;
my @array;
for my $i ( sort <DATA> ) {
if ( $i =~ /(^No\.\d+)(\s+)(\d+)/ ) {
$magazine->[$num]->{title} = $1;
$magazine->[$num]->{copies} = $3;
$num++;
}
}
for my $i ( 0 .. $num - 2 ) {
my $dif = "$magazine->[$i]->{title}" . ' -> '
. "$magazine->[ $i + 1 ]->{title}" . ':';
my $sa = $magazine->[ $i + 1 ]->{copies} - $magazine->[$i]->{copies};
push @array, $dif . $sa;
}
open( FILE, '> mmout.txt' ) or die "$!";
for my $i ( reverse @array ) {
print FILE $i, "\n";
}
close FILE;
- 結城先生だと、x行目とX+1行目という風にとらえて構築してるみたい。
- ただ、それだと最初の行は比較対象が無いので、1行目かどうかを判断する変数を用意して、条件分岐させてる
use strict;
use warnings;
my $outfile = 'mmout_yuki.txt';
open( OUTFILE, "> $outfile" ) or die "$outfile : $!";
my $firstline = 1;
my ( $lastvol, $lastcount );
foreach my $line (<DATA>) {
my ( $vol, $count ) = split( /\s+/, $line );
unless ($firstline){
my $up = $lastcount - $count;
print OUTFILE "$vol -> $lastvol: $up\n";
}
($lastvol , $lastcount) = ($vol,$count);
$firstline = 0;
}
close(OUTFILE);
11-7
- ハッシュに配列の要素を追加する方法すっかり忘れてて、自分の脳レベルに悲しくなる
use strict;
use warnings;
use Data::Dumper;
my $seiseki;
open( FILE, "data.txt" ) or die "$!";
for my $i (<FILE>) {
my ( $yomi, $name, @score ) = split /,/, $i;
my $sum;
for my $score (@score) {
$sum += $score;
}
push @$seiseki, { name => $name, score => $sum };
}
close FILE;
my $sorted;
@$sorted = sort { $b->{score} <=> $a->{score} } @$seiseki;
for my $i (@$sorted){
print $i->{name},$i->{score},"\n";
}
- 結城先生の解答は豪快だわ
- まるまる1行をハッシュのkeyにしてる。想像もつかんかったわ・・・
- カンマを見ると区切りたくなる病に・・・いややっぱり、1行を丸まるkeyってのは考えつかん
use strict;
use warnings;
use Data::Dumper;
open( FILE, 'data.txt' ) or die "$!";
my @file = <FILE>;
close(FILE);
my %line_to_sum;
my %line_to_name;
foreach my $line (@file) {
my ( $yomi, $name, @score ) = split( /,/, $line );
my $sum = 0;
foreach my $score (@score) {
$sum += $score;
}
$line_to_sum{$line} = $sum;
$line_to_name{$line} = $name;
}
print Dumper %line_to_name;
foreach my $line ( sort { $line_to_sum{$b} <=> $line_to_sum{$a} } @file ) {
print $line_to_name{$line}, "\t", $line_to_sum{$line}, "\n";
}
11-8
- これは簡単だった
- というか、いままで「ファイルグロブ」ってのがよくわからなかったんだけど、とっかかりを掴めたわ。
use strict;
use warnings;
for my $file (<*.*>) {
if ( -M $file < 1 ) {
print '(DAY)', $file, "\n";
}
elsif ( -M $file < 7 ) {
print '(WEEK)', $file, "\n";
}
else {
print '(OLD)', $file, "\n";
}
}
- 次回は付録のCGIに挑戦する予定。
- 「いまさらCGI?事態はWAFでしょ!!!!」とか思っていたけど、やはり一度は触れておかなくては行けない気がする。