Javaの正規表現を学習しているときに躓いたところがあるので、忘備録として残しておきます。
やりたかったこと
あるディレクトリにあるファイルのうち、拡張子がpdfのもの(末尾がpdfで終わる文字列)をListに追加していく処理を行いたかった。
ちなみに拡張子がpdfのファイルはファイル名が8桁の整数で構成されているとする。
例:00000001.pdf
上記の処理を行うために以下のようにコードを記述した。
File[] files = new File(args[0]).listFiles();
//pdfファイルを保持するためのList
ArrayList<File> pdfFiles = new ArrayList<>();
//配列filesに代入したファイルをfile数の数だけ取得する
for(int i = 0; i< files.length; i++) {
String fileName = files[i].getName();
if(files[i].isFile() && fileName.matches("pdf$")) {
pdfFiles.add(files[i]);
}
}
発生した不具合
if(files[i].isFile() && fileName.matches("pdf$"))の部分で正規表現を用いて末尾がrdcのファイルを判定しているがこの状態で実行してもfalseになり、Listに追加することができなかった。
ググって調べたが、間違っているようには思えなかったのだが、、
どうやら"pdf$"だとpdfという文字にしかマッチしないようで、pdfより前に文字が存在する値は一致せずfalseになるようだ。
例:①値が"pdf"→trueが返ってきてリストに追加可能
②値が"32412.pdf"→falseが返ってきて値はリストに追加されない
今回の場合、拡張子pdfの前には8桁の整数があったので例の②が当てはまりfalseとなったと思われる。
対処法
正規表現をいずれかに修正することで問題なく処理が通るようになった。
if(files[i].isFile() && fileName.matches("^[0-9]{8}.pdf$")) {
pdfFiles.add(files[i]);
}
if(files[i].isFile() && fileName.matches(".*pdf$")) {
pdfFiles.add(files[i]);
}
パターン1では^[0-9]{8}で0~9の数字が8桁あること、.で任意の1文字が続くことを表している。(ここでは拡張子の「.」)
パターン2では.*で任意の1文字が0回以上繰り返すことを表している。
正規表現は勉強中であるため、間違いはあるかもしれないので、不備があればご指摘いただければ幸いです。