Javaのスレッド処理に関するメモ。
JDK1.4ではThreadを利用していたが、JDK1.5以降はExecutorServiceを利用する。
- 呼び出す側
1
public
static
void
main(String[] args) {
2
Z_Thread main =
new
Z_Thread();
3
// スレッド管理サービスを生成する。
4
ExecutorService singleExecutor = Executors.newSingleThreadExecutor();
5
main.executeSingleTask(singleExecutor);
6
// スレッドを終了する。
7
singleExecutor.shutdown();
8
}
1
private
void
executeSingleTask(ExecutorService serviceExecutor) {
2
// 戻り値を定義する。
3
Future<Long> future =
null
;
4
try
{
5
String fileDir =
"D:\\"
;
6
String fileName =
""
;
7
// 指定ディレクトリの「*.txt」の一覧を取得する。
8
Path path = Paths.get(fileDir);
9
try
(DirectoryStream<Path> directoryStream = Files.newDirectoryStream(path,
"*.txt"
)) {
10
// 指定ディレクトリの「*.txt」数分繰り返す。
11
for
(Path p : directoryStream) {
12
// ファイル名を取得する。
13
fileName = p.getFileName().toString();
14
// 取得したファイル名をタスクに登録する。
15
// タスクはCallableを利用することで戻り値と例外を受け取れるようにする。
16
// タスクはRunnableを利用すると戻り値と例外は受け取れない。
17
future = serviceExecutor.submit(
new
CallableTest(fileDir, fileName));
18
// Futureクラスのgetメソッドを呼び出すと呼び出し側は結果が返ってくるまで処理を止める。
19
// 20秒を過ぎるとタイム例外が返ってくる。
20
Long result = future.get(
20000
, TimeUnit.MILLISECONDS);
21
System.out.println(
"結果:"
+ result +
":スレッドの結果を受け取りました。"
);
22
}
23
}
24
}
catch
(InterruptedException e){
25
System.out.println(
"割り込み例外"
);
26
}
catch
(ExecutionException e) {
27
System.out.println(
"タスクの中で例外発生"
);
28
}
catch
(TimeoutException e) {
29
System.out.println(
"タイムアウト例外発生"
);
30
}
catch
(Exception e) {
31
System.out.println(
"何かの例外発生"
);
32
}
finally
{
33
future.cancel(
true
);
34
}
35
}
- 呼び出される側(タスク)(Callableを利用する)
1
private
String fileDir =
""
;
2
private
String fileName =
""
;
3
4
public
CallableTest(String fileDir, String fileName) {
5
this
.fileDir = fileDir;
6
this
.fileName = fileName;
7
}
8
9
public
Long call()
throws
Exception {
10
try
{
11
System.out.println(Thread.currentThread().getId() +
":スレッド処理開始"
);
12
if
(Thread.currentThread().isInterrupted()) {
13
System.out.println(
"スレッドに割り込みありました。"
);
14
throw
new
InterruptedException(
"割り込み例外"
);
15
}
16
17
// 何かの処理を想定
18
Thread.sleep(
10000
);
19
// コンストラクタで指定したファイルの内容を読み取り表示する。
20
List<String> line = Files.readAllLines(Paths.get(fileDir, fileName), Charset.forName(
"UTF-8"
));
21
System.out.println(Thread.currentThread().getId() +
":"
+ fileName +
"の内容を表示"
);
22
for
(String str : line) {
23
System.out.println(str);
24
}
25
}
catch
(Exception e){
26
System.out.println(Thread.currentThread().getId() +
"エラー検知"
);
27
throw
e;
28
}
finally
{
29
System.out.println(Thread.currentThread().getId() +
":スレッド処理終了"
);
30
}
31
return
Thread.currentThread().getId();
32
}