电商网站开发主要设计内容,wordpress 中文名注册,网站怎么做qq微信登陆界面,网站开发岗位就业分析线程的特点
线程就是独立的执行路径#xff1b;在线程运行时#xff0c;即使没有自己创建线程#xff0c;后台也会有多个线程#xff0c;如主线程#xff0c;gc线程#xff1b;main()称之为主线程#xff0c;为系统的入口#xff0c;用于执行整个程序#xff1b;在一…线程的特点
线程就是独立的执行路径在线程运行时即使没有自己创建线程后台也会有多个线程如主线程gc线程main()称之为主线程为系统的入口用于执行整个程序在一个进程中如果开辟了多个线程线程的运行由调度器安排调度调度器是与操作系统紧密相关的先后顺序是不能人为的干预的。对同一份资源操作时会存在资源抢夺的问题需要加入并发控制线程会带来额外的开销如cpu调度时间并发控制开销。每个线程在自己的工作内存交互内存控制不当会造成数据不一致
进程和线程的区别
进程是操作系统资源分配的基本单位而线程是处理器任务调度和执行的基本单位。还存在资源开销、包含关系、内存分配、影响关系、执行过程等区别。同一进程的线程共享本进程的地址空间和资源而进程之间的地址空间和资源相互独立。
线程创建方式
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-i3ZOerjT-1608708490342)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201222233338560.png)]
1.Thread
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-oaYMfvFx-1608708490345)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201222234526548.png)]
自定义线程类继承Thread类重写run方法编写线程执行体创建线程对象调用start方法启动线程
//创建线程方式一继承thread类重写run方法调用start开启线程//总结注意线程开启不一定立即执行由CPU调度执行
public class ThreadDemo01 extends Thread {Overridepublic void run() {//run方法线程体for (int i 0; i 100; i) {System.out.println(多线程被执行了);}}public static void main(String[] args) {//main线程主线程//创建一个线程对象ThreadDemo01 td1 new ThreadDemo01();td1.start();//调用start方法开启线程for (int i 0; i 1000 ; i) {System.out.println(每天都在学习java);}}
}练习
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-eeB1nHR8-1608708490347)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201222235400735.png)]
package com.dong.thread;import org.apache.commons.io.FileUtils;import java.io.File;
import java.io.IOException;
import java.net.URL;/*** author dong* date 2020/5/24 - 8:39*/
//
public class ThreadDemo02 extends Thread{private String url;//保存网络图片地址private String name;//保存的文件名public ThreadDemo02(String url, String name) {this.url url;this.name name;}Overridepublic void run() {WebDownLoader webDownLoader new WebDownLoader();webDownLoader.downLoader(url,name);System.out.println(图片下载成功名为name);}public static void main(String[] args) {ThreadDemo02 t1 new ThreadDemo02(https://dss0.baidu.com/73t1bjeh1BF3odCf/it/u1561546013,1259770086fm85s1A21EC02EE337FAF0854119903001062,1.jpg);ThreadDemo02 t2 new ThreadDemo02(https://dss0.baidu.com/73t1bjeh1BF3odCf/it/u3506652242,2368086075fm85s8C9F875066675AAE078DE4D6030050F1,2.jpg);ThreadDemo02 t3 new ThreadDemo02(https://dss0.baidu.com/73t1bjeh1BF3odCf/it/u2623032014,2137091052fm85sF4C2BE56F74162EE0E5EEC7C03004071,3.jpg);t1.start();t2.start();t3.start();}
}
//下载器
class WebDownLoader{//下载方法public void downLoader(String url,String name){try {FileUtils.copyURLToFile(new URL(url),new File(name));} catch (IOException e) {e.printStackTrace();System.out.println(文件下载失败Io有问题);//文件下载失败}}
}2.Runnable接口
public class ThreadDemo03 implements Runnable{Overridepublic void run() {for (int i 0; i 200 ; i) {System.out.println(多线程被执行了);}}public static void main(String[] args) {new Thread(new ThreadDemo03()).start();//ThreadDemo02 threadDemo02 new ThreadDemo02();//Thread thread new Thread(threadDemo02);代理//thread.start();for (int i 0; i 1000 ; i) {System.out.println(每天都在学习java);}}
}小结
继承Thread类 子类继承Thread类具备多线程能力启动线程子类对象.start不建议使用避免OOP单继承局限性 实现Runnable接口
实现接口Runnable具有多线程能力
启动线程传入目标对象Thread对象.start ()
推荐使用避免单继承局限性灵活方便方便同一对象被多个线程使用
实例
public class ThreadDemo04 implements Runnable{private static String winner;//胜利者 static保证只有一个胜利者Overridepublic void run() {for (int i 0; i 100 ; i) {//模拟兔子休息if(Thread.currentThread().getName().equals(兔子) i%200){try {Thread.sleep(10);} catch (InterruptedException e) {e.printStackTrace();}}//判断是否结束比赛boolean flaggameOver(i);//如果比赛结束了停止程序if(flag){break;}System.out.println(Thread.currentThread().getName()--跑了i步);}}//判断是否完成比赛private boolean gameOver(int steps){//判断是否有胜利者if(winner!null){return true;} {if (steps100){winnerThread.currentThread().getName();System.out.println(winner is:winner);return true;}}return false;}public static void main(String[] args) {new Thread(new ThreadDemo04(),兔子).start();new Thread(new ThreadDemo04(),乌龟).start();}
}3.实现Callable接口(了解)
实现Callable接口需要返回值类型重写call方法需要抛出异常创建目标对象创建执行服务ExecutorServiceExecutor.newFixedThreadPool(1);提交执行Futureresult1ser.submit(t1);获取结果boolean r1result.get()关闭服务ser.shutdownNow();
package com.kuang.demo02;
import org.apache.commons.io.FileUtils;
import java.io.File;
import java.io.IOException;
import java.net.URL;
import java.util.concurrent.*;
public class TestCallable implements CallableBoolean {private String url;//保存网络图片地址private String name;//保存的文件名public TestCallable(String url, String name) {this.url url;this.name name;}Overridepublic Boolean call() {WebDownLoader webDownLoader new WebDownLoader();webDownLoader.downLoader(url,name);System.out.println(图片下载成功名为name);return true;}public static void main(String[] args) throws ExecutionException, InterruptedException {TestCallable t1 new TestCallable(https://dss0.baidu.com/73t1bjeh1BF3odCf/it/u1561546013,1259770086fm85s1A21EC02EE337FAF0854119903001062,1.jpg);TestCallable t2 new TestCallable(https://dss0.baidu.com/73t1bjeh1BF3odCf/it/u3506652242,2368086075fm85s8C9F875066675AAE078DE4D6030050F1,2.jpg);TestCallable t3 new TestCallable(https://dss0.baidu.com/73t1bjeh1BF3odCf/it/u2623032014,2137091052fm85sF4C2BE56F74162EE0E5EEC7C03004071,3.jpg);//创建执行服务ExecutorService ser Executors.newFixedThreadPool(3);//提交执行FutureBoolean r1 ser.submit(t1);FutureBoolean r2 ser.submit(t2);FutureBoolean r3 ser.submit(t3);//获取结果boolean rs1r1.get();boolean rs2r2.get();boolean rs3r3.get();//关闭服务ser.shutdownNow();}
}
//下载器
class WebDownLoader{//下载方法public void downLoader(String url,String name){try {FileUtils.copyURLToFile(new URL(url),new File(name));} catch (IOException e) {e.printStackTrace();System.out.println(文件下载失败Io有问题);//文件下载失败}}
}静态代理
真实对象和代理对象都要实现同一个接口
代理对象要代理真实角色
好处
代理对象可以做很多真实对象做不了的事情
真实对象专注做自己的事情
package com.kuang.demo03;
public class StacticProxy {public static void main(String[] args) {
// WeddingCompany weddingCompanynew WeddingCompany(new You());
// weddingCompany.HappyMarry();new WeddingCompany(new You()).HappyMarry();}
}
interface Marry{void HappyMarry();
}
class You implements Marry{Overridepublic void HappyMarry(){System.out.println(afdas);}
}class WeddingCompany implements Marry{private Marry target;public WeddingCompany(Marry target){this.targettarget;}Overridepublic void HappyMarry(){before();this.target.HappyMarry();after(); }private void after() {System.out.println(asf); }private void before() {System.out.println(asdfa);}
}Lamda表达式
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GmTxaGNR-1608708490355)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223104552933.png)]
函数式接口
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Ll6HAooJ-1608708490356)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223104815076.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OVOumEzH-1608708490359)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223110252247.png)]
lamda表达式简化
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-90qhdq24-1608708490360)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223111844980.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-YxZohGaf-1608708490361)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223112035798.png)]
public class TestLambda1 {//2.静态内部类static class Love implements ILove {public void ILove(int a) {System.out.println(i like lambda a);}}public static void main(String[] args) {Love lovenew Love();love.ILove(1);Love love1new Love();love1.ILove(2);class Love implements ILove {//3.局部内部类public void ILove(int a) {System.out.println(i like lambda a);}}Love love2 new Love();love2.ILove(3);//4.匿名内部类ILove iLovenew ILove() {Overridepublic void ILove(int a) {System.out.println(i like lambda a);}};iLove.ILove(4);//5.lambda表达式ILove iLove1(int a)-{System.out.println(i like lambda a);};iLove1.ILove(5);}
}
//定义一个接口,只有一个方法函数式接口
interface ILove{void ILove(int a);
}//1.普通实现
class Love implements ILove {Overridepublic void ILove(int a) {System.out.println(i like lambda a);}
}
public class TestLambda2 {public static void main(String[] args) {YouLove youLove(a,b)-{System.out.println(一句话你说:ab);};youLove.youLove(10,20);}
}interface YouLove{void youLove(int a,int b);
}总结
lambda表达式只能有一行代码的情况下才能简化为一行如果有多行那么就用代码块包裹前提是 接口为函数式接口多个参数也可以去掉参数类型 要去 掉 就都去掉 必须加上括号。
线程状态
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-DpOnjVPD-1608708490361)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223112930005.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OEAilaW0-1608708490362)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223113054638.png)]
线程停止
package com.kuang.demo05;public class TestStop implements Runnable {private boolean flagtrue;Overridepublic void run() {int i0;while (flag){System.out.println(run.....Thread(i));}}public void stop(){this.flagfalse;}public static void main(String[] args) {TestStop testStop new TestStop();new Thread(testStop).start();for (int i 0; i 1000 ; i) {System.out.println(maini);if (i900){testStop.stop();System.out.println(线程停止了);}}}
}线程休眠
sleep时间指定当前线程阻塞的毫秒数
sleep存在异常InterruptedException
sleep时间到达后线程进入就绪状态
sleep可以模拟网络延时倒计时等。
每一个对象都有一个锁sleep不会释放锁
package com.kuang.demo05;import java.text.SimpleDateFormat;
import java.util.Date;public class TestSleep2 {public static void main(String[] args) {TestSleep2.tenDown();//打印当前系统时间Date startTimenew Date(System.currentTimeMillis());//获取当前系统时间while (true){try {Thread.sleep(1000);System.out.println(new SimpleDateFormat(HH:mm:ss).format(startTime));startTimenew Date(System.currentTimeMillis());//更新时间} catch (InterruptedException e) {e.printStackTrace();}}}//模拟倒计时public static void tenDown(){int num10;while (true){try {Thread.sleep(1000);if (num0){break;}else{System.out.println(倒计时num--秒);}} catch (InterruptedException e) {e.printStackTrace();}}}
}线程礼让yield
礼让线程让当前正在执行的线程暂停但不阻塞
将线程从运行状态转为就绪状态
让cpu重新调度礼让不一定成功看CPU心情。
package com.kuang.demo05;
public class TestYield{public static void main(String[] args) {MyYield yieldnew MyYield();new Thread(yield,a).start();new Thread(yield,b).start();}
}
class MyYield implements Runnable {Overridepublic void run() {System.out.println(Thread.currentThread().getName()线程开始执行);Thread.yield();//礼让System.out.println(Thread.currentThread().getName()线程停止执行);}
}线程强制执行join
package com.kuang.demo05;
public class TestJoin implements Runnable {Overridepublic void run() {for (int i 0; i 10 ; i) {System.out.println(VIP线程来插队了i);}}public static void main(String[] args) throws InterruptedException {
// Thread thread new Thread(new TestJoin());new Thread(new TestJoin()).start();for (int i 0; i 400 ; i) {System.out.println(主线程在排队i);if (i100){new Thread(new TestJoin()).join();}}}
}线程状态
Thread.State
线程状态线程可以处于一下状态之一
new 尚未启动的线程处于此状态Runnable 在java虚拟机中执行的线程处于此状态Blocked 被阻塞等待监视器锁定的线程处于此状态。Waiting 正在等待另一个线程执行特定动作的线程处于此状态。Timed Waiting 正在等待另一个线程执行动作达到指定等待时间的线程处于此状态。Terminated 已退出的线程处于此状态。
一个线程可以给定时间点处于一个状态。这些状态是不反映任何操作系统线程状态的虚拟机状态
package com.kuang.demo05;
public class TestState {public static void main(String[] args) throws InterruptedException {Thread threadnew Thread(()-{for (int i 0; i 5 ; i) {try {Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}}System.out.println();});Thread.State state thread.getState();System.out.println(state);//newthread.start();//启动线程statethread.getState();//runnableSystem.out.println(state);while (state! Thread.State.TERMINATED){//只要线程不终止就输入线程状态Thread.sleep(100);statethread.getState();System.out.println(state);}}
}[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2HsC4lq6-1608708490364)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223130000180.png)]
线程优先级
java提供一个线程调度器来监控程序中启动后进入就绪状态的所有线程线程调度器按照优先级决定应该调度哪个线程来执行。
线程的优先级用数字表示范围从1~10。
使用以下方式改变或获取优先级
getPriority().setPriority(int xxx)
package com.kuang.demo05;public class TestPriority {public static void main(String[] args) {MyPriority myPriority new MyPriority();Thread t1 new Thread(myPriority);Thread t2 new Thread(myPriority);Thread t3 new Thread(myPriority);Thread t4 new Thread(myPriority);Thread t5 new Thread(myPriority);Thread t6 new Thread(myPriority);//先设置线程优先级t1.setPriority(1);t1.start();t2.setPriority(3);t2.start();t3.setPriority(6);t3.start();t4.setPriority(Thread.MAX_PRIORITY);// 优先级10t4.start();t5.setPriority(Thread.MIN_PRIORITY);// 优先级1t6.setPriority(9);t6.start();System.out.println(main);}
}
class MyPriority implements Runnable{Overridepublic void run() {System.out.println(Thread.currentThread().getName()---线程被执行了---Thread.currentThread().getPriority());}
}[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-vRIzDkCg-1608708490365)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223131437565.png)]
注意先设置优先级再start线程
守护线程daemon
线程分为用户线程和守护线程虚拟机必须确保用户线程执行完毕虚拟机不用等待守护线程执行完毕如后台记录操作日志监控内存垃圾回收等待。。。
package com.kuang.demo05;
public class TestDaemon {public static void main(String[] args) {God god new God();You younew You();Thread thread new Thread(god);thread.setDaemon(true);//默认为flase 为用户线程 true为守护线程thread.start();
// new Thread(you).start();Thread thread1 new Thread(you);thread1.start();}
}
class God implements Runnable{Overridepublic void run() {while (true){System.out.println(上帝守护着你-------);}}
}
class You implements Runnable{Overridepublic void run() {for (int i 0; i 36500 ; i) {System.out.println(开心着活着每一天------);}System.out.println(----goodbye!Beautiful World!!!------);}
}线程同步机制 由于同一进城的多个线程共享同一块存储空间在带来方便的同事也带来了访问冲突问题为了保证数据在方法中被访问时的正确性在访问时加入锁机制synchronized当一个线程获得对象的排它锁独占资源其他线程必须等待使用后释放锁即可存在以下问题 一个线程持有锁会导致其它所有需要此锁的线程挂起 在多线程竞争下加锁释放锁会导致比较多的上下文切换和调度延时引起性能问题 如果一个优先级高的线程等待一个优先级低的线程释放锁会导致优先级倒置引起性能问题。
三大不安全案例解决
不安全的买票
package com.kuang.demo06;
//不安全的买票
public class UnsafeBuyTicket {public static void main(String[] args) {BuyTicket btnew BuyTicket();new Thread(bt,我).start();new Thread(bt,你).start();new Thread(bt,黄牛党).start();}
}class BuyTicket implements Runnable{//票private int ticketNums10;boolean flagtrue;//外部停止方式Overridepublic void run() {//买票while (flag){buy();}}public synchronized void buy(){//锁了方法相当于this 把类给锁住//判断是否有票if(ticketNums0){System.out.println(票没了);flagfalse;return ; }//模拟延时try {Thread.sleep(100);} catch (InterruptedException e) {e.printStackTrace();}System.out.println(Thread.currentThread().getName()ticketNums--);}
}不安全的银行
package com.kuang.demo06;
//不安全取钱
//两个人去银行取钱账户
public class UnsafeBank {public static void main(String[] args) {//账户Account accountnew Account(100,结婚基金);Drawing younew Drawing(account,50,你);Drawing girlFriendnew Drawing(account,100,女朋友);you.start();girlFriend.start();}
}
//账户
class Account{int money;//余额String name;//卡名public Account(int money, String name) {this.money money;this.name name;}
}
//银行模拟取款
class Drawing extends Thread{Account account;//账户//取了多少钱int drawingMoney;//现在手里又多少钱int nowMoney;public Drawing(Account account,int drawingMoney,String name){super(name);this.accountaccount;this.drawingMoneydrawingMoney;}//取钱Overridepublic void run() {synchronized (account) {//锁的对象是变化的量锁需要增删改的对象//判断有没有钱if (account.money - drawingMoney 0) {System.out.println(Thread.currentThread().getName() 钱不够);return;}//卡内余额account.money - drawingMoney;//手里的钱nowMoney drawingMoney;System.out.println(account.name 余额为: account.money);//Thread.currentThread().getName()this.getName();System.out.println(this.getName() 手里的钱: nowMoney);}}
}用sleep可以放大问题的发生性
不安全的集合
package com.kuang.demo06;
import java.util.ArrayList;
public class UnsafeList {public static void main(String[] args) {ArrayListString listnew ArrayListString();for (int i 0; i 1000 ; i) {new Thread(()-{synchronized (list){list.add(Thread.currentThread().getName());}}).start();try {Thread.sleep(30);} catch (InterruptedException e) {e.printStackTrace();}}System.out.println(list.size());}
}同步
同步方法
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gFDPBjYN-1608708490368)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223135044806.png)]
同步块
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-CG6hbeAf-1608708490371)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223135151154.png)]
死锁避免方法
产生死锁的四个必要条件
1.互斥条件一个资源每次只能被一个进程使用。
2.请求与保持条件一个进程因请求资源而阻塞时对已获得的资源保持不妨。
3.不剥夺条件进程已获得的资源在未使用完之前不能强行剥夺。
4.循环等待条件若干进程之间形成一种头尾相接的循环等待资源关系。
Lock锁
JDK5.0开始java提供了更强大的线程同步机制——通过显式定义同步锁对象来实现同步。同步锁使用Lock对象充当java.util.concurrent.locks.Lock接口是控制多个线程对共享资源进行访问的工具。锁提供了对共享资源的独占访问每次只能有一个线程对Lock对象加锁线程开始访问共享资源之前应先获得Lock对象ReentrantLock类实现了Lock它拥有与synchronized相同的并发性和内存语义在实现线程安全的控制中比较常用的是ReentrantLock可以显式加锁、释放锁。
package com.kuang.demo06;import java.util.concurrent.locks.ReentrantLock;public class TestLock {public static void main(String[] args) {Ticket ticket new Ticket();new Thread(ticket).start();new Thread(ticket).start();new Thread(ticket).start();}}
class Ticket extends Thread{private int ticketNums10;//定义lock锁private final ReentrantLock locknew ReentrantLock();Overridepublic void run() {while (true){try {lock.lock();//加锁if (ticketNums 0) {try {Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}System.out.println(ticketNums--);} else {break;}}finally {lock.unlock();//减锁}}}
}synchronized与Lock的对比
Lock是显式锁手动开启和关闭锁别忘记关闭锁synchronized是隐式锁出了作用域自动释放Lock只有 代码块加锁 synchronized有代码块锁和方法锁使用Lock锁JVM将花费较少的时间来调度线程性能更好。并且具有更好的扩展性提供更多的子类优先使用顺序Lock同步代码块已经进入了方法体分配了相应资源同步方法在方法体之外
线程通信
案例生产者消费者
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-978jJ3Gl-1608708490372)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223142705516.png)]
假设仓库中只能存放一件产品生产者将生产出来的产品放入仓库消费者将仓库中产品取走消费。如果仓库中没有产品则生产者将产品放入仓库否则停止生产并等待直到仓库中的产品被消费者取走为止。如果仓库中放有产品则消费者可以将产品取走消费否则停止消费并等待直到仓库中再次放入产品为止。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-35X9RRsH-1608708490374)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223142745865.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-KfXsnaeX-1608708490376)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223142856572.png)]
管程法
package com.kuang.demo07;
//测试生产者消费者模型--》
//生产者消费者产品
public class TestPC{public static void main(String[] args) {SynContain containnew SynContain();new Productor(contain).start();new Consumer(contain).start();}}//生产者
class Productor extends Thread{SynContain contain;public Productor(SynContain contain){this.containcontain;}Override//生产public void run(){for (int i 0; i 100; i) {contain.push(new Chicken(i));System.out.println(生产了i只鸡);}}
}//消费者
class Consumer extends Thread{SynContain contain;public Consumer(SynContain contain){this.containcontain;}Override//生产public void run(){for (int i 0; i 100; i) {System.out.println(消费了contain.pop().id只鸡);}}}
//产品
class Chicken{int id;//产品编public Chicken(int id){this.idid;
}}
//容器
class SynContain {//需要一个容器大小Chicken[] chickens new Chicken[10];//容器计数器int count 0;//生产者放入产品public synchronized void push(Chicken chicken) {//如果容器满了,需要等待消费者消费if (count chickens.length) {//通知消费者消费.生产等待try {//Ctrl加Alt加T进行代码块的包裹this.wait();} catch (InterruptedException e) {e.printStackTrace();}}//如果没有满我们就需要丢入产品chickens[count] chicken;count;//可以同知消费this.notifyAll();}//消费者消费产品public synchronized Chicken pop() {//判断能否消费if (count 0) {//等待生产者生产消费者等待try {this.wait();} catch (InterruptedException e) {e.printStackTrace();}}//如果可以消费count--;Chicken chicken chickens[count];//吃完了通知生产者生产this.notifyAll();return chicken;}}信号灯法
package com.kuang.demo07;
public class TestPc2 {public static void main(String[] args) {TV tv new TV();new Player(tv).start();new Watcher(tv).start();}
}
//生产者--》演员
class Player extends Thread{TV tv;public Player(TV tv) {this.tv tv;}Overridepublic void run() {for (int i 0; i 20 ; i) {if (i%20){this.tv.play(快乐大本营播放中);}else{this.tv.play(抖音记录美好生活);}}}
}
//消费者--》观众
class Watcher extends Thread{TV tv;public Watcher(TV tv) {this.tv tv;}Overridepublic void run() {for (int i 0; i 20 ; i) {tv.watch();}}
}
//产品--节目
class TV{//演员表演观众等待 T//观众观看演员等待 FString voice;//表演的节目boolean flagtrue;//表演public synchronized void play(String voice){if (!flag){try {this.wait();} catch (InterruptedException e) {e.printStackTrace();}}System.out.println(演员表演了:voice);//通知观众观看this.notifyAll();//通知唤醒this.voicevoice;this.flag!this.flag;}//观看public synchronized void watch(){if (flag){try {this.wait();} catch (InterruptedException e) {e.printStackTrace();}}System.out.println(观看了voice);//同知演员表演this.notifyAll();this.flag!this.flag;}
}线程池
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4gsVZkGS-1608708490376)(C:\Users\王东梁\AppData\Roaming\Typora\typora-user-images\image-20201223151328767.png)]
背景经常创建和销毁、使用量特别大的资源比如并发情况下的线程对性能影响很大。思路提前创建好多个线程放入线程池中使用时直接获取使用完放回池中。可以避免频繁创建销毁、实现重复利用。类似生活中的公共交通工具。好处 提高响应速度减少了创建新线程的时间降低资源消耗重复利用线程池中线程不需要每次都创建便于线程管理。。。 corePoolSize:核心池的大小maximumPoolSize最大线程数keepAliveTime线程没有任务时最多保持多长时间后会终止
package com.kuang.demo07;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class TestPool {public static void main(String[] args) {//1.创建服务创建线程池ExecutorService service Executors.newFixedThreadPool(10);//newFixedThreadPool 参数为线程池大小//执行service.execute(new MyThread());service.execute(new MyThread());service.execute(new MyThread());service.execute(new MyThread());//2.关闭连接service.shutdown();}
}
class MyThread implements Runnable{Overridepublic void run() {System.out.println(Thread.currentThread().getName());}
}