服务器之家

服务器之家 > 正文

详解Java利用ExecutorService实现同步执行大量线程

时间:2020-09-02 10:12     来源/作者:关玮琳linSir

自从java1.5以后,官网就推出了executor这样一个类,这个类,可以维护我们的大量线程在操作临界资源时的稳定性。
先上一段代码吧:

testrunnable.java

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
public class testrunnable implements runnable {
  private string name;
 
  public testrunnable(string name) {
    this.name = name;
  }
 
  @override
  public void run() {
    while (true) {
      if (main.surplus < 0)
        return;
      main.surplus--;
      system.out.println(name + " " + main.surplus);
    }
  }
}

main入口

?
1
2
3
4
5
6
7
8
9
10
11
12
public static void main(string[] args) {
 
     testrunnable runnable = new testrunnable("runnable1");
     testrunnable runnable2 = new testrunnable("runnable2");
 
     thread t1 = new thread(runnable);
     thread t2 = new thread(runnable2);
 
     t1.start();
     t2.start();
 
  }

详解Java利用ExecutorService实现同步执行大量线程

这样,我们就看到了,数据肯定是乱了的,当然这个时候我们可以加上一个synchronized的关键字,但是这样也会出现点小问题的

详解Java利用ExecutorService实现同步执行大量线程

下面我打算采用一种java内置的线程管理的机制,来解决这个问题,解决这个问题的思路大概就是,我们维护了一个线程池,当有请求操作的时候统统进入线程池,并且我们只开了一个线程,可以让请求顺序执行,顺序调用临界资源,就很安全了。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
import java.util.concurrent.callable;
import java.util.concurrent.executionexception;
import java.util.concurrent.executorservice;
import java.util.concurrent.executors;
import java.util.concurrent.future;
 
public class main {
  public static int surplus = 10;
 
  private executorservice executor = executors.newsinglethreadexecutor();
 
  void addtask(runnable runnable) {
    executor.execute(runnable);
  }
 
  <v> v addtask(callable<v> callable) {
    future<v> submit = executor.submit(callable);
    try {
      return submit.get();
    } catch (interruptedexception e) {
      system.out.println("interruptedexception" + e.tostring());
    } catch (executionexception e) {
      system.out.println("executionexception" + e.tostring());
    }
    return null;
  }
 
  public void testaddtask(string name) {
    addtask(new runnable() {
      @override
      public void run() {
        for (int i = 0; i < 3; i++) {
          if (main.surplus <= 0)
            return;
          main.surplus--;
          system.out.println(name + " " + main.surplus);
        }
 
      }
    });
  }
 
  public void testaddtask2(string name) {
    int count = addtask(new callable<integer>() {
      @override
      public integer call() throws exception {
        for (int i = 0; i < 3; i++) {
          if (main.surplus <= 0)
            return 0;
          main.surplus--;
          system.out.println(name + " " + main.surplus);
        }
        return main.surplus;
      }
    });
 
  }
 
  public void close() {
    executor.shutdown();
  }
 
  public static void main(string[] args) {
    main main = new main();
    main.testaddtask("task1");
    main.testaddtask2("task2");
    main.testaddtask("task3");
    main.testaddtask2("task4");
    main.close();
  }
}

在这里,我们定义了两种方法,分别是addtask,具有泛型的addtask,这两种方法实现原理都是一样的,其中一个是有回调的,一个是没有回调的,就看项目需求了吧。

详解Java利用ExecutorService实现同步执行大量线程

然后分别调用这两个方法咯,就可以看到结果是非常有序,且不会混乱的。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持服务器之家。

原文链接:http://www.jianshu.com/p/ccdb616723ab

相关文章

热门资讯

2020微信伤感网名听哭了 让对方看到心疼的伤感网名大全
2020微信伤感网名听哭了 让对方看到心疼的伤感网名大全 2019-12-26
Intellij idea2020永久破解,亲测可用!!!
Intellij idea2020永久破解,亲测可用!!! 2020-07-29
歪歪漫画vip账号共享2020_yy漫画免费账号密码共享
歪歪漫画vip账号共享2020_yy漫画免费账号密码共享 2020-04-07
最新idea2020注册码永久激活(激活到2100年)
最新idea2020注册码永久激活(激活到2100年) 2020-07-29
iPhone12什么时候上市 iPhone12手机真实图片 苹果iphone12多少钱
iPhone12什么时候上市 iPhone12手机真实图片 苹果iphone12多少钱 2020-06-03
返回顶部