Categories: Java

【Java入門】Filesクラスでファイル操作

Filesクラスは基本的にPathクラスのオブジェクトを引数に取って処理します。
そのため、Pathクラスの使い方を知っている必要があります。
Pathクラスについては以下の記事で解説しています。

ファイルの存在確認

まずはディレクトリの中に何があるかを確認します。

Linuxコマンド

user01@DESKTOP-AQBVPOG MINGW64 /c/workspace
$ ls -l *.txt
-rw-r--r-- 1 user01 197609 0 8月  15 20:40 text123.txt
-rw-r--r-- 1 user01 197609 0 8月  15 20:40 text456.txt

「text123.txt」と「text456.txt」があります。
Javaでファイルが存在するかどうかを確認するにはexists(path)を使用します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\text123.txt");
Path p2 = Paths.get("C:\\workspace\\text789.txt");

//p1のファイルが存在するかを確認
System.out.println(Files.exists(p1));

//p2のファイルが存在するかを確認
System.out.println(Files.exists(p2));

実行結果

true
false

解説

「text789.txt」は存在しないので、falseとなります。

空ファイルを作成する

空ファイルの作成を行うにはcreateFile(path)を使用します。
まずはこれから作成するファイル名のファイルが存在しないことを確認します。

Linuxコマンド

$ ls -l *999.txt
ls: cannot access '*999.txt': No such file or directory

Javaで「text999.txt」という名前のファイルを作成します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\text999.txt");

//空ファイルの生成。
if(!Files.exists(p1)){
    Files.createFile(p1);
}

ファイルが作成されたかどうかを確認します。

Linuxコマンド

$ ls -l *999.txt
-rw-r--r-- 1 user01 197609 0 8月  16 18:15 text999.txt

これで無事にファイルが作成されました。

同名のファイルが既に存在する場合

同名のファイルが既に存在する場合はjava.nio.file.FileAlreadyExistsExceptionが発生してしまいます。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\text999.txt");

//ファイル作成
Files.createFile(p1);

実行結果

Exception in thread "main" java.nio.file.FileAlreadyExistsException: C:\workspace\text999.txt
    at sun.nio.fs.WindowsException.translateToIOException(WindowsException.java:81)
    at sun.nio.fs.WindowsException.rethrowAsIOException(WindowsException.java:97)
    at sun.nio.fs.WindowsException.rethrowAsIOException(WindowsException.java:102)
    at sun.nio.fs.WindowsFileSystemProvider.newByteChannel(WindowsFileSystemProvider.java:230)
    at java.nio.file.Files.newByteChannel(Files.java:361)
    at java.nio.file.Files.createFile(Files.java:632)
    at test.SampleFiles.lll(SampleFiles.java:31)
    at test.SampleFiles.main(SampleFiles.java:18)

解説

ファイル作成を行う際は必ずexists(path)メソッドでファイルの存在確認をするようにしましょう。

ファイルをコピーする

ファイルコピーを行うにはcopy(path,target)を使用します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\text999.txt");
Path target = Paths.get("C:\\workspace\\text888.txt");

//コピー先ファイルが存在しない場合、コピーする
if(!Files.exists(target)){
    Files.copy(p1, target);
}

ファイルがコピーされたか確認してみます。

Linuxコマンド

user01@DESKTOP-AQBVPOG MINGW64 /c/workspace
$ ls -l text999.txt text888.txt
-rw-r--r-- 1 user01 197609 4 8月  16 18:27 text888.txt
-rw-r--r-- 1 user01 197609 4 8月  16 18:27 text999.txt

user01@DESKTOP-AQBVPOG MINGW64 /c/workspace
$ cat text999.txt
test
user01@DESKTOP-AQBVPOG MINGW64 /c/workspace
$ cat text888.txt
test

中身までしっかりコピーされていることが確認できました。

コピー先のファイルが既に存在する場合

コピー先のファイルが既に存在する場合はjava.nio.file.FileAlreadyExistsExceptionが発生してしまいます。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\text999.txt");
Path target = Paths.get("C:\\workspace\\text888.txt");

//ファイルコピー
Files.copy(p1, target);

実行結果

Exception in thread "main" java.nio.file.FileAlreadyExistsException: C:\workspace\text888.txt
    at sun.nio.fs.WindowsFileCopy.copy(WindowsFileCopy.java:124)
    at sun.nio.fs.WindowsFileSystemProvider.copy(WindowsFileSystemProvider.java:278)
    at java.nio.file.Files.copy(Files.java:1274)
    at test.SampleFiles.mmm(SampleFiles.java:46)
    at test.SampleFiles.main(SampleFiles.java:18)

解説

ファイルをコピーする場合は必ずexists(path)メソッドでコピー先のファイルの存在確認をするようにしましょう。

ファイルを移動する

ファイルを移動するにはmove(path)を使用します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\folderA\\text.txt");
Path target = Paths.get("C:\\workspace\\folderB\\aaa.txt");

//移動先ファイルが存在しない場合、移動する。
if(!Files.exists(target)){
    Files.move(p1, target);
}

ファイルが移動したか確認してみます。

Linuxコマンド

user01@DESKTOP-AQBVPOG MINGW64 /c/workspace
$ ls -l folderA
total 0

user01@DESKTOP-AQBVPOG MINGW64 /c/workspace
$ ls -l folderB
total 1
-rw-r--r-- 1 user01 197609 4 8月  17 13:50 aaa.txt

folderAは空でfolderBにaaa.txtが存在するので、これで無事に移動できました。

注意
    targetの方はaaa.txtというファイル名になっています。folderAに格納されていたtext.txtという名前のファイルをfolderBに格納する際にaaa.txtというファイル名に変わっているのです。

移動先に既に同名ファイルが存在する場合

移動先に同盟のファイルが既に存在する場合はjava.nio.file.FileAlreadyExistsExceptionが発生してしまいます。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\folderA\\text.txt");
Path target = Paths.get("C:\\workspace\\folderB\\aaa.txt");

//ファイルを移動
Files.move(p1, target);

実行結果

Exception in thread "main" java.nio.file.FileAlreadyExistsException: C:\workspace\folderB\aaa.txt
    at sun.nio.fs.WindowsFileCopy.move(WindowsFileCopy.java:343)
    at sun.nio.fs.WindowsFileSystemProvider.move(WindowsFileSystemProvider.java:287)
    at java.nio.file.Files.move(Files.java:1395)
    at test.SampleFiles.ooo(SampleFiles.java:34)
    at test.SampleFiles.main(SampleFiles.java:18)

解説

ファイルを移動する場合は必ずexists(path)メソッドで移動先ファイルの存在確認をするようにしましょう。

ファイル削除

ファイルを削除するにはdeleteIfExists(path)を使用します。
ファイルの削除に成功した場合はtrueを返し、ファイルを削除できなかった場合はfalseを返します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\folderB\\aaa.txt");

//ファイル削除。
System.out.println(Files.deleteIfExists(p1));

実行結果

true

ディレクトリ判定

ディレクトリ判定行うには、isDirectory(path)を使用します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\text123.txt");
Path p2 = Paths.get("C:\\workspace");

//p1がディレクトリか否かを判定
System.out.println(Files.isDirectory(p1));

//p2がディレクトリか否かを判定
System.out.println(Files.isDirectory(p2));

実行結果

false
true

解説

「C:\\workspace\\text123.txt」はディレクトリではないのでfalseとなりました。

通常ファイル判定

通常ファイルであるかを判定するにはisRegularFile(path)を使用します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\text123.txt");
Path p2 = Paths.get("C:\\workspace");

//p1が通常ファイルかどうかを確認
System.out.println(Files.isRegularFile(p1));

//p2が通常ファイルかどうかを確認
System.out.println(Files.isRegularFile(p2));

実行結果

true
false

解説

p1は通常ファイルなのでTrueになり、p2はディレクトリなのでfalseとなります。

隠しファイル判定

隠しファイルであるかを判定するにはisHidden(path)を使用します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\text123.txt");
Path p2 = Paths.get("C:\\workspace\\textHiddne.txt");

//p1が隠しファイルかどうかを確認
System.out.println(Files.isHidden(p1));

//p2が隠しファイルかどうかを確認
System.out.println(Files.isHidden(p2));

実行結果

false
true

解説

「textHiddne.txt」は隠しファイルなのでTrueになります。

ファイルの内容をbyte配列で取得する

ファイルの内容をbyte配列で取得するにはFiles.readAllBytesを使用します。

Java

//ファイルの内容をbyte配列で取得。
byte[] byteData = Files.readAllBytes(Paths.get("C:\\workspace\\test.txt"));

// UTF-8で文字列に変換
String str = new String(byteData, StandardCharsets.UTF_8);

//出力
System.out.println(str);

実行結果

いろはにほへと ちりぬるを
わかよたれそ  つねならむ
うゐのおくやま けふこえて
あさきゆめみし ゑひもせすん

色は匂へど 散りぬるを
我が世誰そ 常ならむ
有為の奥山 今日越えて
浅き夢見じ 酔ひもせず

ディレクトリの作成(再帰なし)

ディレクトリを作成するにはcreateDirectory(path)を使用します。

注意
  • このメソッドは指定したパスの最後のディレクトリのみを作成するため、途中のディレクリ(dir20までの各フォルダ)が存在していないと異常終了してしまいます。
  • これを気にしないで作成したい場合は、後述の`createDirectories(paths)`を使った再帰処理でディレクトリ作成する方法が便利です。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\dir10\\dir20\\dir30");

//ディレクトリを作成(再帰なし)
Files.createDirectory(p1);

Linuxコマンド

$ ls -l -d $(find /c/workspace/dir10)
drwxr-xr-x 1 user01 197609 0 8月  16 17:45 /c/workspace/dir10/
drwxr-xr-x 1 user01 197609 0 8月  16 17:45 /c/workspace/dir10/dir20/
drwxr-xr-x 1 user01 197609 0 8月  16 17:45 /c/workspace/dir10/dir20/dir30/

ディレクトリの作成(再帰あり)

まずはディレクトリが存在しないことを確認します。

Linuxコマンド

$ ls -l -d $(find /c/workspace/dir1)
find: ‘/c/workspace/dir1’: No such file or directory
drwxr-xr-x 1 user01 197609 0 8月  16 16:47 ./

再帰してディレクトリを作成するにはcreateDirectories(paths)を使用します。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\dir1\\dir2\\dir3\\");

//ディレクトリを作成(再帰あり)
Files.createDirectories(p1);

ディレクトリが作成されたかどうかを確認してみます。

Linuxコマンド

$ ls -l -d $(find /c/workspace/dir1)
drwxr-xr-x 1 user01 197609 0 8月  16 16:49 /c/workspace/dir1/
drwxr-xr-x 1 user01 197609 0 8月  16 16:49 /c/workspace/dir1/dir2/
drwxr-xr-x 1 user01 197609 0 8月  16 16:49 /c/workspace/dir1/dir2/dir3/

無事作成されていることを確認できました。

フルパスでファイル名を指定した場合は要注意

以下のように、パスの最後がファイル名になっている場合は注意が必要です。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\dir1\\dir2\\dir3\\test999.txt");

//ディレクトリを作成(再帰あり)
Files.createDirectories(p1);

このまま実行してしまうと以下のように「test999.txt」という名前でディレクトリが作成されてしまいます。

Linuxコマンド

$ ls -l -d $(find /c/workspace/dir1)
drwxr-xr-x 1 user01 197609 0 8月  16 16:49 /c/workspace/dir1/
drwxr-xr-x 1 user01 197609 0 8月  16 16:49 /c/workspace/dir1/dir2/
drwxr-xr-x 1 user01 197609 0 8月  16 16:56 /c/workspace/dir1/dir2/dir3/
drwxr-xr-x 1 user01 197609 0 8月  16 16:56 /c/workspace/dir1/dir2/dir3/test999.txt/

こうした場合はgetParent()を使って親ディレクトリ作成をします。

Java

//パスを取得。
Path p1 = Paths.get("C:\\workspace\\dir7\\dir8\\dir9\\test999.txt");

//親ディレクトリを作成(再帰あり)
Files.createDirectories(p1.getParent());

Linuxコマンド

$ ls -l -d $(find /c/workspace/dir7)
drwxr-xr-x 1 user01 197609 0 8月  16 17:05 /c/workspace/dir7/
drwxr-xr-x 1 user01 197609 0 8月  16 17:05 /c/workspace/dir7/dir8/
drwxr-xr-x 1 user01 197609 0 8月  16 17:05 /c/workspace/dir7/dir8/dir9/

解説

getParent()で「C:\\workspace\\dir7\\dir8\\dir9\\」までを取得してディレクトリ作成をすることができました。

以上で記事の解説はお終い!

もっとJavaやSpringを勉強したい方にはUdemyがオススメ!同僚に差をつけよう!

issiki_wp