【问题标题】:Make correct iteration for parallel threads in java在java中为并行线程进行正确的迭代
【发布时间】:2020-12-12 15:13:29
【问题描述】:

我在使用并行线程时遇到了一些麻烦。我将每个学生班级都设为一个线程,因此每个学生都需要请求一个团队。问题是它需要同时限制为 20 个请求。所以我在 StudentHandler 中做了这个:

int MAX = 20;
int ACTUAL = 0;
public boolean thereIsRoom(){
   return ACTUAL < MAX;
}
public void requestTeam(Student student){
   if(thereIsRoom()){
        ACTUAL += 1;
        System.out.println(ACTUAL);
        for(int x=0; x<teams.size(); x++){
            // student does stuff
        }
        ACTUAL -= 1;
        System.out.println(ACTUAL);
   }
}

输出如下:

1
stuff
0
1
2
3
4
stuff
.
.
31

等等,但我不明白为什么打印 ACTUAL 时超出了我的限制。如何解决?有必要让 StudentHandler 成为另一个线程吗?如果是那怎么办?

【问题讨论】:

  • “如何修复它?” 使代码线程安全。由于这是一个很大的话题,有许多潜在的解决方案,您需要开始研究(也称为研究)Java 中的线程安全主题,即并发编程 i> 在 Java 中。

标签: java multithreading parallel-processing


【解决方案1】:

我无法确定您为什么会出现这种行为,但是您的线程安全性中有一个明显的漏洞,修复它可能会解决问题。问题是在完成thereIsRoom 测试和更新变量AVAILABLE 之间存在时间间隔。这使得一个众所周知的经典问题得到了它自己的名字:竞争条件

例如,如果 10 个学生线程几乎同时尝试加入班级,并且处理器在 if 测试之后运行代码之前对测试进行排序,那么即使超过一次限制,它们都可以进入所有可用的增量都会得到处理。

要解决此问题,必须将测试和增量设计为 原子 操作。最常用的当然是使用synchronization。有时有同步的替代方法。例如,不要让线程直接尝试进入类,而是创建一个队列来处理入口请求,以防止出现竞争条件。

搜索“竞争条件”应该会找到许多文章,涵盖处理问题的各种策略。

【讨论】:

  • 谢谢,我确实不知道“竞争条件”这个术语,所以在阅读后我在thereIsRoom 方法中使用synchronized 解决了这个问题,并将int ACTUAL 转换为volatile int ACTUAL
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-12-05
  • 2022-01-06
  • 1970-01-01
  • 1970-01-01
  • 2013-07-30
相关资源
最近更新 更多