gpt4 book ai didi

java - 具有多线程和实例共享的泛型

转载 作者:行者123 更新时间:2023-12-02 10:20:50 24 4
gpt4 key购买 nike

我有一个通用类,可以像这样绘制

public class Shared<T extends EntityBase> {

private HashMap<String, Class<? extends Executor<T>>> classes;
private HashMap<String, ? super Executor<T>> instances;
private List<Entity> entities;
private Compiler compiler;

// Constructor and getters

public void put(Entity entity, Source source) {
Class<?> cls = compiler.load(source);
put(entity, (Class<? extends Executor<T>>) cls );

}

private void put(Entity entity, Class<? extends Executor<T>> cls) throws IllegalAccessException, InstantiationException {
classes.put(entity.getId(), cls);
instances.put(entity.getId(), cls.newInstance());
entities.add(entity);
}
}

在我的应用程序中,此类被实例化一次,并且多个独立线程访问它。

特别是,单个线程负责写入它,并且多个线程通过 getter 访问它的实例 Map。

当我收到Source时实例并调用 private put方法, map 和列表都会更新。

在调试 session 中 InteliiJSingleton框架时类退出,该类失去其状态并且两者都 MapList再次变得空虚。

我该如何解释呢?为什么Class<? extends Executor<T>>实例和? super Executor<T>实例丢失?

最佳答案

泛型实际上只是编译器想象力的一部分;在运行时,一切都消失了。因此,此示例中的泛型与您所看到的完全无关。

粘贴的代码无法产生您所看到的效果( map 首先更改,然后恢复)。但是,更一般地说,如果您从不同的线程调用“put”,则此代码将被破坏。没有适当的防护措施来阻止同步访问。当您从不同的线程同时更新 map 时, map 规范明确指出任何事情都可能发生(从这个意义上说, map 只是重置为空在技术上是“根据规范”,因为任何事情都是允许的,因为您没有进行线程处理)发行权)。

简单的解决方法是将第二个 put 方法标记为“同步”。

另一种策略是使用 java.util.concurrent 包中的列表和映射。但是,无论使用多少次,都无法保证类、实例和实体彼此同步。只有同步可以做到这一点。

关于java - 具有多线程和实例共享的泛型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54353092/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com