- 浏览: 250125 次
- 性别:
- 来自: 上海
文章分类
最新评论
-
探索者_技术:
不错 讲解的比较详细
Java 执行过程详解 - JVM 生命周期 -
besterzhao:
学习了
关于 sun.misc.Unsafe -
lliiqiang:
属性变量被设定为不可更改的,外界传递的对象复制一份再保存到对象 ...
不可变类(immutable class) -
xunke515:
有启发.感谢
Java System 类详解 - in, out, err -
bo_hai:
你说没错。问题是:怎么样把ClassA中的事务传播到Class ...
Spring 事务在多线程环境下的传播
我觉得要清理一下关于进程和线程的基本概念。
首先就是进程。
什么是进程呢?简单的说就是cpu的一个执行过程,在这个过程中,os为它分配独立的内存空间,这样就保证不被别的进程影响。单任务的os就是说多个进程间只能顺序的执行,也就是说多个事情只能一件一件的做。那么多任务的os支持多个进程交叉同时执行。为什么要这样呢?学过统筹方法吗?如果没有,你是不是经常同事做两件事情?比如在打开电脑的同时,你在吃早点。cpu也是一样的,比如当cpu通过打印机打印的时候,让打印机自己忙去,cpu还可以同时干点别的事情。这样就理解多进程的原因了。
那么什么是多线程呢?
线程也是一个执行过程,只是比进程的粒度更小。在一个进程中可以同时多个线程交叉进行。不同的是,线程并没有向进程那样享有单独的地址空间,而是给你共享这个进程所在的地址空间。
那么为什么还要划分比进程粒度更小的执行过程呢?
在现在os中,支持线程调度,那么线程就成了任务调度的单位。不过进程确实资源分配的单位。
多进程系统可以同时运行多个进程,但是每一个进程只能有一个线程。多线程系统允许运行多个线程,但是统一进程内的所有的线程共享相同的地址空间和系统资源。
不管多进程也好,多线程也好都是为了并发。并发的好处除了加快处理任务外,还有一个好处就是为了更好的设计。比如当你copy文件的时候,你不想copy了,你可以中途取消,这就是并发带来的好处,这个需求是很简单直观的,但如果没有并发技术的支持,在计算机技术里面是很难实现的。没有并发,计算机就会变的一根筋。
在Java里面又是怎么做的呢?
首先,既然是多任务同时进行,得先定义任务。在Java里面定义一个任务很简单,只要让这个类实现Runnable 接口。同时实现这个接口的唯一的一个run()方法。这个有点类似command模式。在run方法里面定义这个任务要完成的事情。
你肯定知道输出是什么,这里句话肯定会顺序输出:
I am a task running
I am in main
这个Runnable接口实在没有什么特别的:
你看,和普通的接口有什么区别?在main方法里面调用,就和一般的类没有什么区别。只是它总是和多线程绑在一起,才显得神秘。既然没有什么特别的,那就怎么让它实现并发呢?那就得把这个task挂在一个线程上:
你认为上面的代码会输出什么?
I am in main
I am a task running
这两句话,不一定哪个先输出。这就是并发导致的,当调用start方法的时候,就会启动一个新的线程和当前正在运行的主线程并发执行,他们会争抢cpu,看谁快。所以输出的顺序无法预知。
你因该注意到了,在构造Thread的时候我们把task传给了他,那时因为它接收Runnable接口。他会在start方法之后调用这个参数对象的run方法。这是不是command模式?
所以说,任何类都可以放在Thread里面去并发运行,只要实现Runnable接口,编写自己的run方法,高速线程,你想干什么。说道这里视乎线程也没有那么什么了,只是他会并发的调用task的run方法。
从Jdk5以后,jdk给我们提供过来更方便的多线程实现工具包java.util.concurrent提供了一些有用的并发编程框架和工具类。
Executor
执行器,是一个简单的标准化的接口,提供线程似的子系统,比如线程池,异步IO以及轻量级的任务框架。
有了这个包,你不用再自己管理Thread的生命周期。而是托管给ExecutorService。ExecutorService可以帮你调度并发任务,你只要调用它的execute方法,你一下他的execute方法,也是按照Command模式设计的。ExecutorService 也是一个接口,并且实现了Executor接口。除了包含Executor方法外,ExecutorService 还定义了其他一些方法:
Executors是一个静态工厂类,提供了很多创建各种ExecutorService的工厂方法。
线程池
如果某些资源的创建比较费劲,也就耗费时间和资源,那就得考虑用pool也就是池来保存一些预先创建好的资源,用的时候拿来用,用完放回去。典型的有jdbc连接池。线程池也算一个。
Executors就提供了各种各项的线程池共你选择:
1. CachedThreadPool
这种线程池会不停的为你创建新的线程,只要当前pool里面没有可用的。这个其实很危险,很容易耗尽你的资源。
2. FixedThreadPool
这个线程池的策略是为你保持指定大小的线程数,这个还算比较好控制,任务比线程数多的时候就排队等候。
3. SingleThreadExecutor
其实就是固定大小为一的FixedThreadPool。这个策略也很有用。当你只想用一个线程完成一系列任务的时候,就可以用它为你维护你可以任务队列,他会帮你一次顺序调用。完成一件,在做下一件。
首先就是进程。
什么是进程呢?简单的说就是cpu的一个执行过程,在这个过程中,os为它分配独立的内存空间,这样就保证不被别的进程影响。单任务的os就是说多个进程间只能顺序的执行,也就是说多个事情只能一件一件的做。那么多任务的os支持多个进程交叉同时执行。为什么要这样呢?学过统筹方法吗?如果没有,你是不是经常同事做两件事情?比如在打开电脑的同时,你在吃早点。cpu也是一样的,比如当cpu通过打印机打印的时候,让打印机自己忙去,cpu还可以同时干点别的事情。这样就理解多进程的原因了。
那么什么是多线程呢?
线程也是一个执行过程,只是比进程的粒度更小。在一个进程中可以同时多个线程交叉进行。不同的是,线程并没有向进程那样享有单独的地址空间,而是给你共享这个进程所在的地址空间。
那么为什么还要划分比进程粒度更小的执行过程呢?
在现在os中,支持线程调度,那么线程就成了任务调度的单位。不过进程确实资源分配的单位。
多进程系统可以同时运行多个进程,但是每一个进程只能有一个线程。多线程系统允许运行多个线程,但是统一进程内的所有的线程共享相同的地址空间和系统资源。
不管多进程也好,多线程也好都是为了并发。并发的好处除了加快处理任务外,还有一个好处就是为了更好的设计。比如当你copy文件的时候,你不想copy了,你可以中途取消,这就是并发带来的好处,这个需求是很简单直观的,但如果没有并发技术的支持,在计算机技术里面是很难实现的。没有并发,计算机就会变的一根筋。
在Java里面又是怎么做的呢?
首先,既然是多任务同时进行,得先定义任务。在Java里面定义一个任务很简单,只要让这个类实现Runnable 接口。同时实现这个接口的唯一的一个run()方法。这个有点类似command模式。在run方法里面定义这个任务要完成的事情。
public class HelloTask implements Runnable { @Override public void run() { System.out.println("I am a task running"); } public static void main(String[] args) { HelloTask task = new HelloTask(); task.run(); System.out.println("I am in main"); } }
你肯定知道输出是什么,这里句话肯定会顺序输出:
引用
I am a task running
I am in main
这个Runnable接口实在没有什么特别的:
public interface Runnable { public abstract void run(); }
你看,和普通的接口有什么区别?在main方法里面调用,就和一般的类没有什么区别。只是它总是和多线程绑在一起,才显得神秘。既然没有什么特别的,那就怎么让它实现并发呢?那就得把这个task挂在一个线程上:
public class HelloTask implements Runnable { @Override public void run() { System.out.println("I am a task running"); } public static void main(String[] args) { HelloTask task = new HelloTask(); Thread t = new Thread(task); t.start(); System.out.println("I am in main"); } }
你认为上面的代码会输出什么?
引用
I am in main
I am a task running
这两句话,不一定哪个先输出。这就是并发导致的,当调用start方法的时候,就会启动一个新的线程和当前正在运行的主线程并发执行,他们会争抢cpu,看谁快。所以输出的顺序无法预知。
你因该注意到了,在构造Thread的时候我们把task传给了他,那时因为它接收Runnable接口。他会在start方法之后调用这个参数对象的run方法。这是不是command模式?
所以说,任何类都可以放在Thread里面去并发运行,只要实现Runnable接口,编写自己的run方法,高速线程,你想干什么。说道这里视乎线程也没有那么什么了,只是他会并发的调用task的run方法。
从Jdk5以后,jdk给我们提供过来更方便的多线程实现工具包java.util.concurrent提供了一些有用的并发编程框架和工具类。
Executor
执行器,是一个简单的标准化的接口,提供线程似的子系统,比如线程池,异步IO以及轻量级的任务框架。
public class HelloTask implements Runnable { private static int taskCount = 0; private final int id = taskCount++; @Override public void run() { System.out.println("I am a task running: " + id); } public static void main(String[] args) { ExecutorService exec = Executors.newCachedThreadPool(); for (int i = 0; i < 5; i++) { exec.execute(new HelloTask()); } exec.shutdown(); System.out.println("I am in main"); } }
有了这个包,你不用再自己管理Thread的生命周期。而是托管给ExecutorService。ExecutorService可以帮你调度并发任务,你只要调用它的execute方法,你一下他的execute方法,也是按照Command模式设计的。ExecutorService 也是一个接口,并且实现了Executor接口。除了包含Executor方法外,ExecutorService 还定义了其他一些方法:
public interface ExecutorService extends Executor { void shutdown(); <T> Future<T> submit(Callable<T> task); <T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks) throws InterruptedException; ... } public interface Executor { void execute(Runnable command); }
Executors是一个静态工厂类,提供了很多创建各种ExecutorService的工厂方法。
线程池
如果某些资源的创建比较费劲,也就耗费时间和资源,那就得考虑用pool也就是池来保存一些预先创建好的资源,用的时候拿来用,用完放回去。典型的有jdbc连接池。线程池也算一个。
Executors就提供了各种各项的线程池共你选择:
1. CachedThreadPool
这种线程池会不停的为你创建新的线程,只要当前pool里面没有可用的。这个其实很危险,很容易耗尽你的资源。
2. FixedThreadPool
这个线程池的策略是为你保持指定大小的线程数,这个还算比较好控制,任务比线程数多的时候就排队等候。
3. SingleThreadExecutor
其实就是固定大小为一的FixedThreadPool。这个策略也很有用。当你只想用一个线程完成一系列任务的时候,就可以用它为你维护你可以任务队列,他会帮你一次顺序调用。完成一件,在做下一件。
发表评论
-
Spring 源码学习 - ClassPathXmlApplicationContext
2012-05-06 11:47 6682众所周知,Spring以其强大而又灵活的IoC管理功能著称。I ... -
从appfuse开始学习Spring和Hibernate - (2)Spring启动log
2012-05-05 21:35 2359分析appfuse的详细的启动日志来看看Spring的启动过程 ... -
从appfuse开始学习Spring和Hibernate - (1)构建项目
2012-05-05 15:54 6390千里之行,始于足下。结合例子学习概念,比较靠谱。本文介绍如何开 ... -
Spring 事务在多线程环境下的传播
2012-05-04 21:42 8795有时候需要使用多线程来提高对于CPU,尤其是多核CPU的利用率 ... -
关于Hashtable和HashMap, Vector和ArrayList
2012-05-01 09:41 1912在功能上讲Hashtable和HashMap, Vector和 ... -
JVisualVM还真是不错
2012-04-27 21:38 1617最近再看Java 性能的问题。一直都习惯使用Jconsole和 ... -
Java String 详解 - String Literal
2012-04-08 14:23 2323为了性能和内存资源上 ... -
Java Management Extensions (JMX) 学习笔记- 程序管理和监控
2012-04-07 20:25 4214在学习Tomcat 7 的源代码的时候发现,大量运用到了JMX ... -
Tomcat 7 源码分析 - 初始化 class loader
2012-04-07 19:24 2393Bootstrap 在启动的时候初 ... -
Tomcat 7 源码分析 - 启动概览 bootstrap
2012-04-07 14:57 2356先大致浏览一下整个启 ... -
Tomcat 7 源码分析 - 下载 tomcat source code 并导入eclipse
2012-04-07 09:23 17418准备好好研究学习一下tomcat 7 的源代码,那么第一步就是 ... -
Java Generic 学习
2012-04-06 19:34 1542泛型是Java 5开始引入的一个语言级别的特性 ... -
Java 执行过程详解 - JVM 生命周期
2012-04-04 12:01 8641Java的执行过程也就是JVM从启动到退出的过程。JVM的运行 ... -
Java System 类详解 - properties and environment variables
2012-04-04 11:32 2477在环境配置中我们经常需要知道或者设置系统属性值和环境变量。系统 ... -
Java System 类详解 - arraycopy
2012-04-04 11:01 2506System类提供了数组copy函数: public ... -
Java System 类详解 - in, out, err
2012-04-04 07:46 10450几乎所有的都用过这个System类吧,因为大家学习的第一个语句 ... -
关于 sun.misc.Unsafe
2012-04-03 15:31 4592今天在看java.util.concurrent.atomic ... -
如何提高代码质量
2012-04-02 20:08 1160本文是写给开 ... -
在Java中什么是 Primitive 和 Reference 类型
2012-03-24 23:14 2839Java虽然是个面向对象的语言,也声称“Everything ... -
Java 并发编程 - Programming Concurrency on the JVM
2012-03-24 23:08 3456这几个月一直在做性能调优的工作,以前总是进行功能的开发,从来不 ...
相关推荐
java.util.concurrent-多线程框架
title: 3-1-案例-售票&线程状态- Java多线程基础- Java多线程案例categories: Java多线程基础售票案例线程状态售票的动作需要被
JavaEE源代码 concurrent-1.3.2JavaEE源代码 concurrent-1.3.2JavaEE源代码 concurrent-1.3.2JavaEE源代码 concurrent-1.3.2JavaEE源代码 concurrent-1.3.2JavaEE源代码 concurrent-1.3.2JavaEE源代码 concurrent-...
- copy %AXIS2_HOME%\lib\backport-util-concurrent-3.1.jar 到%ECLIPSE_HOME%\plugins\Axis2_Codegen_Wizard_1.3.0\lib - 注册此 jar 包: 編輯 %ECLIPSE_HOME%\plugins\Axis2_Codegen_Wizard_1.3.0\plugin.xml , ...
Java-concurrent-collections-concurrenthashmap-blockingqueue.pdf
//d2这个线程开启,多了一条执行路径//由主线程执行// * 主线程出异常会导致其所在线程结束但是不会影响其他线程的执行// * Exception in t
官方版本,亲测可用
An error ocCurred while completing process -java.lang.reflect.InvocationTargetException (1).关闭 Eclipse (2).copy %AXIS2_HOME%\lib\ 下的 backport-util-concurrent-3.1.jar 和 geronimo-stax-api_1.0_...
concurrent-1.3.2.jar concurrent-1.3.2.jar
Concurrent-Utils Utilities for Java concurrent library. This is a library contains some useful and smart utility class for Java concurrent library. Shelly, HermesEventBus and AndroidDataStorage are ...
concurrent-1.3.4.jar
concurrent-all-in-one.pdf
concurrent-1.3.4-sources.jar
An error ocCurred while completing process -java.lang.reflect.InvocationTargetException 解决用到的jar包,两个jar包在backport-util-concurrent-3.1.jar和geronimo-stax-api_1.0_spec-1.0.1.jar.zip的压缩文件...
Concurrent - Programming in Java.pdf,ppt,Doug Lea
非守护线程创建的线程默认为非守护线程,守护则默认为守护线程优先级(priority)优先级高的线程可以得到更多cpu资源, 级别是1-10,默认优先级和创建他的
backport-util-concurrent.jarbackport-util-concurrent.jarbackport-util-concurrent.jar