JavaのArrayListのスレッドセーフの挙動について
解決したいこと
ArrayListのスレッドについての疑問を解消したい。
こんにちは。
現在、JavaSilver資格取得に向けて勉強しております。
黒本にて「ArrayListの要素を拡張for文を使って削除するとどうなるか」
の問題が2パターンありました。
回答としては
①:「「A」のみ出力される」(remove()によってリストの内容だけがズレて、拡張for文のカーソルは動かない為)
②:「実行時に例外がスローされる」(1つのリストを拡張for文二つのマルチスレッド環境で操作しようとした為、「ConcurrentModificationException」が発生)
となっていました。
ArrayListはスレッドセーフのクラスで無いので②の回答には納得できるのですが、その回答の解説に「ConcurrentModificationExceptionは、シングルスレッド環境下でも発生する」と記載がありました。この解説に沿うならば、①の方でもこの例外が発生するのではないかと考えているのですが、なぜ正常に実行されるのでしょうか?
稚拙な質問で申し訳ございませんが、ご教授いただけますと幸いです。よろしくお願い致します。
問題のコード①
public static void main(String[] args) {
List<String> list = new ArrayList<>();
list.add("A");
list.add("B");
list.add("C");
for(String str : list) {
if("B".equals(str)) {
list.remove(str);
} else {
System.out.println(str);
}
}
}
問題のコード②
public static void main(String[] args) {
List<String> list = new ArrayList<>();
list.add("A");
list.add("B");
list.add("C");
list.add("D");
list.add("E");
for(String str : list) {
if("C".equals(str)) {
list.remove(str);
}
}
for(String str : list) {
System.out.println(str);
}
}
自分で試したこと
- ①の方の条件文を「"C".equals(str)」にして実行した所、「ConcurrentModificationException」が発生しました。
- ②の方の条件文を「"D".equals(str)」にして実行した所、以下の様に出力されました。
A
B
C
E