public class StoreMessage extends Thread implements Serializable{
private static long start_nanotime=System.nanoTime();
private static int timeToRun = 60000;
private static byte[] b=null;
private static long startTime = System.currentTimeMillis();
private static long runUntilMillis = System.currentTimeMillis() + timeToRun;
public static Map <Long,Message> map1=new TreeMap<Long,Message>();
public static void store(Message message)throws Exception{
while (true) {
long now = System.currentTimeMillis();
if (now >= runUntilMillis) {
break;
}
long precise_time=TimeUnit.MILLISECONDS.toNanos(now)+(System.nanoTime()-start_nanotime);
map1.put(precise_time, message);
}
}
public static byte[] returning()throws Exception
{
b=serializer.serialize(map1);
System.out.println(b);
map1.clear();
return b;
}
}
What I am trying to do is, store all my message objects received by the class StoreMessage in every one minute to a TreeMap, serialize that TreeMap and return it to the class calling it, and create/clear the TreeMap for the next minute to store the other message objects.
Message object of the message class are jms text messages, which are input as command-line-arguments. The store
method is called in another class, while the returning()
method is called in a different class. Both classes, when instantiated and run, with more than one argument, give me an exception
java.util.ConcurrentModificationException
at java.util.TreeMap$PrivateEntryIterator.nextEntry(TreeMap.java:1100)
at java.util.TreeMap$EntryIterator.next(TreeMap.java:1136)
at java.util.TreeMap$EntryIterator.next(TreeMap.java:1131)
at java.util.TreeMap.writeObject(TreeMap.java:2250)
Why? Especially, when I am clearing the map. I do not get this exception, if I am giving only one command-line-argument. But if it is complied over and over,i get the same exception.
Secondly, I noticed that, as and when the message objects as received, they are stored into the TreeMap and serialized and returned. When I want the tree map to store the messages for one minute and then serialize the whole lot.
try using Collections
:
public static Map <Long,Message> map1 =
Collections.synchronizedMap(new TreeMap<Long,Message>());
to synchronize your Map instance.