天天看点

spring线程池ThreadPoolExecutor配置并且得到任务执行的结果

用的ThreadPoolExecutor的时候,又想知道被执行的任务的执行情况,这时就可以用FutureTask。

ThreadPoolTask

<code>01</code>

<code>package</code> <code>com.zuidaima.threadpool;</code>

<code>02</code>

<code>03</code>

<code>import</code> <code>java.io.Serializable;</code>

<code>04</code>

<code>import</code> <code>java.util.concurrent.Callable;</code>

<code>05</code>

<code>06</code>

<code>public</code> <code>class</code> <code>ThreadPoolTask </code><code>implements</code> <code>Callable&lt;String&gt;, Serializable {</code>

<code>07</code>

<code>08</code>

<code>    </code><code>private</code> <code>static</code> <code>final</code> <code>long</code> <code>serialVersionUID = </code><code>0</code><code>;</code>

<code>09</code>

<code>10</code>

<code>    </code><code>// 保存任务所需要的数据</code>

<code>11</code>

<code>    </code><code>private</code> <code>Object threadPoolTaskData;</code>

<code>12</code>

<code>13</code>

<code>    </code><code>private</code> <code>static</code> <code>int</code> <code>consumeTaskSleepTime = </code><code>2000</code><code>;</code>

<code>14</code>

<code>15</code>

<code>    </code><code>public</code> <code>ThreadPoolTask(Object tasks) {</code>

<code>16</code>

<code>        </code><code>this</code><code>.threadPoolTaskData = tasks;</code>

<code>17</code>

<code>    </code><code>}</code>

<code>18</code>

<code>19</code>

<code>    </code><code>public</code> <code>synchronized</code> <code>String call() </code><code>throws</code> <code>Exception {</code>

<code>20</code>

<code>        </code><code>// 处理一个任务,这里的处理方式太简单了,仅仅是一个打印语句</code>

<code>21</code>

<code>        </code><code>System.out.println(</code><code>"开始执行任务:"</code> <code>+ threadPoolTaskData);</code>

<code>22</code>

<code>        </code><code>String result = </code><code>""</code><code>;</code>

<code>23</code>

<code>        </code><code>// //便于观察,等待一段时间</code>

<code>24</code>

<code>        </code><code>try</code> <code>{</code>

<code>25</code>

<code>            </code><code>// long r = 5/0;</code>

<code>26</code>

<code>            </code><code>for</code> <code>(</code><code>int</code> <code>i = </code><code>0</code><code>; i &lt; </code><code>100000000</code><code>; i++) {</code>

<code>27</code>

<code>28</code>

<code>            </code><code>}</code>

<code>29</code>

<code>            </code><code>result = </code><code>"OK"</code><code>;</code>

<code>30</code>

<code>        </code><code>} </code><code>catch</code> <code>(Exception e) {</code>

<code>31</code>

<code>            </code><code>e.printStackTrace();</code>

<code>32</code>

<code>            </code><code>result = </code><code>"ERROR"</code><code>;</code>

<code>33</code>

<code>        </code><code>}</code>

<code>34</code>

<code>        </code><code>threadPoolTaskData = </code><code>null</code><code>;</code>

<code>35</code>

<code>        </code><code>return</code> <code>result;</code>

<code>36</code>

<code>37</code>

<code>}</code>

模拟客户端提交的线程

<code>import</code> <code>java.util.concurrent.ExecutionException;</code>

<code>import</code> <code>java.util.concurrent.FutureTask;</code>

<code>import</code> <code>java.util.concurrent.TimeUnit;</code>

<code>import</code> <code>org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;</code>

<code>public</code> <code>class</code> <code>StartTaskThread </code><code>implements</code> <code>Runnable {</code>

<code>    </code><code>private</code> <code>ThreadPoolTaskExecutor threadPoolTaskExecutor;</code>

<code>    </code><code>private</code> <code>int</code> <code>i;</code>

<code>    </code><code>public</code> <code>StartTaskThread(ThreadPoolTaskExecutor threadPoolTaskExecutor, </code><code>int</code> <code>i) {</code>

<code>        </code><code>this</code><code>.threadPoolTaskExecutor = threadPoolTaskExecutor;</code>

<code>        </code><code>this</code><code>.i = i;</code>

<code>    </code><code>@Override</code>

<code>    </code><code>public</code> <code>synchronized</code> <code>void</code> <code>run() {</code>

<code>        </code><code>String task = </code><code>"task@ "</code> <code>+ i;</code>

<code>        </code><code>System.out.println(</code><code>"创建任务并提交到线程池中:"</code> <code>+ task);</code>

<code>        </code><code>FutureTask&lt;String&gt; futureTask = </code><code>new</code> <code>FutureTask&lt;String&gt;(</code>

<code>                </code><code>new</code> <code>ThreadPoolTask(task));</code>

<code>        </code><code>threadPoolTaskExecutor.execute(futureTask);</code>

<code>        </code><code>// 在这里可以做别的任何事情</code>

<code>        </code><code>String result = </code><code>null</code><code>;</code>

<code>            </code><code>// 取得结果,同时设置超时执行时间为1秒。同样可以用future.get(),不设置执行超时时间取得结果</code>

<code>            </code><code>result = futureTask.get(</code><code>1000</code><code>, TimeUnit.MILLISECONDS);</code>

<code>        </code><code>} </code><code>catch</code> <code>(InterruptedException e) {</code>

<code>            </code><code>futureTask.cancel(</code><code>true</code><code>);</code>

<code>        </code><code>} </code><code>catch</code> <code>(ExecutionException e) {</code>

<code>            </code><code>// 超时后,进行相应处理</code>

<code>38</code>

<code>        </code><code>} </code><code>finally</code> <code>{</code>

<code>39</code>

<code>            </code><code>System.out.println(</code><code>"task@"</code> <code>+ i + </code><code>":result="</code> <code>+ result);</code>

<code>40</code>

<code>41</code>

<code>42</code>

<code>43</code>

SPRING配置文件

<code>&lt;?xml version=</code><code>"1.0"</code> <code>encoding=</code><code>"UTF-8"</code><code>?&gt;</code>

<code>&lt;beans xmlns=</code><code>"http://www.springframework.org/schema/beans"</code>

<code>    </code><code>xmlns:xsi=</code><code>"http://www.w3.org/2001/XMLSchema-instance"</code> <code>xmlns:mvc=</code><code>"http://www.springframework.org/schema/mvc"</code>

<code>    </code><code>xmlns:aop=</code><code>"http://www.springframework.org/schema/aop"</code> <code>xmlns:context=</code><code>"http://www.springframework.org/schema/context"</code>

<code>    </code><code>xsi:schemaLocation="</code>

<code>        </code><code>http:</code><code>//www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd</code>

<code>        </code><code>http:</code><code>//www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd</code>

<code>        </code><code>http:</code><code>//www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd</code>

<code>        </code><code>http:</code><code>//www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd</code>

<code>        </code><code>"&gt;</code>

<code>    </code><code>&lt;bean id=</code><code>"threadPoolTaskExecutor"</code>

<code>        </code><code>class</code><code>=</code><code>"org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor"</code><code>&gt;</code>

<code>        </code><code>&lt;!-- 核心线程数,默认为</code><code>1</code> <code>--&gt;</code>

<code>        </code><code>&lt;property name=</code><code>"corePoolSize"</code> <code>value=</code><code>"10"</code> <code>/&gt;</code>

<code>        </code><code>&lt;!-- 最大线程数,默认为Integer.MAX_VALUE --&gt;</code>

<code>        </code><code>&lt;property name=</code><code>"maxPoolSize"</code> <code>value=</code><code>"50"</code> <code>/&gt;</code>

<code>        </code><code>&lt;!-- 队列最大长度,一般需要设置值&gt;=notifyScheduledMainExecutor.maxNum;默认为Integer.MAX_VALUE</code>

<code>            </code><code>&lt;property name=</code><code>"queueCapacity"</code> <code>value=</code><code>"1000"</code> <code>/&gt; --&gt;</code>

<code>        </code><code>&lt;!-- 线程池维护线程所允许的空闲时间,默认为60s --&gt;</code>

<code>        </code><code>&lt;property name=</code><code>"keepAliveSeconds"</code> <code>value=</code><code>"300"</code> <code>/&gt;</code>

<code>        </code><code>&lt;!-- 线程池对拒绝任务(无线程可用)的处理策略,目前只支持AbortPolicy、CallerRunsPolicy;默认为后者 --&gt;</code>

<code>        </code><code>&lt;property name=</code><code>"rejectedExecutionHandler"</code><code>&gt;</code>

<code>            </code><code>&lt;!-- AbortPolicy:直接抛出java.util.concurrent.RejectedExecutionException异常 --&gt;</code>

<code>            </code><code>&lt;!-- CallerRunsPolicy:主线程直接执行该任务,执行完之后尝试添加下一个任务到线程池中,可以有效降低向线程池内添加任务的速度 --&gt;</code>

<code>            </code><code>&lt;!-- DiscardOldestPolicy:抛弃旧的任务、暂不支持;会导致被丢弃的任务无法再次被执行 --&gt;</code>

<code>            </code><code>&lt;!-- DiscardPolicy:抛弃当前任务、暂不支持;会导致被丢弃的任务无法再次被执行 --&gt;</code>

<code>            </code><code>&lt;bean </code><code>class</code><code>=</code><code>"java.util.concurrent.ThreadPoolExecutor$CallerRunsPolicy"</code> <code>/&gt;</code>

<code>        </code><code>&lt;/property&gt;</code>

<code>    </code><code>&lt;/bean&gt;</code>

<code>&lt;/beans&gt;</code>

测试类

<code>package</code> <code>com.zuidaima.test;</code>

<code>import</code> <code>org.junit.Test;</code>

<code>import</code> <code>org.junit.runner.RunWith;</code>

<code>import</code> <code>org.springframework.beans.factory.annotation.Autowired;</code>

<code>import</code> <code>org.springframework.test.context.ContextConfiguration;</code>

<code>import</code> <code>org.springframework.test.context.junit4.AbstractJUnit4SpringContextTests;</code>

<code>import</code> <code>org.springframework.test.context.junit4.SpringJUnit4ClassRunner;</code>

<code>import</code> <code>com.zuidaima.threadpool.StartTaskThread;</code>

<code>@RunWith</code><code>(SpringJUnit4ClassRunner.</code><code>class</code><code>)</code>

<code>// 指定的运行runner,并且把你所指定的Runner作为参数传递给它</code>

<code>@ContextConfiguration</code><code>(locations = </code><code>"classpath*:applicationContext.xml"</code><code>)</code>

<code>public</code> <code>class</code> <code>TestThreadPool </code><code>extends</code> <code>AbstractJUnit4SpringContextTests {</code>

<code>    </code><code>private</code> <code>static</code> <code>int</code> <code>produceTaskSleepTime = </code><code>10</code><code>;</code>

<code>    </code><code>private</code> <code>static</code> <code>int</code> <code>produceTaskMaxNumber = </code><code>1000</code><code>;</code>

<code>    </code><code>@Autowired</code>

<code>    </code><code>public</code> <code>ThreadPoolTaskExecutor getThreadPoolTaskExecutor() {</code>

<code>        </code><code>return</code> <code>threadPoolTaskExecutor;</code>

<code>    </code><code>public</code> <code>void</code> <code>setThreadPoolTaskExecutor(</code>

<code>            </code><code>ThreadPoolTaskExecutor threadPoolTaskExecutor) {</code>

<code>    </code><code>@Test</code>

<code>    </code><code>public</code> <code>void</code> <code>testThreadPoolExecutor() {</code>

<code>        </code><code>for</code> <code>(</code><code>int</code> <code>i = </code><code>1</code><code>; i &lt;= produceTaskMaxNumber; i++) {</code>

<code>            </code><code>try</code> <code>{</code>

<code>                </code><code>Thread.sleep(produceTaskSleepTime);</code>

<code>            </code><code>} </code><code>catch</code> <code>(InterruptedException e1) {</code>

<code>                </code><code>e1.printStackTrace();</code>

<code>            </code><code>new</code> <code>Thread(</code><code>new</code> <code>StartTaskThread(threadPoolTaskExecutor, i)).start();</code>

<code>44</code>

<code>45</code>

<code>46</code>

<code>47</code>

原文中有些纰漏,我已经修改

项目截图(基于行家构建)

spring线程池ThreadPoolExecutor配置并且得到任务执行的结果

运行截图:

spring线程池ThreadPoolExecutor配置并且得到任务执行的结果

如果遇到CPU忙执行超过1秒的会返回空

spring线程池ThreadPoolExecutor配置并且得到任务执行的结果