Java 多线程之线程实现的方式-1

图片

1.并发与并行

1.1并发

  • 并发:指两个或多个时间在同一时间段内发生(交替执行)

并发

1.2并行

  • 并行:指两个或多个时间在同一时刻发生(同时发生)
    并行

2.线程和进程

2.1进程

是指一个内存中运行的应用程序,每个进程都有一个独立的内存空间,一个应用程序可以同时运行多个进程
进程也是程序一次执行过程,是系统运行程序的基本单位,系统运行一个程序即是一个进程从创建,运行
到消亡的过程

在这里插入图片描述

2.2线程

线程是进程中的一个执行单元,负责当前进程中程序的执行,一个进程中至少有一个线程,也可以有多个线
程,这个应用程序也可以称之为多线程程序

如下图的例子!!!
在这里插入图片描述

3.线程的调度

3.1分时调度

所有线程轮流使用CPU的使用权,平均分配每个线程占用CPU时间

3.2抢占式调度

抢先让优先级高的线程使用CPU,如果线程的优先级相同,会随机选择一个(线程随机性),Java使用的便是
抢占式

4.创建多线程的方式

4.1继承Thread类

  • 1.继承Thread类,并重写run()方法,该方法代表了线程需要完成的任务,称之为线程执行体
  • 2.创建Thread子类的实例,即创建了线程对象
  • 3.开启线程调用start()启动线程
public class PrimeThread extends Thread{
	long minPrime;
	PrimeThread(long minPrime){
		this.minPrime = minPrime;
	}
	
	public void run(){
		// 执行自己的业务...
	}
}

public static void main(String[] args){
	// 实例化子类
	PrimeThread p = new PrimeThread(122);
	// 启动线程
	p.start();
}

4.2实现Runnable接口重写run方法

  • 1.实现Runnable接口,并重写run方法
  • 2.创建Thread线程类,将实现Runnable接口的类的实例,放入到Thread的构造器中,并调用start方法
public class PrimeThread implements Runnable{
	long minPrime;
	PrimeThread(long minPrime){
		this.minPrime = minPrime;
	}
	
	@Override
	public void run(){
		// 执行自己的业务...
	}
}

public static void main(String[] args){
	// 实例化子类
	PrimeThread p = new PrimeThread(122);
	// 启动线程
	new Thread(p).start();
}

5.多线程例子

5.1例子

!!!上代码!!!

public class MyThread implements Runnable{

	@Override
	public void run(){
		for(int i=0;i<20;i++){
			System.out.println("run:"+i);
		}
	}
}

public static void main(String[] args){
	// 实例化子类
	MyThread mt = new MyThread();
	// 启动线程
	mt.start();

	for(int i=0;i<20;i++){
		System.out.println("main:"+i);
	}
}

!!!结果!!!
随机性打印

5.2执行过程

  • 1.JVM执行main方法,创建一个main方法的线程
  • 2.当代码执行到new MyThread();的时候,会创建一个新的线程
  • 3.两个线程同时抢夺CPU的时间片来执行线程,谁抢到了谁就执行代码

!!!由此可见多线程的结构!!!
多线程结构

  • 当调用run方法时,属于单线程,并且被当作普通方法调用,在main线程里执行
  • 当调用start方法时,会开辟一个新的栈空间并执行底层run方法,属于多线程
  • CPU会根据哪个线程抢得时间片而优先执行哪个线程
  • 多线程之间,线程与线程互不影响

6.Thread类

下图为常用的Thread方法

在这里插入图片描述

7.Runnable接口

  • 1.定义Runnable接口的实现类,重写该接口的run方法,该run方法的方法体同样是该线程知兴替
  • 2.创建Runnable实现类的实例,并以此实例作为Thread的target来创建Thread对象,该Thread对象才是真正的线程对象
  • 3.调用线程对象的start方法启动线程
public class MyRunnable implements Runnable{
	@Override
	public void run(){
		for (int i=0;i<20;i++){
			System.out.println(Thread.currentThread().getName()+""+i);
		}
	}
}

public class Demo{
	public static void main(String[] args){
		MyRunnable mr = new MyRnnable();
		//实例化Thread 并调用start方法启动线程
		new Thread(mr).start();
		
		for (int i=0;i<20;i++){
			System.out.println(Thread.currentThread().getName()+""+i);
		}
	}
}

!!!打印台显示结果!!!
结果

8.Thread和Runnable的区别

  • 如果一个类继承Thread,则不适合资源共享,如果实现了Runnable接口,则很容易实现资源共享
  • 可以避免java中单继承的局限性
  • 增加程序健壮性,实现解耦操作,代码可以被多个线程共享,代码和线程独立
  • 线程池只能放入实现Runnable和Callable类线程,不能放入继承Thread的类
发布了9 篇原创文章 · 获赞 9 · 访问量 604

猜你喜欢

转载自blog.csdn.net/weixin_41241629/article/details/104175991