- 浏览: 1089930 次
- 性别:
- 来自: 成都
文章分类
最新评论
-
skyesx:
这是2PC实现,更常用的是一个柔性事务的实现,可以参考http ...
Spring分布式事务实现 -
ddbird:
这第一句就不严谨“分布式事务是指操作多个数据库之间的事务”,显 ...
Spring分布式事务实现 -
呵呵6666:
基于互联网支付系统的微服务架构分布式事务解决方案http:// ...
Spring分布式事务实现 -
小黄牛:
写得不错,交流群:472213887
Spring分布式事务实现 -
jiaoqf321456:
这明明是用的apache的压缩,给ant.jar有半毛钱关系吗 ...
使用ant.jar进行文件zip压缩
说明:Servlet也是多线程结构。servlet类中定义的成员变量,被所有的客户线程共享。当容器同时收到对同一Servlet的多个请求,那这个Servlet的service方法将在多线程中并发的执行。
一、线程池示例
(1)threadpool.xml
(2)解析XML文件
(3)工作线程
(4)管理线程池
(5)调用
(6)具有线程池的工作队列
我们通常想要的是同一组固定的工作线程相结合的工作队列,它使用 wait() 和 notify() 来通知等待线程新的工作已经到达了。该工作队列通常被实现成具有相关监视器对象的某种链表。
大多数专家建议使用 notifyAll() 而不是 notify() ,而且理由很充分:使用 notify() 具有难以捉摸的风险,只有在某些特定条件下使用该方法才是合适的。另一方面,如果使用得当, notify() 具有比 notifyAll() 更可取的性能特征;特别是, notify() 引起的环境切换要少得多,这一点在服务器应用程序中是很重要的。
二、如何停止线程
(1)运行状态下,通过置一个volatile变量值来结束一个循环线程。
(2)非运行状态下(调用sleep,wait,或者被I/O阻塞,可能是文件或者网络等等),使用interrupt(),让线程在run方法中停止。
当interrupt()被调用的时候,InterruptedException将被抛出,所以你可以再run方法中捕获这个异常,让线程安全退出:
当线程被I/O阻塞的时候,调用interrupt()的情况是依赖与实际运行的平台的。在Solaris和Linux平台上将会抛出InterruptedIOException的异常,但是Windows上面不会有这种异常。所以,我们处理这种问题不能依靠于平台的实现。
也可以使用InterruptibleChannel接口。 实现了InterruptibleChannel接口的类可以在阻塞的时候抛出ClosedByInterruptException。
需要注意一点,当线程处于写文件的状态时,调用interrupt()不会中断线程。
(3)一个示例
三、关于volatile
volatile是一个类型修饰符(type specifier)。它是被设计用来修饰被不同线程访问和修改的变量。如果没有volatile,基本上会导致这样的结果:要么无法编写多线程程序,要么编译器失去大量优化的机会。
一般说来,volatile用在如下的几个地方:
1、中断服务程序中修改的供其它程序检测的变量需要加volatile;
2、多任务环境下各任务间共享的标志应该加volatile;
3、存储器映射的硬件寄存器通常也要加volatile说明,因为每次对它的读写都可能由不同意义;
一、线程池示例
(1)threadpool.xml
<?xml version="1.0" encoding="UTF-8"?> <config> <threadPool> <minPools>10</minPools> <!--线程池最小线程--> <maxPools>100</maxPools> <!--线程池最大线程--> <checkThreadPeriod>5</checkThreadPeriod> <!--检查线程池中线程的周期5分钟--> </threadPool> </config>
(2)解析XML文件
import java.io.InputStream; import java.util.Iterator; import org.dom4j.Document; import org.dom4j.Element; import org.dom4j.io.SAXReader; import org.springframework.core.io.ClassPathResource; public class XMLReader { private Document document; private static final XMLReader instance = new XMLReader(); /** * 私有的默认构造子 */ private XMLReader() { loadXML(); } /** * 静态工厂方法 */ public static XMLReader getInstance() { return instance; } private void loadXML(){ InputStream is = null; SAXReader reader =null; try { is = (new ClassPathResource("threadpool.xml")).getInputStream(); reader = new SAXReader(); document = reader.read(is); is.close(); } catch (Exception e) { e.printStackTrace(); } } /** * 读取指定值 * @param name * @return */ public String getThreadPoolPara(String name){ String str = ""; try { Element root = document.getRootElement(); // 获得根元素 Iterator lv = root.elementIterator("threadPool"); Element el = null; while (lv.hasNext()) { el = (Element) lv.next(); str = el.element(name).getText(); } } catch (Exception e) { System.out.println(e.toString()); } return str; } }
(3)工作线程
class WorkThread extends Thread { private boolean runningFlag; private String argument; public boolean isRunning() { return runningFlag; } public synchronized void setRunning(boolean flag) { runningFlag = flag; if (flag) this.notify(); } public String getArgument() { return this.argument; } public void setArgument(String string) { argument = string; } public WorkThread(int threadNumber) { runningFlag = false; System.out.println("thread " + threadNumber + "started."); } public synchronized void run() { try { while (true) { if (!runningFlag) { this.wait(); } else { System.out.println("processing " + getArgument() + "... done."); sleep(5000); System.out.println("Thread is sleeping..."); setRunning(false); } } } catch (InterruptedException e) { System.out.println("Interrupt"); } } }
(4)管理线程池
import java.util.*; class ThreadPoolManager { private int maxPools; private int minPools; private int checkThreadPeriod; // private java.util.Timer timer = null; public Vector vector; @SuppressWarnings("unchecked") public ThreadPoolManager() { setMaxPools(Integer.parseInt(XMLReader.getInstance().getThreadPoolPara("maxPools"))); setMinPools(Integer.parseInt(XMLReader.getInstance().getThreadPoolPara("minPools"))); setCheckThreadPeriod(Integer.parseInt(XMLReader.getInstance().getThreadPoolPara("checkThreadPeriod"))); System.out.println("Starting thread pool..."); vector = new Vector(); for (int i = 1; i <= minPools; i++) { WorkThread thread = new WorkThread(i); vector.addElement(thread); thread.start(); } // timer = new Timer(true); // timer.schedule(new CheckThreadTask(this),0,checkThreadPeriod); } @SuppressWarnings("unchecked") public void process(String argument) { int i; for (i = 0; i < vector.size(); i++) { WorkThread currentThread = (WorkThread) vector.elementAt(i); if (!currentThread.isRunning()) { System.out.println("Thread " + (i + 1) + " is processing:" + argument); currentThread.setArgument(argument); currentThread.setRunning(true); return; } if(i == vector.size()-1){//没的空闲线程了,就新建一个 if(vector.size() < maxPools){ WorkThread thread = new WorkThread(i); vector.addElement(thread); thread.setArgument(argument); thread.setRunning(true); thread.start(); } } } if (i == maxPools) { System.out.println("pool is full, try in another time."); } } public int getCheckThreadPeriod() { return checkThreadPeriod; } public void setCheckThreadPeriod(int checkThreadPeriod) { this.checkThreadPeriod = checkThreadPeriod; } public int getMaxPools() { return maxPools; } public void setMaxPools(int maxPools) { this.maxPools = maxPools; } public int getMinPools() { return minPools; } public void setMinPools(int minPools) { this.minPools = minPools; } }// end of class ThreadPoolManager
(5)调用
public static void main(String[] args) { try { BufferedReader br = new BufferedReader(new InputStreamReader( System.in)); String s; ThreadPoolManager manager = new ThreadPoolManager(); while ((s = br.readLine()) != null) { manager.process(s); } } catch (IOException e) { } }
(6)具有线程池的工作队列
我们通常想要的是同一组固定的工作线程相结合的工作队列,它使用 wait() 和 notify() 来通知等待线程新的工作已经到达了。该工作队列通常被实现成具有相关监视器对象的某种链表。
public class WorkQueue { private final int nThreads; private final PoolWorker[] threads; private final LinkedList queue; public WorkQueue(int nThreads) { this.nThreads = nThreads; queue = new LinkedList(); threads = new PoolWorker[nThreads]; for (int i=0; i<nThreads; i++) { threads[i] = new PoolWorker(); threads[i].start(); } } public void execute(Runnable r) { synchronized(queue) { queue.addLast(r); queue.notify(); } } private class PoolWorker extends Thread { public void run() { Runnable r; while (true) { synchronized(queue) { while (queue.isEmpty()) { try { queue.wait(); } catch (InterruptedException ignored) { } } r = (Runnable) queue.removeFirst(); } // If we don't catch RuntimeException, // the pool could leak threads try { r.run(); } catch (RuntimeException e) { // You might want to log something here } } } } }
大多数专家建议使用 notifyAll() 而不是 notify() ,而且理由很充分:使用 notify() 具有难以捉摸的风险,只有在某些特定条件下使用该方法才是合适的。另一方面,如果使用得当, notify() 具有比 notifyAll() 更可取的性能特征;特别是, notify() 引起的环境切换要少得多,这一点在服务器应用程序中是很重要的。
二、如何停止线程
(1)运行状态下,通过置一个volatile变量值来结束一个循环线程。
(2)非运行状态下(调用sleep,wait,或者被I/O阻塞,可能是文件或者网络等等),使用interrupt(),让线程在run方法中停止。
当interrupt()被调用的时候,InterruptedException将被抛出,所以你可以再run方法中捕获这个异常,让线程安全退出:
try { .... wait(); } catch (InterruptedException iex) { throw new RuntimeException("Interrupted",iex); }
当线程被I/O阻塞的时候,调用interrupt()的情况是依赖与实际运行的平台的。在Solaris和Linux平台上将会抛出InterruptedIOException的异常,但是Windows上面不会有这种异常。所以,我们处理这种问题不能依靠于平台的实现。
也可以使用InterruptibleChannel接口。 实现了InterruptibleChannel接口的类可以在阻塞的时候抛出ClosedByInterruptException。
需要注意一点,当线程处于写文件的状态时,调用interrupt()不会中断线程。
(3)一个示例
import java.io.BufferedReader; import java.io.FileDescriptor; import java.io.FileInputStream; import java.io.InputStream; import java.io.InputStreamReader; import java.nio.channels.Channels; public class InterruptInput { static BufferedReader in = new BufferedReader( new InputStreamReader( Channels.newInputStream( (new FileInputStream(FileDescriptor.in)).getChannel()))); public static void main(String args[]) { try { System.out.println("Enter lines of input (user ctrl+Z Enter to terminate):"); System.out.println("(Input thread will be interrupted in 10 sec.)"); // interrupt input in 10 sec (new TimeOut()).start(); String line = null; while ((line = in.readLine()) != null) { System.out.println("Read line:'"+line+"'"); } } catch (Exception ex) { System.out.println(ex.toString()); // java.nio.channels.ClosedChannelException } } public static class TimeOut extends Thread { int sleepTime = 10000; Thread threadToInterrupt = null; public TimeOut() { // interrupt thread that creates this TimeOut. threadToInterrupt = Thread.currentThread(); setDaemon(true); } public void run() { try { sleep(10000); // wait 10 sec } catch(InterruptedException ex) {/*ignore*/} threadToInterrupt.interrupt(); } } }
三、关于volatile
volatile是一个类型修饰符(type specifier)。它是被设计用来修饰被不同线程访问和修改的变量。如果没有volatile,基本上会导致这样的结果:要么无法编写多线程程序,要么编译器失去大量优化的机会。
一般说来,volatile用在如下的几个地方:
1、中断服务程序中修改的供其它程序检测的变量需要加volatile;
2、多任务环境下各任务间共享的标志应该加volatile;
3、存储器映射的硬件寄存器通常也要加volatile说明,因为每次对它的读写都可能由不同意义;
发表评论
-
使用zxing.jar生成二维码
2015-10-15 13:52 01、ZxingCodeUtils /** * 使用Zx ... -
Java生成条形码与二维码
2015-09-29 11:02 0一、一维条形码 /** * 利用jbarcode.ja ... -
将html特殊码( &#x)转换成字符
2015-06-09 11:54 0public static void main(St ... -
Java多线程编程
2013-10-16 13:45 0一、线程安全的延迟初始化 1、基于volatile的双重检查锁 ... -
Java常用方法整理
2013-06-13 16:00 01、判断是否为中文字符 /** * 判断是否为中文 ... -
使用servicemix实现FTP连接池
2013-06-13 13:17 0一、配置文件 <?xml version=" ... -
嵌入式运行HttpServer
2015-06-30 13:14 1690一、嵌入式运行Jetty并提供上传文件功能 1、定义处理请求的 ... -
使用Quartz执行定时任务
2012-05-24 11:00 0一、在application中运用 (1)定义任务 pac ... -
Java内存泄漏分析与解决方案
2012-03-18 13:49 0作为Internet最流行的编程语言之一,Java现正非常 ... -
java访问FtpSever
2011-10-09 15:18 0使用apache common-net包来实现。 ... -
JNI(Java Native Interface)的使用
2015-06-30 13:12 3220Java JNI是Java Native Interf ... -
Java Regular Expressions Syntax
2009-07-22 20:54 3008一、正则表达式语法 1. ... -
jsp custom taglib
2009-07-10 12:20 01.java文件 public class Repeate ... -
java filter
2009-07-10 12:13 17268过滤器Filter也具有生命周期:init()-> ... -
HTTP 头部详细解释
2009-07-09 11:46 01. Accept:告诉WEB服务器 ... -
JavaMail读发邮件
2009-07-07 14:04 6225一、基本概念: SMTP(Simple Mail Tra ... -
java 验证码/Checked vs UnChecked Exception
2009-06-15 10:54 2260<一>、Java生成验证码图片 1.Servlet ... -
jsp统计在线人数和在线注册人数
2009-05-31 12:50 9135一、统计在线人数 1.监 ... -
Java TimeZone
2009-04-15 16:32 28862protected static Format form ... -
JPA是什么
2009-03-28 18:59 2388JPA全称为Java Persiste ...
相关推荐
java 线程池 学习代码,想学线程池的可以参考一下
Reference: 《创建Java线程池》[1],《Java线程:新特征-线程池》[2], 《Java线程池学习》[3],《线程池ThreadPoolExecutor使用简介》[4],《Java5中的线程池实例讲解》[5],《ThreadPoolExecutor使用和思考》[6] ...
NULL 博文链接:https://lhgyy00.iteye.com/blog/450628
主要给大家介绍了关于java线程池使用后到底要不要关闭的相关资料,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
java技术学习——基于Java线程池技术实现Knock Knock游戏项目(包含服务端、客户端两部分) java技术学习——基于Java线程池技术实现Knock Knock游戏项目(包含服务端、客户端两部分) java技术学习——基于Java...
文档中详细描述了线程池的各个知识点,并把相应知识点的源码也有标出。也会涉及到tomcat及netty自建线程池与jdk原生的区别与联系;线程池中线程抛异常,新建,回收等细节点描述。比较全面。
自定义实现Java线程池,学习大师设计思想,瞻仰大神笔法
NULL 博文链接:https://lhgyy00.iteye.com/blog/452050
——学习参考资料:仅用于个人学习使用! 本代码仅作学习交流,切勿用于商业用途,否则后果自负。若涉及侵权,请联系,会尽快处理! 未进行详尽测试,请自行调试!
相对系统的了解java 线程池的知识点
Java多线程是一块重要的内容,李兴华讲解的Java是一个很好的资源
这部分代码就不再追踪下去,有兴趣的读者可以自己打开源码分析,不必害怕,学习大神们的编码方式,看源码能让你学习到很多 } } private void runTask(Runnable task) { final ReentrantLock runLock = this....
java线程池源码 cThreadPool 项目描述:对java.util.concurrent包下线程池相关源码进行重新实现,深入研究和学习线程池超时机制、饱和策略、生命周期等知识 ThreadPoolExecutor类下部分方法和内部类介绍: 1、Worker...
线程池模板 (可以让你快速地使用线程池技术) 帮助你学习线程池
聊聊并发(3)Java线程池的分析和使用Java开发Java经验技巧共7页.pdf.zip
NULL 博文链接:https://wentry.iteye.com/blog/1873521
主要介绍了Java 线程池的相关资料,并符实例代码,帮助大家学习参考,需要的朋友可以参考下
主要介绍了Java线程池的拒绝策略实现详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
主要介绍了java 定时器线程池(ScheduledThreadPoolExecutor),文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
主要介绍了Java 线程池的相关资料,帮助大家更好的理解和学习Java,感兴趣的朋友可以了解下