連結リストについて驚いたこと。

 先日、Javaのコードを書いている際に、隣の席のFさんと話題になったことがあります。Java.util.iteratorクラスについてです。 まず、Bean(Cでいう構造体みたいなの?VBでいうユーザー定義名前みたいなの?)の中に値を入れ、それをいくつか挿入したArrayListを作成し、それを繰り返し処理していくというコードです。 [java]System.out.println(list); // ①listにはBeanがいくつか入っている Iterator iterator = list.iterator(); while(iterator.hasNext()) { Bean bean = (Bean)iterator.next(); // これでlistの中の一つのbeanが取れる bean.setXXX("abcdefg"); // beanの中の変数の値を変える } System.out.println(list); // ②[/java] ①の時点でリストをシスアウトしたものと②でシスアウトしたものが違って出力されました。私は今まで、while文のなかで取得したbeanを変更しても、元のlistは変わらないと思っていたのですが、iterator反復子で処理した内容は元のリストにも反映されました。今まではリストをもう一つ作ってbeanを追加しなおしてから使っていたので影響は無かったのですが、こういう知らないで使っていた、という事実にびっくりしました。ResultSetと同じようにiterator.next()をすると、カーソルを移動させるみたいです。 whileの中で処理をしている途中でlistの値を変更すると、ConcurrentModificationExceptionという例外が起こります。なので、Iteratorオブジェクトを使った繰り返しはsynchronizedブロックの中で行うと良い、ということです。実際、そこまでやってるコードは見たこと無いですが…。 [java]synchronized(list) { Iterator iterator = list.iterator(); while(iterator.hasNext()) { Bean bean = (Bean)iterator.next(); bean.setXXX("abcdefg"); } }[/java] この事を調べるのに Javaプログラマのためのアルゴリズムとデータ構造 という本を読みました。知らなくてもコードは書けるのですが、知らないことがいっぱいあるのに書いてるのが怖くなりました。