Java8でファイルの文字エンコーディング一括変換を行う

Java6までは、Javaでファイルエンコーディングの変換を行おうとすると、Readerで開いて一行ずつ読み込みながらWriterで書き込むみたいなコードが必要になってました。
これはJava7のnioで導入されたファイルユーティリティで簡単に書けるようになったのですが、フォルダ以下のファイルをすべて処理しようとすると再帰コードを書く必要があったりして面倒でした。
※追記 7/9 コメントで指摘あるように、walkFileTreeを使うと再帰書かずにファイルツリーの処理ができました。walkだとStreamになって便利、という感じですね。


でも、Java8ではファイルユーティリティにフォルダ以下のファイルをすべて処理するためのwalkメソッドが追加されているので、すべてのファイルを処理するということも楽になりました。


ということで、指定フォルダ以下のファイルのすべての文字コードWindows-31JからUTF-8に変換するとこんな感じになります。

public class Sjis2Utf8 {
    public static void main(String[] args) throws IOException {
        Path dir = Paths.get("C:\\Users\\naoki\\Desktop\\test");
        Files.walk(dir)
                .filter(p -> !Files.isDirectory(p))
                .forEach(p -> {
                    try{
                        Path tmp = Files.createTempFile(dir, "tmp", ".txt");
                        Files.write(tmp, 
                                Files.readAllLines(p, Charset.forName("Windows-31j")),
                                Charset.forName("utf-8"));
                        Files.delete(p);
                        Files.move(tmp, p);
                    }catch(IOException ex){
                        throw new RuntimeException(ex);
                    }
                });
    }
}


ただ、mainメソッドでthrowsを記述しているにもかかわらず、forEachの中でtry〜catchを書く必要があったりして、やっぱイケてないところが残ってしまっています。
forEachにはこういう問題もあるので、for文は使わざるを得なかったりするんですよねぇ。