Java 如何使此方法线程安全?
我希望getData是幂等的,如果这个词正确的话。对它的每次调用,无论是来自两个不同的线程,都会并发地、串行地返回相同的值。 我的主要问题是两个线程调用MyMap.getData,我注意到返回的映射是不一致的——请参阅现在的代码块l.lock'ed——因为它可能被两个线程变异,或者底层映射的put和get没有同步。我想知道这是否是线程安全的,如果不是,如何使它防弹。该方法基本上可以获取数据 下面是一些伪java guava代码:Java 如何使此方法线程安全?,java,multithreading,guava,Java,Multithreading,Guava,我希望getData是幂等的,如果这个词正确的话。对它的每次调用,无论是来自两个不同的线程,都会并发地、串行地返回相同的值。 我的主要问题是两个线程调用MyMap.getData,我注意到返回的映射是不一致的——请参阅现在的代码块l.lock'ed——因为它可能被两个线程变异,或者底层映射的put和get没有同步。我想知道这是否是线程安全的,如果不是,如何使它防弹。该方法基本上可以获取数据 下面是一些伪java guava代码: public class MyMap extends Map {
public class MyMap extends Map {
final Lock l = new ReentrantLock();
public Table<S, I, F> getData(Iterable<S> ss, Iterable<B> bs) {
final Table<S, I, F> t = HashBasedTable.create();
final ImmutableSet.Builder<B> builder = ImmutableSet.builder();
for (B b : bs) {
builder.add(b)
}
final ImmutableSet<B> finalBs = builder.build();
for (A a : as) {
final ImmutableTable<I, I, F> im = get(a);
l.lock();
try {
if (im == null) {
final Table<I, I, F> mutableT = HashBasedTable.create()
... populate table ...
put(a, ImmutableTable.copyOf(mutableT);
}
} finally {
l.unlock();
}
for (Map.Entry<I, I, F> entry : im) {
final A a = ... some simple transform of key ...
for (Map.Entry<I, F> entry2 : entry.getValue().entrySet()) {
if (finalBs.contains(entry.B) {
t.put(a, entry.B, entry.C)
}
}
}
}
return ImmutableTable.copyOf(t);
}
}
在for循环外锁定?什么部分需要线程安全性?我没有真正遵循代码。您的get方法似乎是一个merge而不是get。像查询数据库和一些我不认识的类名之类的东西都没用。线程安全取决于许多正确的细节。你能更好地解释你的意图吗?@Bubletan这就是我要问的。@markspace为了清楚起见,我将更新我的帖子。@markspace,ConcurrentLinkedQueue是一个可变且线程安全的类的例子:不管有多少线程对其方法进行重叠调用;你放进去的每一样东西最终都会出来,正好一次,如果A在B之前进去,A会在B之前出来。,。。。该大小不如其他队列可靠,但Javadoc警告您这一点,因此仍然是线程安全的。其所有其他担保都将有效。但如果应用程序要求A在B之前出现,则需要更高级别的同步以确保A在B之前出现。