多线程ppt课件.ppt

上传人(卖家):三亚风情 文档编号:2645709 上传时间:2022-05-14 格式:PPT 页数:66 大小:918KB
下载 相关 举报
多线程ppt课件.ppt_第1页
第1页 / 共66页
多线程ppt课件.ppt_第2页
第2页 / 共66页
多线程ppt课件.ppt_第3页
第3页 / 共66页
多线程ppt课件.ppt_第4页
第4页 / 共66页
多线程ppt课件.ppt_第5页
第5页 / 共66页
点击查看更多>>
资源描述

1、1内容多线程基本概念Java多线程创建多线程线程的状态控制Java多线程的一些问题小结注: 本课件部分材料来自网络21 多线程基本概念文件文件输入输出装置输入输出装置各种系统资源各种系统资源数据区段数据区段程序区段程序区段只有一个地方在执行只有一个地方在执行文件文件输入输出装置输入输出装置各种系统资源各种系统资源数据区段数据区段程序区段程序区段同时有数个地方在执行同时有数个地方在执行传统的进程传统的进程多线程的任务多线程的任务3多线程的优势:减轻编写交互频繁、涉及面多的程序的困难程序的吞吐量会得到改善由多个处理器的系统,可以并行运行不同的线程(否则,任何时刻只有一个线程在运行,形成并发运行)4

2、线程与进程的区别:多个进程的内部数据和状态都是完全独立的,而多线程是共享一块内存空间和一组系统资源,有可能互相影响线程本身的数据通常只有寄存器数据,以及一个程序执行时使用的堆栈,所以线程的切换比进程切换的负担要小5多线程编程原则安全性: 如果两个以上的线程访问同一对象时,一个线程会损坏另一个线程的数据,这就违反了安全性原则可行性: 如果仅仅实现了安全性,程序却在某一点后不能继续执行或者多个线程发生死锁,那么这样的程序也不能作为真正的多线程程序来应用高性能: 多线程的目的是为了增加程序运行的性能62. Java线程概念对线程的综合支持是Java技术的一个重要特色.它提供了thread类、监视器和

3、条件变量的技术.虽然许多操作系统支持多线程,但若要用C或C+编写多线程程序是十分困难的,因为它们对数据同步的支持不充分.7线程对象和线程的区别:线程对象是可以产生线程的对象比如在java平台中Thread对象,Runnable对象。线程,是指正在执行的一个指令序列。在java平台上是指从一个线程对象的start()开始,运行run方法体中的那一段相对独立的过程。8思考如果我们成功编译了该JAVA文件,然后运行发生的过程JVM进程启动, JVM产生一个主线程还有一些其它线程,例如垃圾回收等 class BeginClass public static void main(String args)

4、 for(int i=0;i100;i+) System.out.println(Hello,World!); 9剖析多线程程序class MyThread extends Thread public void run() System.out.println(Thread say:Hello,World!); public class MoreThreads public static void main(String args) new MyThread(); new MyThread().start(); System.out.println(Main say:Hello,World);

5、 103. 创建多线程Runnable 与Thread1. public class mythread extends Applet implements Runnable (小应用或已经是某个类的子类时)2. 继承类Thread public class mythread extends Thread创建方法:newthread=new Thread(this);newthread.start();11Runable与Thread的区别使用runable最主要的原因是:java缺少多重继承的机制,可能你的类已经继承了其他类了,这时你无法继承自thread类,只能用runnable了Runab

6、le 创建的线程共享数据区 12public class Test public static void main(String args) throws Exception MyThread mt = new MyThread(); mt.start(); mt.join(); Thread.sleep(3000); mt.start(); 输出:Exception in thread main java.lang.IllegalThreadStateException说明:通过Thread实例的start(),一个Thread的实例只能产生一个线程13class R implements

7、Runnable private int x = 0; public void run() for(int i=0;i100;i+) try Thread.sleep(10); catch(Exception e) System.out.println(x+); public class Test public static void main(String args) throws Exception R r = new R(); for(int i=0;i10;i+) new Thread(r).start(); 14package debug; import java.io.*; imp

8、ort java.lang.Thread; class MyThread extends Thread public int x = 0; public void run() System.out.println(+x); class R implements Runnable private int x = 0; public void run() System.out.println(+x); public class Test public static void main(String args) throws Exception for(int i=0;i10;i+) Thread

9、t = new MyThread(); t.start(); Thread.sleep(10000);/让上面的线程运行完成让上面的线程运行完成 R r = new R(); for(int i=0;i10;i+) Thread t = new Thread(r); t.start(); 15重要的方法start()从CPU中申请另一个线程空间来执行run()方法中的代码run()是运行线程的主体,启动线程时,由java直接调用 public void run() 如果你不调用Start, 直接调用run, 会如何?stop()停止线程, 调用线程的 newthread.stop() (不是安

10、全的处理) sleep方法暂停线程的执行,让其它线程得到机会,sleep要丢出异常,必须抓住: Trysleep(100)catch(InterruptedException e) 16import javax.swing.*;public class Applet1 extends JAppletmythread t1=new mythread(); public void init() t1.start();class mythread extends Thread public void run() for (int i=0;i4;i+) System.out.println( +i);

11、 try sleep(400); catch(InterruptedException e) 177.2 创建线程的方式import javax.swing.*;import java.awt.*;public class Applet1 extends JApplet C t1=new C(this); public void init() t1.start(); public void paint(Graphics g) g.drawString(Hello,java,10,50); class C extends Thread Applet1 a; C(Applet1 b) a=b; p

12、ublic void run() while(true) a.repaint();try sleep(400); catch(InterruptedException e) 18join:等待线程执行完毕,被等待的那个线程不结束,当前线程就一直等待.public class Test public static void main(String args) throws Exception MyThread mt = new MyThread(); mt.start(); mt.join(); System.out.println(101); 19其它常用的方法 isAlive :判断线程目前

13、是否正在执行状态中 if(newthread.isAlive() newthread.stop(); resume:要求被暂停线程继续执行 suspend:暂停线程的执行 yield:将执行的权力交给其它线程,自己到队列的最后等待.20线程的优先权某一时刻只有一个线程在执行,调度策略为固定优先级调度.newthread.setPriority(Thread.MIN_PRIORITY)级别有:MIN-PRIORITY NOM_PRIORITY MAX-PRIORITY自私的线程:有很高的优先权的线程,不主动睡眠或让出处理器控制权.214. 线程的状态控制线程的状态new Thread()New

14、ThreadRunnablestart()Not Runnablestop()stop()Deadyield()stop() orrun()exit. .suspend()sleep()wait()resume().22当一个线程执行完所有语句后就自动终止调用线程的stop()方法,也可以强制终止线程,可能产生不完整的残废数据 。如果希望线程正常终止,可采用标记来使线程中的run()方法退出23public class Xyz implements Runnable private boolean timeToQuit=false; public void run() while (!time

15、ToQuit) . /clean up before run() ends; public void stopRunning() timeToQuit=true; 24public class ControlThread private Runnable r=new Xyz(); private Thread t=new Thread(r); public void startThread() t.start(); publi void stopThread() r.stopRunning();25暂停线程的执行等待条件满足再执行下面的例子显示线程的挂起和唤醒Applet第一次开始时,线程被启

16、动浏览器改变页面时,小应用程序的stop()方法被调用,线程被挂起.浏览器回到原来的页面时,线程被唤醒.26public void start() if (mythread=null) mythread=new Thread(); mythread.start(); else mythread.resume();public void run() while(true) trysleep(100); catch(InterruptedException e) public void stop()mythread.suspend();.275 . Java多线程问题执行顺序多个线程运行时,调度策

17、略为固定优先级调度.级别相同时,由操作系统按时间片来分配下面给出的例子中,共运行三个线程,它们做同样的事, 每次打印循环次数和自己的序列号,运行结果表明,它们并不是连续运行的.如果给某个线程赋予较高的优先权,则发现这个进程垄断控制权 thread.setPriority(Thread.MAX_PRIORITY)287.3 多线程问题/多个进程运行时执行顺序是交叉的多个进程运行时执行顺序是交叉的public class MyThread extends Thread int threadNum; public static void main(String args) MyThread arra

18、y=new MyThread3; for (int i=0;i3;i+) arrayi=new MyThread(i); for (int i=0;i3;i+) arrayi.start(); MyThread(int SerialNum) super(); threadNum=SerialNum; public void run() for(int j=0;j5;j+) System.out.println(threadNum+: ); trysleep(1000);catch(InterruptedException e); System.out.println(thread +threa

19、dNum+ bye.);29如何写多线程1.分别定义不同的线程类,在各自的run方法中定义线程的工作 class mythread1 extends Thread public void run. class mythread2 extends Thread public void run. 2. 在主类中实例化各线程类,并启动线程. public class demo extends Applet public void init() mythread t1=new mythread1(); mythread t2=new mythread2(); t1.start(); t2.start(

20、); 30练习:将窗口分为上下两个区,分别运行两个线程,一个在上面的区域中显示由右向左游动的字符串,另一个在下面的区域从左向右游动的字符串.方法一: 一个线程,在paint方法中使用两个输出字符串的语句public void paint(Graphics g) if y1200 y2=0 else y2=y2+10; g.drawString(“hello, Java!”,20,y1,); g.drawString(“hello, Java!”,40,y2,);31方法二:定义两个类,运行各自的线程,各自有自己的paint()方法.注意: 两个Applet必须是panel类或者是canvas类

21、,将Applet的区域分成两块,否则不能运行paint语句.32import javax.swing.*;import java.awt.*;public class Applet1 extends JApplet C t1,t2; myCanvas c1,c2; Container contentPane = getContentPane( ); public void init() c1=new myCanvas(); c2=new myCanvas(); contentPane.setLayout(new GridLayout(2,1); contentPane.validate();

22、contentPane.add(c1); contentPane.add(c2); t1=new C(c1,5); t2=new C(c2,-5); t1.start(); t2.start(); class myCanvas extends Canvaspublic void paint(Graphics g, int x,int y)g.drawString(Hello World, x, y); class C extends Thread myCanvas a; int steps; int x; C(myCanvas b,int size) a=b; steps=size; x=0;

23、public void run() while(true) x=x+steps;if (xa.getWidth() x=0;a.repaint();a.paint(a.getGraphics(),x,50);try sleep(10); catch(InterruptedException e) 33线程间的通信1. 线程间的通信可以用管道流,.创建管道流:PipedInputStream pis=new PipedInputStream();PipedOutputStream pos=new PipedOutputStream(pis);或:PipedOutputStream pos=new

24、 PipedOutputStream();PipedInputStream pis=new PipedInputStream(pos);线程线程1PipedOutputStream PipedInputStream输出流输出流outStream输入流输入流inStream线程线程234管道流不能直 接读写PrintStream p = new PrintStream( pos );p.println(“hello”);DataInputStream d=new DataInputStream(pis);d.readLine();2. 通过一个中间类来传递信息.线程线程2线程线程1中间类中间类m

25、ssm.write(s)s=m.read()write()read()printStream DataInputStream35管道流可以连接两个线程间的通信两个线程在运行,一个往外输出信息,一个读入信息.将一个写线程的输出通过管道流定义为读线程的输入.outStream = new PipedOutputStream();inStream = new PipedInputStream(outStream);new Writer( outStream ).start();new Reader( inStream ).start(); 36主类主类Pipethread辅类辅类Writer线线程程

26、类类辅类辅类Reader线线程程类类管管道道流流将数据写将数据写到输出流到输出流从流中读数据从流中读数据输入流输入流作为参数传给作为参数传给WriterWriter( outStream )377.4 多线程问题-线程间的通信.import java.io.*;public class Pipethread public static void main(String args) Pipethread thisPipe = new Pipethread(); thisPipe.process(); public void process() PipedInputStream inStream;

27、 PipedOutputStream outStream; PrintStream printOut; try outStream = new PipedOutputStream(); inStream = new PipedInputStream(outStream); new Writer( outStream ).start() new Reader( inStream ).start(); catch( IOException e ) 387.4 多线程问题-线程间的通信class Reader extends Thread private PipedInputStream inStr

28、eam; public Reader(PipedInputStream i)inStream=i; public void run() String line; DataInputStream d; boolean reading = true; d = new DataInputStream( inStream ); while(reading & d != null) tryline = d.readLine(); if( line != null ) System.out.println(Read: + line ); else reading = false; catch( IOExc

29、eption e); tryThread.sleep(4000); catch( InterruptedException e ); 397.4 多线程问题-线程间的通信.class Writer extends Thread private PipedOutputStream outStream; private String messages= Monday,Tuesday,Wednsday,Thursday,Friday :,Saturday:,Sunday :; public Writer(PipedOutputStream o) outStream = o; public void

30、run() PrintStream p = new PrintStream( outStream ); for (int i = 0; i messages.length;i+) p.println(messagesi); p.flush(); System.out.println(WrIte: + messagesi ); try Thread.sleep(4000); catch(InterruptedException e); p.close(); p = null; 40结果可能是:WrIte:MondayRead: MondayWrIte:TuesdayRead: TuesdayRe

31、ad: WednsdayWrIte:WednsdayRead: ThursdayWrIte:ThursdayRead: Friday :WrIte:Friday :WrIte:Saturday:Read: Saturday:Read: Sunday :WrIte:Sunday :41资源协调线程线程A线程线程B1.线程A在数据库中查询存票,发现票C可以卖出2.线程A接受用户订票请求,准备出票.3.这时切换到了线程B执行4.线程B在数据库中查询存票,发现票C可以卖出5.线程B将票卖了出去6.切换到线程A执行,线程A卖了一张已经卖出的票42资源协调线程线程1线程线程2线程线程10资源资源取过来取过

32、来加加1后送回去后送回去withdrwal()withdrwal()透支透支余额余额变量变量43对共享对象的访问必须同步,叫做条件变量.Java语言允许通过监视器(有的参考书称其为管程)使用条件变量实现线程同步.监视器阻止两个线程同时访问同一个条件变量.它如同锁一样作用在数据上.线程1进入withdrawal方法时,获得监视器(加锁);当线程1的方法执行完毕返回时,释放监视器(开锁),线程2的withdrawal方能进入.withdrawal()线程线程1监视器监视器线程线程244用synchronized来标识的区域或方法即为监视器监视的部分。一个类或一个对象有一个监视器,如果一个程序内有两

33、个方法使用synchronized标志,则他们在一个监视器管理之下.一般情况下,只在方法的层次上使用关键区readwrite监监视视器器线程线程1线程线程245此处给出的例子演示两个线程在同步限制下工作的情况.class Account statics int balance=1000; statics int expense=0; public synchronized void withdrawl(int amount) if (amount=balance) balance-=amount; expense+=amount; else System.out.println(“bounce

34、d: “+amount); 46实例范围同步方法 publicd class syncTest synchronized void aMethod() /需要同步使用的代码 synchronized aMethod()可以防止多个线程同时访问这个对象实例的synchronized方法(如果一个对象有多个synchronized方法,只要一个线程访问了其中的一个synchronized方法,其它线程不能同时访问这个对象中任何一个synchronized方法)。47实例范围同步区块 publicd class syncTest void aMethod() /无需同步使用的代码 synchroni

35、zed(this) /需要同步使用的代码块 除了方法前用synchronized关键字,synchronized关键字还可以用于方法中的某个区块中,表示只对这个区块的资源实行互斥访问。用法是: synchronized(this)/*区块*/,它的作用域是当前对象。 48类范围 在类范围内使用synchronized也有同步方法和同步区块两种形式: 类范围同步方法 publicd class syncTest synchronized static void aMethod() /需要在类范围同步使用的代码 49synchronized static aStaticMethod防止多个线程同时

36、访问这个类中的synchronized static 方法。它可以对类的所有对象实例起作用。也就是说在一个JVM中,同一时间最多有一个该类的静态同步方法在执行。这样的方法可以应用到多线程的同步中,实现各线程直接的数据共享和互动50类范围同步区块 publicd class syncTest static void aMethod() /无需同步使用的代码 synchronized (syncTest.class) /需要在类范围同步使用的代码 类范围同步区块功能与类范围同步方法相同,只是对一个区块的代码的同步。用法是:在static 方法内加同步区块:sychronized (类名.class

37、) /*区块*/。 51synchronized关键字是不能继承的,也就是说,基类的方法synchronized f() 在继承类中并不自动是synchronized f(),而是变成了f()。继承类需要你显式的指定它的某个方法为synchronized方法; 522. 等待同步数据生产者生产者消费者消费者.共享对象共享对象writeread可能出现的问题可能出现的问题:生产者比消费者快时生产者比消费者快时,消费者会漏掉一些数据消费者会漏掉一些数据没有取到没有取到消费者比生产者快时消费者比生产者快时,消费者取相同的数据消费者取相同的数据.notify()和和wait ()方法用来协调读取的关系

38、方法用来协调读取的关系.notify()和和wait ()都只能从同步方法中的调用都只能从同步方法中的调用.53notify的作用是唤醒正在等待同一个监视器的线程.wait的作用是让当前线程等待信息版例子read()方法在读信息之前先等待,直到信息可读,读完后通知要写的线程.write()方法在写信息之前先等待,直到信息被取走,写完后通知要读的进程.54writerreaderaaaabbbbbccccaaaaaaaaaaaaaaaaaaaaaaaabbbbbcccc ccccccccccccbbbbbcccc55public class WaitNotifyDemo public stati

39、c void main(String args) MessageBoard m = new MessageBoard(); Reader readfrom_m = new Reader(m); Writer writeto_m=new Writer(m); writeto_m.start(); readfrom_m.start(); 567.3 多线程问题-资源协调class MessageBoard private String message; private boolean ready = false; public synchronized String read() while (r

40、eady = false) try wait(); catch (InterruptedException e) ready = false; notify(); return message; public synchronized void write(String s) while (ready = true) try wait(); catch (InterruptedException e) message = s;System.out.println(Boad Got:+s); ready = true; notify(); 577.3 多线程问题-资源协调class Reader

41、 extends Thread private MessageBoard mBoard; public Reader(MessageBoard m) mBoard = m; public void run() String s = ;boolean reading = true;while( reading ) s = mBoard.read(); System.out.println(Reader read: + s); if( s.equals(logoff) ) reading = false; System.out.println(Finished: 10 seconds.); try

42、 sleep( 10000 ); catch (InterruptedException e) 587.3 多线程问题-资源协调class Writer extends Thread private MessageBoard mBoard; private String messages = Monday :-,.,Sunday : -; public Writer(MessageBoard m) mBoard = m; public void run() for (int i = 0; i messages.length; i+) System.out.println(Writer wrot

43、e: + messagesi ); mBoard.write(messages i ); try sleep(int)(Math.random() * 100); catch (InterruptedException e) System.out.println(Writer wrote: + logoff); mBoard.write(logoff); 59notifyAll()让等待某个对象K的所有线程离开阻塞状态, notify()随机地选取等待某个对象K的线程,让它离开阻塞状态sleep()方法是使线程停止一段时间的方法。在sleep 时间间隔期满后,线程不一定立即恢复执行。这是因为在

44、那个时刻,其它线程可能正在运行而且没有被调度为放弃执行,除非:(a)“醒来”的线程具有更高的优先级 (b)正在运行的线程因为其它原因而阻塞60waite()和notify()因为会对对象的“锁标志”进行操作,所以它们必须在synchronized函数或synchronizedblock中进行调用。如果在non-synchronized函数或non-synchronizedblock中进行调用,虽然能编译通过,但在运行时会发生IllegalMonitorStateException的异常61多线程问题-资源的协调和锁定1. 死锁问题如果你持有一个锁并试图获取另一个锁时,就有死锁的危险.解决死锁问

45、题的方法:给条件变量施加排序线程线程2pen线程线程1note把把“pen”给我给我,我我才能给你才能给你“note”把把“note”给我给我,我我才能给你才能给你“pen”62多线程问题-daemon线程什么是daemon(守护)?在客户/服务器模式下,服务器的作用是等待用户发来请求,并按请求完成客户的工作守护线程是为其它线程提供服务的线程守护线程一般应该是一个独立的线程,它的run()方法是一个无限循环.守护线程与其它线程的区别是,如果守护线程是唯一运行着的线程,程序会自动退出客户端 服务器端requestdaemon63调用isDaemon(),可调查一个线程是不是一个Daemonset

46、Daemon()打开或者关闭一个线程的Daemon状态如果是一个Daemon线程,那么它创建的任何线程也会自动具备Daemon属性。64小结1. 实现线程有两种方法:实现Ruannable接口继承Thread类2. 在小应用中通常在start中创建线程3.当新线程被启动时,java调用该线程的run方法,它是Thread的核心.4. 线程由四个状态:新生,运行,暂停,死亡655. 两个或多个线程竞争资源时,需要用同步的方法协调资源.6. 多个线程执行时,要用到同步方法,即使用 synchronized的关键字设定同步区7. wait和notify起协调作用8. 守护进程的特点是当程序中只剩它自己时,会自动中止.66

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 办公、行业 > 各类PPT课件(模板)
版权提示 | 免责声明

1,本文(多线程ppt课件.ppt)为本站会员(三亚风情)主动上传,163文库仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。
2,用户下载本文档,所消耗的文币(积分)将全额增加到上传者的账号。
3, 若此文所含内容侵犯了您的版权或隐私,请立即通知163文库(发送邮件至3464097650@qq.com或直接QQ联系客服),我们立即给予删除!


侵权处理QQ:3464097650--上传资料QQ:3464097650

【声明】本站为“文档C2C交易模式”,即用户上传的文档直接卖给(下载)用户,本站只是网络空间服务平台,本站所有原创文档下载所得归上传人所有,如您发现上传作品侵犯了您的版权,请立刻联系我们并提供证据,我们将在3个工作日内予以改正。


163文库-Www.163Wenku.Com |网站地图|