[code="java"]
Map> readCache = ServiceCache.getReadcache();
Set sets = readCache.keySet();
for (Integer siteNum : sets) {
List<ByteBuffer> buffers = readCache.get(siteNum);
if (buffers.size() > 0) {
ByteBuffer buffer = buffers.get(0);
HeartBeatPackage hb = ServerDataParser.getHreatBeat(buffer);
buffers.remove(0);
}
[/code]
大致代码如上,从map中取出一个ArrayList,在使用之前我判断buffer.size() >0 了。为什么还会报异常
Exception in thread "Thread-13" java.lang.IndexOutOfBoundsException: Index: 0, Size: 0
at java.util.ArrayList.RangeCheck(ArrayList.java:547)
at java.util.ArrayList.remove(ArrayList.java:387)
at com.hongdian.rtu.process.DisData.run(DisData.java:38)
at java.lang.Thread.run(Thread.java:662)
看错误提示:Exception in thread "Thread-13"....可能程序在多线程运行中,有多个线程都通过了 if (buffers.size() > 0) 这行代码,此时有一个线程由于阻塞没有继续运行,而其他线程轮询执行buffers.remove(0); 当这个List被remove完了后,那个被阻塞的线程获得了执行权,此时再执行get(0)或remove()时,出现了数组越界.
你的线程只是并发了但没有同步,所以容易出这样的错误.
相当于ArrayList只是被new了,但是没有add(Object)任何元素.所以你在取第一个值时会报数组越界的错误.
下面是个简单的例子,可以帮助理解
import java.util.List;
import java.util.ArrayList;
class Test
{
public static void main(String[] args)
{
System.out.println("Hello World!");
List list = new ArrayList();
//if(list.size()>0)
list.add("hello");
System.out.println(list.get(0));
list.remove(0);
System.out.println(list.get(0));
}
}
后台错误:
E:>javac Test.java
E:>java Test
Hello World!
hello
Exception in thread "main" java.lang.IndexOutOfBoundsException: Index: 0, Size:
0
at java.util.ArrayList.RangeCheck(Unknown Source)
at java.util.ArrayList.get(Unknown Source)
at Test.main(Test.java:15)
如果判断其为null
则为list==null
如果判断里面有没有元素
则为list.size()==0
这两个是不同的。就像""与null是不同的。
看起来好像没有错的,
问题是在这里出来的么?
从这里看,问题应该不是在这里出现的
因为是线程,这个需要再多的代码,
我肯定这里没有错
同意楼的是线程并发问题引起。但是看你个的那部分代应该不会引发这个问题只为你的变量都是局部变量,楼主是不是没有原始的代码上传呢。。。。或者少了关键的部分