はじめに
みなさんPerl書いてますかー!
今回も引き続き、Path::Tiny
というモジュールを紹介します。
このモジュールを使うことで・・・
- テキストファイルの読み書きが簡単に!
- ファイルの扱いが簡単に!
いろいろできるので試しつつ順に紹介していきます。
前回は、「テキストファイルの読み書きが簡単に!」の部分をご紹介しました。
https://qiita.com/hiro_nico/items/204b4fa4500edcc07268
基本的な使い方は、前回書いたので省略します。
今回は、
「ファイルの扱いが簡単に!」の部分をお送りします。
Path::Tiny
ファイルパス
ファイルを扱う処理をするときは、ファイルパスについても処理しますよね。
Path::Tiny使えばいろんなことが簡単にできますよ!
例えば
下記のようなファイル構成で話をしていきます。
C:\tmp>tree /f
C:.
│ CBR250RR.txt
│ program.pl
│
└─honda
GOLDWING.txt
NC750X.txt
Rebel250.txt
ファイル名の取得 (basename)
まずCBR250RR.txt
というファイル名を取得してみます。
use Path::Tiny;
my $txt = path("CBR250RR.txt");
print $txt->basename;
CBR250RR.txt
これくらいなら書かなくてもよいくらいですね・・・w
Path::Tinyオブジェクトに対して使うと
ファイル名の取得できます。
CBR250RR.txt
から拡張子を抜いた部分を取得することもできます。
use Path::Tiny;
my $txt = path("CBR250RR.txt");
print $txt->basename('.txt');
CBR250RR
また下記のように指定することもできるようです。
# 正規表現で拡張子を指定する
$txt->basename(qr/\.txt/);
# 配列から拡張子を指定する
my @suffixes = ('.txt', '.pl');
$txt->basename(@suffixes);
絶対パスの取得 (absolute)
use Path::Tiny;
my $txt = path("CBR250RR.txt");
print $txt->absolute;
C:/tmp/CBR250RR.txt
相対パスの取得 (relative)
relative("基準とするところ")
use Path::Tiny;
my $txt = path("CBR250RR.txt");
print $txt->relative("honda");
../CBR250RR.txt
CBR250RR.txt
は、honda
フォルダの一個上ってことで合ってますね。
実行環境に合わせてファイルパスを表示 (canonpath)
Windows環境で実行していますが
先程までのファイルパス表示を見てみると
スラッシュ区切り(/
)となってしまっています。
canonpath
を使用すると、windowsなら\
区切りで表示してくれます。
use Path::Tiny;
my $txt = path("CBR250RR.txt");
print $txt->absolute . "\n";
print $txt->absolute->canonpath;
C:/tmp/CBR250RR.txt
C:\tmp\CBR250RR.txt
これならファイルパスを使うときに
ファイルが見つからんぞゴラァ!
と怒られることはなさそうですねw
ファイル操作
コピーや移動や削除もできちゃいますよ!
ファイルのコピー (copy)
copy(コピー先)
use Path::Tiny;
my $txt = path("CBR250RR.txt");
$txt->copy("CB400SF.txt");
C:.
│ CB400SF.txt
│ CBR250RR.txt
│ program.pl
│
└─honda
GOLDWING.txt
NC750X.txt
Rebel250.txt
CB400SF.txt
が増えましたね!
ファイルの移動・リネーム (move)
ファイルの移動とリネームには、move
を使います。
move(移動先)
use Path::Tiny;
my $txt = path("CBR250RR.txt");
$txt->move('C:\tmp\honda\CBR250RR.txt');
C:.
│ program.pl
│
└─honda
CBR250RR.txt
GOLDWING.txt
NC750X.txt
Rebel250.txt
CBR250RR.txt
がhonda
フォルダの中に入りましたね!
リネームする場合も同じように・・・
use Path::Tiny;
my $txt = path("CBR250RR.txt");
$txt->move('CBR250R.txt');
C:.
│ CBR250R.txt
│ program.pl
│
└─honda
GOLDWING.txt
NC750X.txt
Rebel250.txt
CBR250RR.txt
がCBR250R.txt
に変わりました!
ファイルの削除 (remove)
use Path::Tiny;
my $txt = path("CBR250RR.txt");
$txt->remove;
C:.
│ program.pl
│
└─honda
GOLDWING.txt
NC750X.txt
Rebel250.txt
CBR250RR.txt
が消えたッ!
ちなみにフォルダは消せません・・・
use Path::Tiny;
my $dir = path("honda");
$dir->remove;
C:\tmp>perl program.pl
Error unlink on 'honda': Is a directory at program.pl line 5.
ディレクトリだから消せねえよ!!
って怒られました(´・ω・`)
ディレクトリの削除 (remove_tree)
これを使えば消せますよ!
use Path::Tiny;
my $dir = path("honda");
$dir->remove_tree;
C:.
CBR250RR.txt
program.pl
サブフォルダーは存在しません
ディレクトリの作成 (mkpath)
消したら作りたいじゃないですか?(いつもの
use Path::Tiny;
my $dir = path("kawasaki");
$dir->mkpath;
C:.
│ CBR250RR.txt
│ program.pl
│
├─honda
│ GOLDWING.txt
│ NC750X.txt
│ Rebel250.txt
│
└─kawasaki
kawasaki
フォルダが増えました。ヤッター!
他のファイルを扱う
フォルダ内のファイルを取得 (children)
use Path::Tiny;
my $dir = path("honda");
foreach my $file ($dir->children) {
printf "%s\n", $file->basename;
}
GOLDWING.txt
NC750X.txt
Rebel250.txt
フォルダ内にあるファイル一覧が表示できました。
children
から返ってくるものは、
Path::Tinyオブジェクトになっているので
紹介してきたような関数がそのまま呼べちゃいます!
あとは、フォルダ内の特定の拡張子だけとか取りたくなるじゃないですか?
そういった場合も、
children(qr/\.pl/)
など正規表現で取得するものを絞ることもできます。
拡張子だけでなくファイル名で絞ることもできますよ!
use Path::Tiny;
my $dir = path("honda");
foreach my $file ($dir->children(qr/^(NC|Rebel)/)) {
printf "%s\n", $file->basename;
}
NC750X.txt
Rebel250.txt
うん 便利ぃ~
children
はフォルダ内のファイルだけではなく
フォルダ内にフォルダがあった場合も同じく取得してくれます。
ファイルかフォルダかの判定は後述・・・
指定したファイルを取得 (child)
children
と似たような名前でchild
という関数があります。
なんじゃこりゃー!
って思った人もいるのではないでしょうか?(私は思いました)
child
は、指定したファイルやディレクトリのPath::Tinyオブジェクトを取得できます。
基本的にはフォルダ(Path::Tinyオブジェクト)に対して使う感じですかね。
使い方は、以下のような感じ。
use Path::Tiny;
my $dir = path("honda");
my $txt = $dir->child("Rebel250.txt");
print $txt->absolute;
C:/tmp/honda/Rebel250.txt
ファイルの存在有無 (exists)
存在するCBR250RR.txt
と存在しないCBR1000RR.txt
で確認してみます。
use Path::Tiny;
my $txt1 = path("CBR250RR.txt");
my $txt2 = path("CBR1000RR.txt");
if ($txt1->exists) {
printf "%s is exists.\n", $txt1;
} else {
printf "%s is not exists.\n", $txt1;
}
if ($txt2->exists) {
printf "%s is exists.\n", $txt2;
} else {
printf "%s is not exists.\n", $txt2;
}
CBR250RR.txt is exists.
CBR1000RR.txt is not exists.
ちゃんと判定できましたね。
ファイル・ディレクトリの判定 (is_file, is_dir)
use Path::Tiny;
my $txt = path("CBR250RR.txt");
my $dir = path("honda");
if ($txt->is_file) {
printf "%s is file.\n", $txt;
}
if ($dir->is_dir) {
printf "%s is dir.\n", $dir;
}
CBR250RR.txt is file.
honda is dir.
判定できました!
私はchildren
のときとかによく使ったりしますネ~
親ディレクトリを取得する (parent)
path(ファイルパス)
と書いてましたが、
実はpath(フォルダ, ファイル名)
というように
複数指定するとファイルパスをつなげてくれるんですよー!
use Path::Tiny;
my $txt = path("honda", "GOLDWING.txt");
print $txt;
honda/GOLDWING.txt
話がそれましたが・・・w
親ディレクトリを取得するときは、parent
を使用します。
use Path::Tiny;
my $txt = path("honda", "GOLDWING.txt");
my $dir = $txt->parent;
print $dir;
honda
深くもぐるにはchild
を使ってファイルなどを取得して、
上に戻るときにはparent
を使えば
親ディレクトリのPath::Tinyオブジェクトを取得できるというわけですね!
まとめ
ここまでPath::Tiny
を使った便利な関数を紹介してきました。
まだこれでも半分くらいでしょうか・・・?
まだまだできることがあるので、
深く知りたい場合は、Path::Tinyの公式ドキュメントを見てみてくださいね!
(やる気があれば、もう1記事くらい書くかも?)