前言 多线程作为Android开发中相对而言较为高阶的知识,其中用到相关的知识点是非常的多,所以在我们需要进行设计或者写多线程的代码就必须要进行相对谨慎的处理,这样就由必要对其要有着比较系统化的认知Android多线程机制 我们一般将Android应用分成为两种:主线程和工作线程;主线程主要是用来进行初始化UI,而工作线程主要是进行耗时操作,例如读取数据库,网络连接等 Android系统是以进程为单位来对应用程序资源进行限制,这个问题的可以解释为:一个进程最多能够开几个线程?最好能开几个?但实则这个是没有上限这一说,主要是因为资源的限制 Android中关于主线程的理解:Android的主线程是UI线程,在Android中,四大组件运行在主线程中,在主线程中做耗时操作会导致程序出现卡顿甚至出现ANR异常,一个。 在一个程序中,这些独立运行的程序片断叫作线程(Thread),利用它编程的概念就叫作多线程处理。多线程处理一个常见的例子就是用户界面。多线程基础 线程总的来就是进程的一个实体,是CPU进行分派和调度的基本单位,拥有着比进程更小且能够独立运行的基本单位,线程本身基本上是不拥有系统资源,仅拥有一点在运行过程中必须拥有的资源,但它可与同属一个进程中的其他进程进行共享其所拥有的所有资源 线程状态 线程状态有些地方将之分为5中状态,而且在JavaJdk中线程被其定义为6中状态,我们可以对其进行类比 普遍定义的5中状态:新建,就绪,运行,阻塞,死亡 JavaJdk定义状态线程阻塞 线程阻塞是指在某一时刻的某一个线程在进行运行一段代码的情况下,突然另一个线程也要进行运行,但在运行过程中,那个线程执行完全运行之前,另一个线程是不可能获取到CPU的执行权,就会导致线路阻塞的出现 死锁 死锁也称之为抱死,意思就是说一个进程锁定了另外一个进程所需要的页或表是,但第二个进程同时又锁定了第一个进程所需的一页,这样就会出现死锁现象 使用代码实现死锁publicclassDeadLockimplementsRunnable{注意。。。这里对象必须是static类型的,保证锁住的是同一个对象privatestaticfinalObjectobject1newObject();privatestaticfinalObjectobject2newObject();publicDeadLock(intflag){this。}Overridepublicvoidrun(){if(flag1){synchronized(object1){System。out。println(持有对象object1的锁,等待持有object2锁释放资源);try{Thread。sleep(2000);}catch(InterruptedExceptione){e。printStackTrace();}synchronized(object2){System。out。println(程序结束);}}}if(flag2){synchronized(object2){System。out。println(持有对象object2的锁,等待持有object1锁释放资源);try{Thread。sleep(2000);}catch(InterruptedExceptione){e。printStackTrace();}synchronized(object1){System。out。println(程序结束);}}}}}publicclassClient{publicstaticvoidmain(String〔〕args){newThread(newDeadLock(1))。start();newThread(newDeadLock(2))。start();持有对象object1的锁,等待持有object2锁释放资源持有对象object2的锁,等待持有object1锁释放资源。。。。。。。程序一直运行。。。。。。。}}线程使用 创建线程 简要介绍实现线程的三种方式:继承Thread,实现runnable,实现callable。这里有一点需要注意的是,实现callable是与线程池相关联的而callable很重要的一个特性是其带有返回值。当我们只需实现单线程时实现runnable更加利于线程程序的拓展publicclassHappyThreadextendsThread{Overridepublicvoidrun(){super。run();System。out。println(继承Thread);}}publicclassJobRunnableimplementsRunnable{Overridepublicvoidrun(){try{Thread。sleep(1000);System。out。println(实现runnable实现线程);}catch(InterruptedExceptione){e。printStackTrace();}}}publicclassEnjoyCallableimplementsCallableString{OverridepublicStringcall()throwsException{Thread。sleep(2000);return实现callable实现线程池;}}publicclassClient{publicstaticvoidmain(String〔〕args){继承thread实现线程newHappyThread()。start();runnable与线程newThread(newJobRunnable())。start();callable与线程池包含返回值ExecutorServiceexecutorServiceExecutors。newCachedThreadPool();FutureStringsubmitexecutorService。submit(newEnjoyCallable());try{System。out。println(submit。get());submit。cancel(true);}catch(InterruptedExceptione){e。printStackTrace();}catch(ExecutionExceptione){e。printStackTrace();}}继承Thread1s后实现runnable实现线程2秒后实现callable实现线程池}守护线程 在线程开启之前进行调用thread。setDaemon(true);将thread设定成当前线程中的守护线程使用案例publicclassDaemonThreadClient{publicstaticvoidmain(String〔〕args)throwsInterruptedException{ThreadthreadnewDaemonThread();thread。setDaemon(true);thread。start();Thread。sleep(20);System。out。println(主线程结束);}}classDaemonThreadextendsThread{Overridepublicvoidrun(){while(true){try{Thread。sleep(5);System。out。println(守护线程运行中);}catch(InterruptedExceptione){e。printStackTrace();}}}}output守护线程运行中守护线程运行中守护线程运行中守护线程运行中主线程结束Processfinishedwithexitcode0yield线程让步与join合并等待线程结束 线程让步【yield方法】让当前线程释放CPU资源,让其他线程抢占publicclassYieldClient{publicstaticvoidmain(String〔〕args){newThreadA()。start();newThreadB()。start();}}classThreadAextendsThread{publicThreadA(){setPriority(2);}Overridepublicvoidrun(){yield();for(inti0;i10;i){System。out。println(ThreadA低优先级的运行);}}}classThreadBextendsThread{publicThreadB(){setPriority(8);}Overridepublicvoidrun(){for(inti0;i10;i){System。out。println(ThreadB高优先级的运行);}}}outputThreadB高优先级的运行。。。ThreadB高优先级的运行ThreadA低优先级的运行ThreadA低优先级的运行ThreadA低优先级的运行ThreadA低优先级的运行。。。ThreadA低优先级的运行ThreadA低优先级的运行Processfinishedwithexitcode0线程阻塞等待但不会释放锁资源publicclassJoinClient{publicstaticvoidmain(String〔〕args)throwsInterruptedException{JoinAThreadjoinAThreadnewJoinAThread();joinAThread。start();joinAThread。join();System。out。println(主线程开始);Thread。sleep(10);System。out。println(主线程运行中);Thread。sleep(10);System。out。println(主线程运行中);System。out。println(主线程结束);}}classJoinAThreadextendsThread{Overridepublicvoidrun(){super。run();try{System。out。println(JoinAThread开始);Thread。sleep(30);System。out。println(JoinAThread运行中);Thread。sleep(30);System。out。println(JoinAThread运行中);System。out。println(JoinAThread结束);}catch(InterruptedExceptione){e。printStackTrace();}}}outputJoinAThread开始JoinAThread运行中JoinAThread运行中JoinAThread结束主线程开始主线程运行中主线程运行中主线程结束Processfinishedwithexitcode0线程终止publicclassInterruptClient{publicstaticvoidmain(String〔〕args){newInterruptThread()。start();}}classInterruptThreadextendsThread{Overridepublicvoidrun(){super。run();for(inti0;i10;i){if(isInterrupted()){System。out。println(线程打断而结束);}System。out。println(线程执行。。。i);if(i2){终止线程interrupt();}}}}output线程执行。。。0线程执行。。。1线程执行。。。2线程打断而结束Processfinishedwithexitcode0线程关键知识点 Java中的sleep与wait区别测试sleep和wait区别publicclassClient{publicstaticvoidmain(String〔〕args)throwsInterruptedException{ProductproductnewProduct();newThread(newChildSetRunnable(product),setthread)。start();主线程睡眠,保证获取线程晚于设置线程的执行Thread。sleep(500);newThread(newChildGetRunnable(product),getthread)。start();}}publicclassChildGetRunnableimplementsRunnable{privatePpublicChildGetRunnable(Productproduct){this。}Overridepublicvoidrun(){运行加锁System。out。println(Thread。currentThread()。getName()run());synchronized(product){System。out。println(Thread。currentThread()。getName()System。currentTimeMillis()读取价格product。getPrice());}}}publicclassChildSetRunnableimplementsRunnable{privatePpublicChildSetRunnable(Productproduct){this。}Overridepublicvoidrun(){System。out。println(Thread。currentThread()。getName()run());synchronized(product){try{System。out。println(Thread。currentThread()。getName()System。currentTimeMillis()设置价格100开始);1。测试sleep释放CPU时间片,但仍然持有对product的锁资源Thread。sleep(3000);2。测试wait释放CPU时间片,但是会释放锁资源product。wait(3000);product。setPrice(100);System。out。println(Thread。currentThread()。getName()System。currentTimeMillis()设置价格100结束);}catch(InterruptedExceptione){e。printStackTrace();}}}} 这种具体某个对象锁waitnotify方法与Condition的await以及signal方法类似;全面这种方法的阻塞等待都可以是释放锁,而且在唤醒后,这种线程都是能够获取锁资源的,而这个门栓就跟阀门类似结语 今天的课程就到这里了,有需要文章中所涉及到的源码可以点击下方评论区留言或者点击我的头像私信我