| ページ一覧 | ブログ | twitter |  書式 | 書式(表) |

MyMemoWiki

差分

ナビゲーションに移動 検索に移動
311 バイト追加 、 2020年2月16日 (日) 04:27
編集の要約なし
==[[Java 並行処理]]==[[Java]{{category ] | [[Category:並行処理}}]]
==非同期に grep を実施する例1==
===内容===
*Thread ではなく、Executor を使って、Runnable を使って、[[R]]unnable を非同期に実行する
*共有データにスレッドセーフな単一の変数([http://java.sun.com/javase/ja/6/docs/ja/api/ java.util.concurrent.atomic])を使用する
====[http://java.sun.com/javase/ja/6/docs/ja/api/ java.util.concurrent.atomic]====
====[http://java.sun.com/javase/ja/6/docs/ja/api/java/util/concurrent/Executor.html Executor]====
*[http://java.sun.com/javase/ja/6/docs/ja/api/ java.util.concurrent]
*送信された Runnable [[R]]unnable タスクを実行するオブジェクト
*通常、executor は、明示的にスレッドを作成する代わりに使用
====ソース====
import java.io.BufferedReaderBuffered[[R]]eader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FilenameFilter;
import java.io.InputStreamReaderInputStream[[R]]eader;
import java.io.OutputStreamWriter;
import java.util.ArrayList;
static AtomicInteger workingThreadCount = null;
private static final int THREAD_SIZE TH[[R]]EAD_SIZE = 10;
public static void main(String[] args) throws Exception {
if (args.length <&lt;=2) {
System.out.println("Usage: java JGrep 対象ディレクトリ 正規表現 [ファイルフィルタ]");
System.exit(-1);
String fileFilter = "";
if (args.length > &gt; 2) {
fileFilter = args[2];
}
// スレッドで処理させる単位(バケツ)のサイズを決定
int buketSize = files.length / THREAD_SIZETH[[R]]EAD_SIZE;
buketSize++;
int filesInBuketCnt = 0;
List<&lt;List<&lt;File>> &gt;&gt; buketBuket = new ArrayList<&lt;List<&lt;File>>&gt;&gt;(); List<&lt;File> &gt; fileBuket = null;
for (File file : files) {
if (filesInBuketCnt == 0) {
fileBuket = new ArrayList<&lt;File>&gt;();
}
fileBuket.add(file);
filesInBuketCnt++;
if (filesInBuketCnt > &gt; buketSize) {
buketBuket.add(fileBuket);
filesInBuketCnt = 0;
}
}
if (files !=null && filesInBuketCnt > &gt; 0) {
buketBuket.add(fileBuket);
}
// 非同期処理を行う
Executor executer = new Executor() {
public void execute(Runnable [[R]]unnable command) {
new Thread(command).start();
}
int threadId = 1;
for (List<&lt;File> &gt; lstFiles : buketBuket) {
executer.execute(
new GrepCommand(threadId++,
* grep を実行する
*/
public static class GrepCommand implements Runnable [[R]]unnable {
private int threadId;
private File[] files;
/**
* 対象ファイルから、正規表現に一致する行を、出力ディレクトリにスレッド識別用IDファイル名にて結果出力する対象ファイルから、[[正規表現]]に一致する行を、出力ディレクトリにスレッド識別用IDファイル名にて結果出力する
* @param threadId スレッド識別用ID
* @param files grep 対象ファイル
* @param outDir 結果出力ディレクトリ
* @param expr [[正規表現]](Java)
*/
public GrepCommand(int threadId, File[] files, File outDir, String expr) {
}
/* (non-Javadoc[[Java]]doc) * @see java.lang.Runnable[[R]]unnable#run()
*/
public void run() {
for (File file : files) {
System.out.printf("[%03d]処理中 ... %s\n", this.threadId, file.getName());
BufferedReader Buffered[[R]]eader reader = new BufferedReaderBuffered[[R]]eader( new InputStreamReaderInputStream[[R]]eader(new FileInputStream(file)));
long lineno = 0;
int remain = workingThreadCount.addAndGet(-1);
System.out.println("残りのスレッド数... " + remain);
if ( remain <&lt;= 0) {
System.out.println("終了しました。");
}
=====実行例11=====
> &gt; java JGrep "C:\\work\\" ".*[[TEST]].*" ".*\.txt$"
[006]処理中 ... WORK16.txt
===内容===
*上記例を書き換え
*ExecutorService ExecutorSer[[vi]]ce を使って複数スレッドを管理*Runnable [[R]]unnable の代わりに、Callableを利用して、結果を受け取る
*Future にて結果を表示
====[http://java.sun.com/javase/ja/6/docs/ja/api/java/util/concurrent/ExecutorService.html ExecutorService]====
====[http://java.sun.com/javase/ja/6/docs/ja/api/java/util/concurrent/Callable.html Callable]====
*結果を返し、例外をスローすることがあるタスク
*Runnable [[R]]unnable と似ていて、どちらもインスタンスが別のスレッドによって実行される可能性があるクラス用に設計*Runnable [[R]]unnable は結果を返さず、チェック例外をスローすることはできません
====ソース====
import java.io.BufferedReaderBuffered[[R]]eader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FilenameFilter;
import java.io.InputStreamReaderInputStream[[R]]eader;
import java.io.OutputStreamWriter;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorServiceExecutorSer[[vi]]ce;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
public class JGrep {
private static final int THREAD_SIZE TH[[R]]EAD_SIZE = 10;
// スレッドプール
private ExecutorService ExecutorSer[[vi]]ce threadPool;
public static void main(String[] args) throws Exception {
if (args.length <&lt;=2) {
System.out.println("Usage: java JGrep 対象ディレクトリ 正規表現 [ファイルフィルタ]");
System.exit(-1);
String fileFilter = "";
if (args.length > &gt; 2) {
fileFilter = args[2];
}
// スレッドで処理させる単位(バケツ)のサイズを決定
int buketSize = files.length / THREAD_SIZETH[[R]]EAD_SIZE;
buketSize++;
int filesInBuketCnt = 0;
List<&lt;List<&lt;File>> &gt;&gt; buketBuket = new ArrayList<&lt;List<&lt;File>>&gt;&gt;(); List<&lt;File> &gt; fileBuket = null;
for (File file : files) {
if (filesInBuketCnt == 0) {
fileBuket = new ArrayList<&lt;File>&gt;();
}
fileBuket.add(file);
filesInBuketCnt++;
if (filesInBuketCnt > &gt; buketSize) {
buketBuket.add(fileBuket);
filesInBuketCnt = 0;
}
}
if (files !=null && filesInBuketCnt > &gt; 0) {
buketBuket.add(fileBuket);
}
// Callable は、Runnabla は、[[R]]unnabla と同じような役割を担うが、 // Runnable [[R]]unnable と異なり、結果を返し、例外をスローすることができる List<&lt;Callable<&lt;Long>> &gt;&gt; tasks = new ArrayList<&lt;Callable<&lt;Long>>&gt;&gt;(); threadPool = Executors.newFixedThreadPool(THREAD_SIZETH[[R]]EAD_SIZE);
int threadId = 1;
for (List<&lt;File> &gt; lstFiles : buketBuket) {
tasks.add(
new GrepCommand(threadId++,
// 指定されたタスクを実行し、すべて完了すると、ステータスと結果を含む Future のリストを返す
List<&lt;Future<&lt;Long>> &gt;&gt; results = threadPool.invokeAll(tasks); for (Future<&lt;Long> &gt; f : results) {
System.out.printf("一致件数 %d 件\n", f.get().longValue());
}
* grep を実行する
*/
public static class GrepCommand implements Callable<&lt;Long> &gt; {
private int threadId;
private File[] files;
/**
* 対象ファイルから、正規表現に一致する行を、出力ディレクトリにスレッド識別用IDファイル名にて結果出力する対象ファイルから、[[正規表現]]に一致する行を、出力ディレクトリにスレッド識別用IDファイル名にて結果出力する
* @param threadId スレッド識別用ID
* @param files grep 対象ファイル
* @param outDir 結果出力ディレクトリ
* @param expr [[正規表現]](Java)
*/
public GrepCommand(int threadId, File[] files, File outDir, String expr) {
}
/* (non-Javadoc[[Java]]doc)
* @see java.util.concurrent.Callable#call()
*/
for (File file : files) {
System.out.printf("[%03d]処理中 ... %s\n", this.threadId, file.getName());
BufferedReader Buffered[[R]]eader reader = new BufferedReaderBuffered[[R]]eader( new InputStreamReaderInputStream[[R]]eader(new FileInputStream(file)));
long lineno = 0;

案内メニュー