ArrayIndexOutOfBounds由于多个线程,我该怎么办?

时间:2014-06-18 08:10:55

标签: java multithreading

我已经阅读了很多关于多线程安全运行的内容,但老实说我不知道​​在这种情况下该怎么做。我正在使用API​​,我几乎不得不使用,这一行:

Character interactingMonster = myPlayer().getInteracting();

不幸的是,我有三个独立的线程同时运行,由于某种原因,我得到了这个例外,假设因为我在同一时间共享资源:

[ERROR][06/18 09:54:56 AM]: Uncaught exception!
java.lang.ArrayIndexOutOfBoundsException: 32767
at org.api.Players.getLocalPlayer(Players.java:39)

我遇到多个线程的所有其他问题,我已经修复了使用线程安全的数据类型,比如AtomicLong和CopyOnWriteArrayList,但在这种情况下,我需要一些建议。我需要找到一种方法来解决这个问题,而不必忽略使用多线程的好处。

任何提示?

PS。我无法访问myPlayer().getInteracting();它只是API,而且它的类被混淆了。

3 个答案:

答案 0 :(得分:1)

如果你调用的API不是线程安全的(文档应该告诉你,你的经验会暗示它不安全),那么你需要同步访问它,所以只有一个线程可以一次调用它。如果调用总是在同一个方法中进行(并且其中没有其他事情发生),那么您可以使整个方法同步。或者,您可以拥有一个同步的代码块,在这种情况下,您必须有一个要使用的对象,例如:

synchronized (myObject) {
    // call to non-thread-safe API
}

并确保对所有对同一api的调用使用相同的myObject。

这将对性能产生影响,并且意味着您必须开始担心潜在的死锁。有很多有关java和线程安全的教程,使用了“同步”和“#39;同步”。以及最近添加的Lock对象。

答案 1 :(得分:0)

您始终可以将该行代码与目标对象同步开始:

Character interactingMonster;
synchronized (myPlayer){
    interactingMonster = myPlayer().getInteracting();
}

答案 2 :(得分:0)

了解同步http://docs.oracle.com/javase/tutorial/essential/concurrency/sync.html

我是一个视觉人,所以这是一个有趣的同步我喜欢使用的例子,我觉得解释同步是如何工作的。代码基本上由2种不同的线程类型组成,一种是同步的,另一种不是。每个线程类型都打印一个字符串,后跟一个从0增加到9的整数。

在输出中,您会在一开始就看到foobar的大字体,这些消息只会在foo 9和{{ 1}},这是同步线程。未同步的帖子是bar 1hello,您会看到这些消息混杂在一起。


<强>输出

world

<小时/> 的代码

foo 0
foo 1
foo 2
foo 3
foo 4
foo 5
foo 6
foo 7
foo 8
foo 9
bar 0
bar 1
bar 2
bar 3
bar 4
bar 5
bar 6
bar 7
bar 8
bar 9
world 0
hello 0
hello 1
world 1
hello 2
world 2
hello 3
world 3
hello 4
world 4
hello 5
world 5
hello 6
world 6
hello 7
world 7
hello 8
world 8
world 9
hello 9