java基础(十一):多线程
2021-05-14 12:28
标签:任务 原来 nbsp 线程之间的通信 tar 之间 OLE 实例 定义 目录 线程基础内容 线程同步 线程间通信 程序Program 程序是一段静态的代码,它是应用程序执行的蓝本 进程Process 进程是指一种正在运行的程序,有自己的地址空间 进程的特点 线程Thread 线程特点 线程和进程的区别 线程的创建 线程的启动 两种线程创建方式的比较 继承Thread类方式的多线程 实现Runnable接口方式的多线程 实现Runnable接口方式要通用一些。 Thread类常用方法 3.线程的生命周期 新生状态: 就绪状态: 运行状态: 阻塞状态: 死亡状态: Java提供一个线程调度器来监控程序中启动后进入就绪状态的所有线程。 线程调度器按照线程的优先级决定应调度哪个线程来执行。 线程的优先级用数字表示,范围从1到10 使用下述方法获得或设置线程对象的优先级。 注意:优先级低只是意味着获得调度的概率低。并不是绝对先调用优先级高后调用优先级低的线程。 Join (): Sleep () : yield () setDaemon() stop() 当多个线程访问同一个数据时,容易出现线程安全问题。需要让线程同步,保证数据安全 线程同步:当两个或两个以上线程访问同一资源时,需要某种方式来确保资源在某一时刻只被一个线程使用 线程同步的实现方案 同步监视器 同步监视器的执行过程 线程同步的好处 : 解决了线程安全问题 线程同步的缺点 死锁 在生产者消费者问题中,仅有synchronized是不够的 Java提供了3个方法解决线程之间的通信问题 均是java.lang.Object类的方法 都只能在同步方法或者同步代码块中使用,否则会抛出异常 生产者消费者的实现思路 产品类 消费者线程 生产者线程 测试类 补充: 为什么通信? 不通信就无法实现生产和消费的交替进行 如何通信:wait 等待 notify唤醒 notifyAll 唤醒所有的阻塞线程 代码示例: java基础(十一):多线程 标签:任务 原来 nbsp 线程之间的通信 tar 之间 OLE 实例 定义 原文地址:https://www.cnblogs.com/Vincent-yuan/p/13124245.html
1.程序、进程与线程
2.线程的创建和启动
4.线程控制方法
5.线程同步
6.线程通信
//产品类
public class Product {
private String name;//馒头 玉米饼
private String color;//白色 黄色
private boolean isProduce = false;//是否生产产品
public synchronized void get(){
//如果没有生产,等待
if(isProduce == false)
{
wait();
}
System.out.println(“消费者消费:”+name+“ ”+color); //消费产品
isProduce = false; //修改状态:没有生产
notify();//通知生产者生产
}
public synchronized void put(String name,String color){
//如果已经生产,等待
if(isProduce == true){
wait();//生产产品
}
this.name = name;
this.color = color;
System.out.println("生产者生产:"+this.name+" "+this.color);
isProduce = true; //修改状态:已经生产
notify(); //通知消费者消费
}
}
//消费者线程
public class Consumer implements Runnable{
private Product product;
public Consumer() {
super();
}
public Consumer(Product product) {
super();
this.product = product;
}
public void run() {
while(true){
product.get();
}
}
}
//生产者线程
public class Producer implements Runnable {
private Product product;
public Producer() { }
public Producer(Product product) {
this.product = product;
}
public void run() {
int i = 0;
while (true) {
if (i % 2 == 0) {
product.put("馒头", "白色");
} else {
product.put("玉米饼", "黄色");
}
i++;
}
}
}
//测试类
public class TestCommunication {
public static void main(String[] args) {
//创建产品类(生产者和消费者操作的是同一个产品)
Product product = new Product();
//创建两个线程
Consumer c = new Consumer(product);
Thread t1 = new Thread(c);
Producer p = new Producer(product);
Thread t2 = new Thread(p);
//启动两个线程
t1.start();
t2.start();
}
}
/**
* 测试两种实现线程方式的区别
* 区别
*
* @author Terry
*
*/
public class ThreadDemo3 {
/**
* @param args
*/
public static void main(String[] args) {
//new了两个线程对象——s1和s2
//其中两个对象各对应一个内存区域。线程运行过程中运行都是自己内存块中的数据
Shop1 s1 = new Shop1("小武");
s1.start();
Shop1 s2 = new Shop1("小潘");
s2.start();
/*
//实例化了两个线程对象,所以分配了两块内存空间
//执行过程中操作的是自己的内存空间
Shop2 s3 = new Shop2("小武");
s3.run();
Shop2 s4 = new Shop2("小潘");
s4.run();
//实际实例化了两个线程对象
//所以同样分配两个内存空间
Thread t1 = new Thread(new Shop2("小武"));
t1.start();
Thread t2 = new Thread(new Shop2("小潘"));
t2.start();
//创建了两个线程对象,但是使用的是同一个对象——s5
Shop2 s5 = new Shop2("w");
Thread t3 = new Thread(s5);
t3.start();
Thread t4 =new Thread(s5);
t4.start();
*/
}
}
/**
* 因为业务的拓展,现在可以实现多窗口的出售
* 要求:每天只卖10个
* @author Terry
*
*/
class Shop1 extends Thread{
//private int count = 10;
//使用静态变量可以有效的实现资源共享(因为在内存中只有一份count)
private static int count = 10;
public Shop1(String name) {
super(name);
}
public void run(){
//判断是否已经卖完
while(count>0){
count--;
System.out.println(this.getName() +"卖出了一个烧饼" + ",现在剩余" + count);
}
}
}
/**
* 使用接口实现上面的代码
* @author Terry
*
*/
class Shop2 implements Runnable{
//私有变量,存储剩余烧饼的个数
private int count = 10;
//存储当前人的姓名
private String name="";
public Shop2(String name) {
this.name = name;
}
/**
* 实现销售的方法
*/
public void run(){
//判断是否已经卖完
while(count>0){
count--;
System.out.println(Thread.currentThread().getId() + "、" + this.name +"卖出了一个烧饼" + ",现在剩余" + count);
}
}
}