Java线程----概念,创建
一.概念(定义)
1 . 进程 :是操作系统中运行的一个任务。进程是指一个内存中运行的应用程序,每个进程都有自己独立的一块内存空间,一个进程中可以启动多个线程。比如在Windows系统中,一个运行的exe就是一个进程。
2 . 线程 :是进程的一个顺序执行流。线程是指进程中的一个执行流程,一个进程中可以运行多个线程。比如java.exe进程中可以运行很多线程。线程总是属于某个进程,进程中的多个线程共享进程的内存。
- 多线程:指的是这个程序(一个进程)运行时产生了不止一个线程
- 并行与并发:
- 并行:多个cpu实例或者多台机器同时执行一段处理逻辑,是真正的同时。
- 并发:通过cpu调度算法,让用户看上去同时执行,实际上从cpu操作层面不是真正的同时。并发往往在场景中有公用的资源,那么针对这个公用的资源往往产生瓶颈,我们会用TPS或者QPS来反应这个系统的处理能力。
二. 进程与线程的区别
进程和线程的主要差别在于它们是不同的操作系统资源管理方式。进程有独立的地址空间,一个进程崩溃后,在保护模式下不会对其它进程产生影响,而线程只是一个进程中的不同执行路径。线程有自己的堆栈和局部变量,但线程之间没有单独的地址空间,一个线程死掉就等于整个进程死掉,所以多进程的程序要比多线程的程序健壮,但在进程切换时,耗费资源较大,效率要差一些。但对于一些要求同时进行并且又要共享某些变量的并发操作,只能用线程,不能用进程。
1) 简而言之,一个程序至少有一个进程,一个进程至少有一个线程.
2) 线程的划分尺度小于进程,使得多线程程序的并发性高。
3) 另外,进程在执行过程中拥有独立的内存单元,而多个线程共享内存,从而极大地提高了程序的运行效率。
4) 线程在执行过程中与进程还是有区别的。每个独立的线程有一个程序运行的入口、顺序执行序列和程序的出口。但是线程不能够独立执行,必须依存在应用程序中,由应用程序提供多个线程执行控制。
5) 从逻辑角度来看,多线程的意义在于一个应用程序中,有多个执行部分可以同时执行。但操作系统并没有将多个线程看做多个独立的应用,来实现进程的调度和管理以及资源分配。这就是进程和线程的重要区别。
6).优缺点
线程和进程在使用上各有优缺点:线程执行开销小,但不利于资源的管理和保护;而进程正相反。同时,线程适合于在SMP机器上运行,而进程则可以跨机器迁移。
三 . Java线程的创建及启动
1)继承Thread类(重写run方法来定义线程要执行的任务代码)
1 public class ThreadDemo1 {
2 public static void main(String[] args) {
3 Thread t1 = new MyThread1();
4 Thread t2 = new MyThread2();
5 /*
6 * 启动线程要调用start方法,不要直接调用
7 * run方法。
8 * 当线程启动后,被分配时间片开始运行时会
9 * 自动调用run方法。
10 */
11 t1.start();
12 t2.start();
13 }
14 }
15 /**
16 * 第一种创建线程存在两个不足:
17 * 1:由于java是单继承,所以导致继承了Thread不能
18 * 在继承其他类,在实际开发中经常会出现继承冲突
19 * 问题
20 * 2:由于重写线程run方法,将线程要执行的任务定义
21 * 在了线程中,导致任务与线程有一个耦合关系,
22 * 不利于线程重用。
23 * @author adminitartor
24 *
25 */
26 class MyThread1 extends Thread{
27 public void run(){
28 for(int i=0;i<1000;i++){
29 System.out.println("你是谁啊?");
30 }
31 }
32 }
33 class MyThread2 extends Thread{
34 public void run(){
35 for(int i=0;i<1000;i++){
36 System.out.println("我是查水表的!");
37 }
38 }
39 }
2)实现Runnable接口(单独定义任务)
1 /**
2 * 第二种创建线程的方式
3 * 实现Runnable接口单独定义任务
4 * @author adminitartor
5 *
6 */
7 public class ThreadDemo2 {
8 public static void main(String[] args) {
9 Runnable r1 = new MyRunnable1();
10 Runnable r2 = new MyRunnable2();
11
12 Thread t1 = new Thread(r1);
13 Thread t2 = new Thread(r2);
14
15 t1.start();
16 t2.start();
17 }
18 }
19 class MyRunnable1 implements Runnable{
20 public void run(){
21 for(int i=0;i<1000;i++){
22 System.out.println("你是谁啊?");
23 }
24 }
25 }
26 class MyRunnable2 implements Runnable{
27 public void run(){
28 for(int i=0;i<1000;i++){
29 System.out.println("我是查水表的!");
30 }
31 }
32 }
匿名内部类创建线程
1 /**
2 * 用匿名内部类形式完成线程两种方式的创建
3 * @author adminitartor
4 *
5 */
6 public class ThreadDemo3 {
7 public static void main(String[] args) {
8 //方式一
9 Thread t1 = new Thread(){
10 public void run(){
11 for(int i=0;i<1000;i++){
12 System.out.println("你是谁啊?");
13 }
14 }
15 };
16
17 //方式二
18 Runnable runn = new Runnable(){
19 public void run(){
20 for(int i=0;i<1000;i++){
21 System.out.println("我是查水表的!");
22 }
23 }
24 };
25 Thread t2 = new Thread(runn);
26
27 t1.start();
28 t2.start();
29
30 }
31 }
3)线程池
2 import java.util.concurrent.ExecutorService;
3
4 /**
5 * Java线程:线程池-
6 *
7 * @author 8 */
9 public class Test {
10 public static void main(String[] args) {
11 //创建一个可重用固定线程数的线程池
12 ExecutorService pool = Executors.newFixedThreadPool(2);
13 //创建实现了Runnable接口对象,Thread对象当然也实现了Runnable接口
14 Thread t1 = new MyThread();
15 Thread t2 = new MyThread();
16 Thread t3 = new MyThread();
17 Thread t4 = new MyThread();
18 Thread t5 = new MyThread();
19 //将线程放入池中进行执行
20 pool.execute(t1);
21 pool.execute(t2);
22 pool.execute(t3);
23 pool.execute(t4);
24 pool.execute(t5);
25 //关闭线程池
26 pool.shutdown();
27 }
28 }
29
30 class MyThread extends Thread{
31 @Override
32 public void run() {
33 System.out.println(Thread.currentThread().getName()+"正在执行。。。");
34 }
35 }
输出结果为:
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-2正在执行。。。
Process finished with exit code 0
ExecutorService pool = Executors.newSingleThreadExecutor();
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
Process finished with exit code 0
ExecutorService pool = Executors.newCachedThreadPool();
pool-1-thread-1正在执行。。。
pool-1-thread-4正在执行。。。
pool-1-thread-3正在执行。。。
pool-1-thread-2正在执行。。。
Process finished with exit code 0
1 import java.util.concurrent.Executors;
2 import java.util.concurrent.ScheduledExecutorService;
3 import java.util.concurrent.TimeUnit;
4
5 /**
6 * Java线程:线程池-
7 *
8 * @author Administrator 2009-11-4 23:30:44
9 */
10 public class Test {
11 public static void main(String[] args) {
12 //创建一个线程池,它可安排在给定延迟后运行命令或者定期地执行。
13 ScheduledExecutorService pool = Executors.newScheduledThreadPool(2);
14 //创建实现了Runnable接口对象,Thread对象当然也实现了Runnable接口
15 Thread t1 = new MyThread();
16 Thread t2 = new MyThread();
17 Thread t3 = new MyThread();
18 Thread t4 = new MyThread();
19 Thread t5 = new MyThread();
20 //将线程放入池中进行执行
21 pool.execute(t1);
22 pool.execute(t2);
23 pool.execute(t3);
24 //使用延迟执行风格的方法
25 pool.schedule(t4, 10, TimeUnit.MILLISECONDS);
26 pool.schedule(t5, 10, TimeUnit.MILLISECONDS);
27 //关闭线程池
28 pool.shutdown();
29 }
30 }
31
32 class MyThread extends Thread {
33 @Override
34 public void run() {
35 System.out.println(Thread.currentThread().getName() + "正在执行。。。");
36 }
37 }
pool-1-thread-1正在执行。。。
pool-1-thread-2正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-2正在执行。。。
Process finished with exit code
ScheduledExecutorService pool = Executors.newSingleThreadScheduledExecutor();
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-1正在执行。。。
Process finished with exit code 0
1 import java.util.concurrent.ArrayBlockingQueue;
2 import java.util.concurrent.BlockingQueue;
3 import java.util.concurrent.ThreadPoolExecutor;
4 import java.util.concurrent.TimeUnit;
5
6 /**
7 * Java线程:线程池-自定义线程池
8 *
9 * @author Administrator
10 */
11 public class Test {
12 public static void main(String[] args) {
13 //创建等待队列
14 BlockingQueue<Runnable> bqueue = new ArrayBlockingQueue<Runnable>(20);
15 //创建一个单线程执行程序,它可安排在给定延迟后运行命令或者定期地执行。
16 ThreadPoolExecutor pool = new ThreadPoolExecutor(2,3,2,TimeUnit.MILLISECONDS,bqueue);
17 //创建实现了Runnable接口对象,Thread对象当然也实现了Runnable接口
18 Thread t1 = new MyThread();
19 Thread t2 = new MyThread();
20 Thread t3 = new MyThread();
21 Thread t4 = new MyThread();
22 Thread t5 = new MyThread();
23 Thread t6 = new MyThread();
24 Thread t7 = new MyThread();
25 //将线程放入池中进行执行
26 pool.execute(t1);
27 pool.execute(t2);
28 pool.execute(t3);
29 pool.execute(t4);
30 pool.execute(t5);
31 pool.execute(t6);
32 pool.execute(t7);
33 //关闭线程池
34 pool.shutdown();
35 }
36 }
37
38 class MyThread extends Thread {
39 @Override
40 public void run() {
41 System.out.println(Thread.currentThread().getName() + "正在执行。。。");
42 try {
43 Thread.sleep(100L);
44 } catch (InterruptedException e) {
45 e.printStackTrace();
46 }
47 }
48 }
pool-1-thread-1正在执行。。。
pool-1-thread-2正在执行。。。
pool-1-thread-2正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-2正在执行。。。
pool-1-thread-1正在执行。。。
pool-1-thread-2正在执行。。。
Process finished with exit code 0
创建自定义线程池的构造方法很多,本例中参数的含义如下:
ThreadPoolExecutor
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue)
用给定的初始参数和默认的线程工厂及处理程序创建新的 ThreadPoolExecutor。使用 Executors 工厂方法之一比使用此通用构造方法方便得多。
参数:
corePoolSize - 池中所保存的线程数,包括空闲线程。
maximumPoolSize - 池中允许的最大线程数。
keepAliveTime - 当线程数大于核心时,此为终止前多余的空闲线程等待新任务的最长时间。
unit - keepAliveTime 参数的时间单位。
workQueue - 执行前用于保持任务的队列。此队列仅保持由 execute 方法提交的 Runnable 任务。
抛出:
IllegalArgumentException - 如果 corePoolSize 或 keepAliveTime 小于零,或者 maximumPoolSize 小于或等于零,或者 corePoolSize 大于 maximumPoolSize。
NullPointerException - 如果 workQueue 为 null

浙公网安备 33010602011771号