これは簡単な質問ではないと思います。手短に、何が起こっているかの小さな例を挙げます。Byron.txt ファイルにデータ ソースがあるとします。
彼女は雲のない気候と星空の夜のように、美しさの中を歩きます。
そして、暗くて明るい最高のもの
彼女の側面と彼女の目で会いましょう:華やか な日に天国が否定
するその優しい光にとてもまろやかです.
そして、このコードは AsyncTask 内で実行されます。
final ArrayList<Record> poem = new ArrayList<Record>();
final Object objectLock = new Object();
private Record rec = new Record();
@Override
protected Void doInBackground(Void... args) {
String line = null;
int i;
int last;
try {
process = Runtime.getRuntime().exec("cat Byron.txt");
bufferedReader = new BufferedReader(new InputStreamReader(process.getInputStream()), 8192);
synchronized (objectLock) {
poem.clear();
last = i = poem.size() - 1;
}
while(line = bufferedReader.readLine()) != null) {
rec.setString(line);
synchronized (objectLock) {
last++;
poem.add(last, rec);
}
while(!bPause && i < last) {
i++;
publishProgress(poem.get(i));
}
}
}
catch (Exception e) {
e.printStackTrace();
}
return null;
}
@Override
protected synchronized void onProgressUpdate(Record... m) {
if(m.length > 0) {
mContext.mTable.appendRow(m[0]);
}
}
UI に TableLayout があり、新しい行を取得するたびに新しい TableRow を追加します。これは、UI に表示される出力です。
彼女は雲のない気候と星空の夜のように、美しさの中を歩きます。
雲ひとつない気候と星空。
雲ひとつない気候と星空。
優しい光に
まろやかに やさしい光にまろやかに
デバッガーを起動すると、なぜそれが起こるのかがわかります。がスキップされ、ループが続く
場合があります。すでにキャッチ済み
のため公開はありません。
その後、ブロックはスキップされた回数だけ実行されます
が、元の行が失われ、代わりに現在の行が数回追加されます。
その後、すべての新しい行が再びキャッチされるまで公開されます。synchronized (objectLock)
i
last
poem
i
last
コードに従っていることがわかり、何が起こっているのかを説明できます。ここでの質問は、ブロックがスキップされるのはなぜですか?
同期ブロックが実行可能になるまで停止すると予想していました。
少なくともこれは、synchronized (objectLock)
使用しなくてもの機能を理解した方法でwait()
あり、notify()
ここでディスカッションを開くふりはしません (必要に応じて、チャット エリアでディスカッションを開くこともできます)
。コードに問題がある場合は、質問に答えてお知らせください。
ノート:
synchronized
アプリ内の別の場所で、ユーザーがこれまでに取得した行をメールで送信したい場合があるため、必要です。- ユーザーは公開を一時停止できます (
bpause
)。それがwhile
ループで、が falseの場合にのみi
続きます。last
bPause