Java 这段代码是线程安全的吗? private static final Word2Vec word2vectors=getWordVector(); 私有静态Word2Vec getWordVector(){ 字符串路径; 试一试{ PATH=new ClassPathResource(“models/word2vec_model”).getFile().getAbsolutePath(); }捕获(例外e){ e、 printStackTrace(); 返回null; } log.warn(“加载模型…”); 返回WordVectorSerializer.readWord2VecModel(新文件(路径)); } ExecutorService池=Executors.newFixedThreadPool(4); long startTime=System.currentTimeMillis(); 列表

Java 这段代码是线程安全的吗? private static final Word2Vec word2vectors=getWordVector(); 私有静态Word2Vec getWordVector(){ 字符串路径; 试一试{ PATH=new ClassPathResource(“models/word2vec_model”).getFile().getAbsolutePath(); }捕获(例外e){ e、 printStackTrace(); 返回null; } log.warn(“加载模型…”); 返回WordVectorSerializer.readWord2VecModel(新文件(路径)); } ExecutorService池=Executors.newFixedThreadPool(4); long startTime=System.currentTimeMillis(); 列表,java,executorservice,Java,Executorservice,如果满足以下条件,您的代码段将是线程安全的: word2vectors.wordsAreset(…)调用是线程安全的 word2vectors数据结构由当前线程创建和初始化 不改变pools.execute调用和计算结束之间的数据结构 如果wordsNearest不查看其他数据结构,并且不更改word2vectors数据结构,则可以合理地假设它是线程安全的。然而,唯一确定的方法是对其进行分析 但也值得注意的是,您只向执行者提交了一个任务。由于每个任务都是由单个线程运行的工作,因此您的代码实际上只

如果满足以下条件,您的代码段将是线程安全的:

  • word2vectors.wordsAreset(…)
    调用是线程安全的
  • word2vectors
    数据结构由当前线程创建和初始化
  • 不改变pools.execute调用和计算结束之间的数据结构
  • 如果
    wordsNearest
    不查看其他数据结构,并且不更改
    word2vectors
    数据结构,则可以合理地假设它是线程安全的。然而,唯一确定的方法是对其进行分析


    但也值得注意的是,您只向执行者提交了一个任务。由于每个任务都是由单个线程运行的工作,因此您的代码实际上只使用一个线程。要利用多线程,您需要将单个大任务拆分为多个独立的小任务;e、 g.将10000次重复循环置于执行调用之外…

    取决于
    WordsAreset
    方法。如果我无法控制WordsAreset,如何使此代码安全?在不知道任何其他信息的情况下,唯一安全的方法是在调用
    WordsArest
    时使用一个线程或同步
    word2vectors
    。如果您至少知道它不使用静态字段(或通常的可变全局变量),然后,您可以创建任何类型
    word2vectors
    的4个实例。我想说,这是一个相当低的门槛,任何理智的库都应该能够做到。因为您只向ExecutorService提交一个Runnable,所以您将只运行一个线程。当然是线程安全的,但您可能希望有4个线程运行该任务。您能否以此为例,将其拆分为多个小任务?我已经告诉过您一种方法。再次阅读我的答案。我用你的建议更新了我的代码。这似乎不安全。假设我无法控制word2vectors.WordsArest,如何使此方法线程安全?如果您不知道
    WordsArest
    是线程安全的,那么保证线程安全的唯一方法就是只使用一个线程。@StephenC或使用同步。
    private static final Word2Vec word2vectors = getWordVector();
    
        private static Word2Vec getWordVector() {
            String PATH;
            try {
                PATH = new ClassPathResource("models/word2vec_model").getFile().getAbsolutePath();
            } catch (Exception e) {
                e.printStackTrace();
                return null;
            }
            log.warn("Loading model...");
            return WordVectorSerializer.readWord2VecModel(new File(PATH));
        }
    
            ExecutorService pools = Executors.newFixedThreadPool(4);
            long startTime = System.currentTimeMillis();
            List<Future<?>> runnables = new ArrayList<>();
            if (word2vectors != null) {
                for (int i = 0; i < 3000; i++) {
                    MyRunnable runnable = new MyRunnable("beautiful", i);
                    runnables.add(pools.submit(runnable));
                }
            }
            for(Future<?> task: runnables){
                try {
                    task.get();
                }catch(InterruptedException ie){
                    ie.printStackTrace();
                }catch(ExecutionException ee){
                    ee.printStackTrace();
                }
            }
            pools.shutdown();
    
    static class MyRunnable implements Runnable{
            private String word;
            private int count;
            public MyRunnable(String word, int i){
                this.word = word;
                this.count = i;
            }
    
            @Override
            public void run() {
                    Collection<String> words = word2vectors.wordsNearest(word, 5);
                    log.info("Top 5 cloest words: " + words);
                    log.info(String.valueOf(count));
            }
        }