Java的多线程机制.ppt
《Java的多线程机制.ppt》由会员分享,可在线阅读,更多相关《Java的多线程机制.ppt(60页珍藏版)》请在装配图网上搜索。
Java的多线程机制,Java的多线程机制,2,主要内容,线程的概念线程的生命周期Java中多线程的编程继承Thread类与使用Runnable接口Thread类的主要方法线程的同步与死锁动画,Java的多线程机制,3,程序-进程-线程,程序是为完成特定任务、用某种语言编写的一组指令的集合。指一段静态的代码。进程是程序的一次执行过程,是系统进行调度和资源分配的一个独立单位。,Java的多线程机制,4,程序-进程-线程,线程是比进程更小一级的执行单元。一个进程在其执行过程中,可以产生多个线程,形成多条执行线索。每个线程也有它自身的产生、存在和消亡的过程,也是一个动态的概念。一个线程有它自己的入口和出口,以及一个顺序执行的序列线程不能独立存在,必须存在于进程中,各线程间共享进程空间的数据。线程线程创建、销毁和切换的负荷远小于进程,又称为轻量级进程(lightweightprocess)。系统负担小,主要是CPU的分配。,Java的多线程机制,5,基本概念之一:进程,进程是正在运行的一个程序程序:静态对象进程:动态过程操作系统为每个进程分配一段内存空间,包括:代码、数据以及堆栈等资源多任务的操作系统(OS)中,进程切换对CPU资源消耗较大,Java的多线程机制,6,基本概念之二:多线程,多线程是指同时存在几个执行体,按几条不同的执行线索共同工作的情况。多线程实现单个进程中的并发计算。各线程间共享进程空间的数据,并利用这些共享单元来实现数据交换、实时通信与必要的同步操作。多线程的程序能更好地表述和解决现实世界的具体问题,是计算机应用开发和程序设计的一个必然发展趋势。,Java的多线程机制,7,进程与多线程,Java的多线程机制,8,线程的调度,调度策略时间片抢占式:高优先级的线程抢占CPUJava的调度方法同优先级线程组成先进先出队列,使用时间片策略对高优先级,使用优先调度的抢占式策略,1,2,Java的多线程机制,9,Java与多线程,Java语言的一个重要功能特点就是内置对多线程的支持,它使得编程人员可以很方便地开发出具有多线程功能,能同时处理多个任务的功能强大的应用程序。每个Java程序都有一个隐含的主线程applicationmain方法Applet小程序,主线程指挥浏览器加载并执行Java小程序。,Java的多线程机制,10,线程的概念模型,Java的多线程机制,11,线程的生命周期,要想实现线程,必须在主线程中创建新的线程对象。Java语言使用Thread类及其子类的对象来表示线程,在它的一个完整的生命周期中通常要经历如下的五种状态:新建:当一个Thread类或其子类的对象被声明并创建时,新生的线程对象处于新建状态就绪:处于新建状态的线程被启动后,将进入线程队列等待CPU时间片,此时它已具备了运行的条件运行:当就绪的线程被调度并获得处理器资源时,便进入运行状态,run()方法定义了线程的操作和功能阻塞:在某种特殊情况下,被人为挂起或执行输入输出操作时,让出CPU并临时中止自己的执行,进入阻塞状态死亡:线程完成了它的全部工作或线程被提前强制性地中止stop()或destroy(),Java的多线程机制,12,线程的生命周期,Java的多线程机制,13,线程的生命周期(续),Newborn:线程已创建,但尚未执行Runnable:(就绪)线程已被调度,按优先级和先到先服务原则在队列中排队等待CPU时间片资源Runnnig:正在运行Blocked:(阻塞)因某事件或睡眠而被暂时性地挂起Dead:正常/强行中断,退出运行状态,Java的多线程机制,14,线程状态,Java的多线程机制,15,Java对多线程的支持,提供对多线程的支持Thread类start(),stop(),run()Runnable接口实现多线程的两种编程方法继承Thread类实现Runnable接口,Java的多线程机制,16,Thread类,Thread类综合了Java程序中一个线程需要拥有的属性和方法当生成一个Thread类的对象后,一个新的线程诞生了。每个线程都是通过目标对象的方法run()来完成其操作的。方法run()称为线程体(线程方法)。提供线程体的目标对象是在初始化一个线程时指明的。任何实现了Runnable接口(实现run()方法)的类实例都可以作为线程的目标对象。,Java的多线程机制,17,方法之一:继承Thread类,Thread类的重要方法:run()定义线程的具体操作系统调度此线程时自动执行初始时无具体操作内容如何编程呢?,继承Thread类,定义run()方法,Java的多线程机制,18,Easy?Letstryit!,小例子:SimpleThread.javaTwoThreadsTest.java,Java的多线程机制,19,Java的多线程机制,20,Thread类,java.lang包构造函数Thread();Thread(Stringthreadname);指定线程实例名线程的优先级控制三个常量:MAX_PRIORITY10;MIN_PRIORITY1;NORM_PRIORITY5;getPriority()返回线程优先值setPriority(intnewPriority)改变线程的优先级线程创建时继承父线程的优先级,Java的多线程机制,21,Thread类的有关方法,voidstart():由Newborn到Runnable启动线程StringgetName():返回线程的名称run():线程在被调度时执行的操作staticvoidsleep(指定时间毫秒):令当前活动线程在指定时间段内放弃对CPU控制,使其他线程有机会被执行,时间到后重排队产生例外InterruptedException用try块调用sleep(),用catch块处理例外,Java的多线程机制,22,Thread类的有关方法(续),suspend():挂起线程,处于阻塞状态resume():恢复挂起的线程,重新进入就绪队列排队应用:可控制某线程的暂停与继续方法:设一状态变量suspendStatus=false(初始)暂停:if(!suspendStatus)T.suspend();suspendStatus=true;继续:if(suspendStatus)T.resume();suspendStatus=false;,Java的多线程机制,23,Thread类的有关方法(续),staticvoidyield():对正在执行的线程若就绪队列中有与当前线程同优先级的排队线程,则当前线程让出CPU控制权,移到队尾若队列中没有同优先级的线程,忽略此方法stop():强制线程生命期结束booleanisAlive():返回boolean,表明是否线程还存在staticcurrentThread():返回当前线程,Java的多线程机制,24,生成与运行线程方法1,Java的多线程机制,25,建立线程,Java的多线程机制,26,Thread类方法总结,启动线程:start()有关线程执行的控制:stop()、suspend()、resume()有关调度控制Thread.sleep(10);/低优先级的线程也可以获得执行Thread.yield();/同优先级的线程可以获得执行suspend();/暂停本线程,Java的多线程机制,27,方法之二:Runnable,Runnable接口自定义类(,该类)实现Runnable接口使用Thread类的另一构造函数:Thread(Runnable,String)用实现了Runnable接口的类的对象中所定义的run()方法,来覆盖新创建的线程对象的run()方法使用start()启动线程,Java的多线程机制,28,方法之二:Runnable(续),例:classAimplementsRunnablepublicvoidrun().classBpublicstaticvoidmain(Stringarg)Runnablea=newA();Threadt=newThread(a);t.start();,用实现了Runnable接口的类的对象中所定义的run()方法,来覆盖新创建的线程对象的run()方法,Java的多线程机制,29,建立线程例,publicclassThreadTestpublicstaticvoidmain(Stringargs)Job1j=newJob1();Threadt1=newThread(j);t1.start();classJob1implementsRunnableinti=1;publicvoidrun()while(i50)System.out.println(i+);,Java的多线程机制,30,建立线程,Java的多线程机制,31,生成与运行线程方法2,classMyRunimplementsRunnablepublicvoidrun()线程体MyRunmr=newMyRun();Threadt1=newThread(mr);t1.start();/Thread实例用于线程控制适合于:定义run()方法的类必须是其他类或其他类的子类。,Java的多线程机制,32,方法之二:Runnable(续),两种方法的选择当需要从其他类,如Applet类继承时,使用Runnable接口当编写简单的程序时,可考虑使用继承Thread类例:RaceApplet.java具体运行结果(线程调度)与平台有关,Java的多线程机制,33,Java的多线程机制,34,publicvoidinit()/重载Applet的init()方法for(inti=0;iNUMRUNNERS;i+)runnersi=newRunner();/创建赛跑线程线程runnersi.setPriority(i+1);/设优先级first=1,second=2if(updateThread=null)/创建绘图线程,并设优先级为3updateThread=newThread(this,ThreadRace);updateThread.setPriority(NUMRUNNERS+1);addMouseListener(newMyAdapter();/注册事件监听者/endofinit(),Java的多线程机制,35,/内部事件监听者类,监听鼠标事件classMyAdapterextendsMouseAdapter/鼠标点击后,开始赛跑及绘制线程publicvoidmouseClicked(MouseEventevt)if(!updateThread.isAlive()updateThread.start();/启动绘制线程for(inti=0;iNUMRUNNERS;i+)if(!runnersi.isAlive()runnersi.start();/启动赛跑线程/endofclassMyAdapter,Java的多线程机制,36,publicvoidpaint(Graphicsg)/paint()方法中绘制框架/endofpaint()/update()方法中绘制赛跑者的进度publicvoidupdate(Graphicsg)for(inti=0;iNUMRUNNERS;i+)/画两条线g.drawLine(SPACING,(i+1)*SPACING,SPACING+(runnersi.tick)/100000,(i+1)*SPACING);/endofupdate(),Java的多线程机制,37,publicvoidrun()/实现Runnable接口的run()方法while(true)repaint();/重新绘制,自动调用update()方法tryThread.sleep(10);/休眠,把执行机会让给低优先级线程catch(InterruptedExceptione)/endofrun()publicvoidstop()/重载Applet的stop()方法for(inti=0;iNUMRUNNERS;i+)if(runnersi.isAlive()runnersi=null;/中止赛跑线程if(updateThread.isAlive()updateThread=null;/中止绘图线程/endofstop()/RaceApplet.java,Java的多线程机制,38,线程的同步与互斥,问题的提出多个线程执行的不确定性引起执行结果的不稳定如线程A:A1A2线程B:B1B2多个线程对内存、数据的共享,会造成操作的不完整性,会破坏数据。如push(a):i+;numi=a;pop():取出numi;i-;,Java的多线程机制,39,线程的同步与互斥,问题的解决同步:用synchronized关键字前缀给针对共享资源的操作加锁;同步方法、同步块synchronizedvoidpush();synchronizedintpop();临界区实现机制:管程,Java的多线程机制,40,线程的同步与互斥,对象互斥锁在Java中,每个对象有一个“互斥锁”,该锁可用来保证在同一时刻只能有一个线程访问该对象。锁的使用过程(当一个线程要操作一个对象时),是,Java的多线程机制,41,线程的同步与互斥,加锁1(临界区-方法)synchronized方法名进入该方法时加锁加锁2(临界区-代码块)方法名.synchronized(this)/进入该代码段时加锁.一个线程为某对象加锁后,便对该对象具有了监控权。,Java的多线程机制,42,线程的同步与互斥,线程间需协调与通讯:生产者/消费者问题,Java的多线程机制,43,线程的同步与互斥,wait()与notify()Object类的方法:publicfinalvoidwait():令当前线程挂起并放弃管程,同步资源解锁,使别的线程可访问并修改共享资源,而当前线程排队等候再次对资源的访问notify()唤醒正在排队等待资源管程的线程中优先级最高者,使之执行并拥有资源的管程wait()+notify()+标志变量:可协调、同步不同线程的工作,Java的多线程机制,44,线程的同步与互斥,Java的多线程机制,45,线程的同步与互斥,publicfinalvoidwait()方法在当前线程中调用方法:对象名.wait()使当前线程进入等待(某对象)状态,直到另一线程对该对象发出notify(或notifyAll)为止。调用方法的必要条件:当前线程必须具有对该对象的监控权(加锁)当前线程将释放对象监控权,然后进入等待队列(wait队列)。在当前线程被notify后,要重新获得监控权,然后从断点处继续代码的执行。,Java的多线程机制,46,线程的同步与互斥,publicfinalvoidnotify()方法在当前线程中调用方法:对象名.notify()功能:唤醒等待该对象监控权的一个线程。调用方法的必要条件:当前线程必须具有对该对象的监控权(加锁)notifyAll()唤醒wait队列中的所有线程,并把它门移入锁申请队列。,Java的多线程机制,47,线程状态,Java的多线程机制,48,线程调度,publicstaticvoidsleep(longmillis)当前进程休眠指定时间publicstaticvoidyield()主动让出CPU,重新排队正在执行的线程将CPU让给其他具有相同优先级的线程,自己进入就绪状态重新排队publicfinalvoidjoin()等待某线程结束,Java的多线程机制,49,等待另一线程结束,Runnableot=newotheeThread();Threadtt=newThread(ot);tt.start();/执行自己的工作trytt.join();catch(interruptedExceptione)./继续做自己的事,Java的多线程机制,50,终止线程,publicclassRimplementRunnableprivatebooleantimeToQuit=false;/设标记publicvoidrun()while(!timeToQuit)publicvoidstopRunning()timeToQuit=true;publicclasstestpublicstaticvoidmain(Stringargs)Runnabler=newR();Threadt=newThread(r);t.start();if()r.stopRunning();,Java的多线程机制,51,线程的同步与互斥,Wait_Notify程序CubbyHole.java创建用户的线程子类Producer:产生数据(存数据);Consumer:消费数据(取数据)CubbyHole类,共享数据区,同步方法put(intvalue)方法intget()方法主类中创建共享数据对象,并启动两线程,Java的多线程机制,52,classCubbyHoleprivateintseq;/共享数据privatebooleanavailable=false;/条件标志变量publicsynchronizedintget()/取数据的同步方法get()while(available=false)trywait();/条件不符合,则waitcatch(InterruptedExceptione)available=false;/修改条件notify();/通知唤醒其他等待管程的线程returnseq;/返回要取出的数值/endofget(),Java的多线程机制,53,/存放数据的同步方法put()publicsynchronizedvoidput(intvalue)while(available=true)trywait();/条件不符合,则waitcatch(InterruptedExceptione)seq=value;/把共享变量修改为要放置的数据available=true;/修改条件notify();/通知唤醒其他等待管程的线程/endofput()/endofclassCubbyHole,Java的多线程机制,54,classProducerextendsThread/生产者线程类privateCubbyHolecubbyhole;privateintnumber;publicProducer(CubbyHolec,intnumber)cubbyhole=c;this.number=number;publicvoidrun()/定义run()方法for(inti=0;i10;i+)/共产生10个cubbyhole.put(i);System.out.println(Producer#+this.number+put:+i);trysleep(int)(Math.random()*100);catch(InterruptedExceptione)/endofclassProducer,Java的多线程机制,55,classConsumerextendsThread/消费者线程类privateCubbyHolecubbyhole;privateintnumber;publicConsumer(CubbyHolec,intnumber)cubbyhole=c;this.number=number;publicvoidrun()/定义run()方法intvalue=0;for(inti=0;i10;i+)/消费10个value=cubbyhole.get();System.out.println(Consumer#+this.number+got:+value);/endofclassConsumer,Java的多线程机制,56,classProducerConsumerTest/主类:测试publicstaticvoidmain(Stringargs)CubbyHolec=newCubbyHole();/theshareddataobjectProducerp1=newProducer(c,1);/Producer线程Consumerc1=newConsumer(c,1);/Consumer线程p1.start();/启动生产者线程c1.start();/启动消费者线程/endofProducerConsumerTest程序执行结果:生产者线程和消费者线程严格地轮流执行,获得了线程间的协调执行。,Java的多线程机制,57,线程的死锁,死锁不同的线程分别占用对方需要的同步资源不放弃,都在等待对方放弃自己需要的同步资源,就形成了线程的死锁解决方法专门的算法、原则尽量减少同步资源的定义,Java的多线程机制,58,动画,即若干幅相近的图片接连显示例:旋转的地球RollEarth.java,Java的多线程机制,59,publicclassRollEarthextendsAppletimplementsRunnablepublicvoidrun()/实现动画while(true)/循环往复地显示每一帧图片trydisplayImage(m_Graphics);m_nCurrImage+;if(m_nCurrImage=NUM_IMAGES)m_nCurrImage=0;Thread.sleep(50);catch(InterruptedExceptione)/endofrun()/endofclass,Java的多线程机制,60,课后作业,P202.第11、12、13题,- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- Java 多线程 机制
装配图网所有资源均是用户自行上传分享,仅供网友学习交流,未经上传用户书面授权,请勿作他用。
关于本文