Android开发秘籍学习笔记(二)
来源:互联网 发布:win10如何更改mac地址 编辑:程序博客网 时间:2024/05/21 07:06
Android中有关线程Thread等相关知识的笔记
线程Thread
每个应用程序在创建时都会默认运行单一的进程,其中包含所有的任务。为避免用户界面被挂起,那些耗时的任务 ,诸如网络下载或密集的计算,应当驻留于单独的后台线程中,如何适当地实现这种操作由开发者决定,但之后则是由Android系统基于开发者的实现来确定线程的优先级。
大多数应用程序都通过使用线程来提升性能。如果用户界面的挂起在软件设计阶段没有被发觉,到了测试阶段就会迅速体现出来,因为Android系统会在用户界面挂起时弹出警告—告诉用户Slow app isn’t responding.
Android Thread的使用方法:
Thread的使用方法主要有两种方法:其中一种是extends Thread,然后重载Thread的run()函数,另一种是构建一个新的Thread对象,可带Runnable或不带。但不管怎么样,都是要通过start()函数来运行相应的代码
构建Thread对象的方法如下:
1、Thread()不代任何参数,该方法会在构建的时候自动生成线程名字。
举例:
Thread mThread = new Thread(){ @Override public void run() { // TODO Auto-generated method stub System.out.println("This is thread_test"); super.run(); } }; mThread.start(); System.out.println(mThread.getName());
得到的logcat:
04-27 09:22:08.692: INFO/System.out(831): Thread-1004-27 09:22:08.702: INFO/System.out(831): This is thread_test
2、Thread(Runnable runnable)该函数多了Runnable个对象,被运行的代码在Runnable对象里。
举例:
Runnable mRunnable = new Runnable(){ @Override public void run() { // TODO Auto-generated method stub System.out.println("This is thread with Runnable"); } }; Thread mThread = new Thread(mRunnable); mThread.start(); System.out.println(mThread.getName());
得到的logcat:
04-27 09:37:47.832: INFO/System.out(865): Thread-1104-27 09:37:47.861: INFO/System.out(865): This is thread with Runnable
3、Thread(Runnable runnable,String threadName)该函数有Runnable也有自己的名字threadName。
举例:
Runnable mRunnable = new Runnable(){ @Override public void run() { // TODO Auto-generated method stub System.out.println("This is thread with Runnable and Name"); } }; Thread mThread = new Thread(mRunnable,"mThreadTest"); mThread.start(); System.out.println(mThread.getName());
得到的logcat:
04-27 09:44:03.682: INFO/System.out(900): mThreadTest04-27 09:44:03.702: INFO/System.out(900): This is thread with Runnable and Name
Runable和Thread的关系
在java中可有两种方法实现多线程,一种是继承Thread类,一种是实现Runnable接口;
1)继承Thread类的方式
Thread类是在java.lang包中定义的 。一个类只要继承了Thread类同时覆写了本类中的run()
步骤就可以实现多线程操作了,然而一个类只能继承一个父类,这是此种方法的的局限 。 下面看例子:
class MyThread extends Thread{ private String name; public MyThread(String name) { super(); this.name = name; } public void run() { for(int i=0;i<10;i++) { System.out.println("线程开端:"+this.name+",i="+i); } }}public class ThreadDemo01 { public static void main(String[] args) { MyThread mt1=new MyThread("线程a"); MyThread mt2=new MyThread("线程b"); mt1.start(); mt2.start(); }}
2) Runnable接口
在实际开辟中一个多线程的操作很少 使用Thread类,而是通过Runnable接口实现 。 public interface Runnable{ public void run(); }
例子:
class MyThread implements Runnable{ private String name; public MyThread(String name) { this.name = name; } public void run(){ for(int i=0;i<100;i++){ System.out.println("线程开端:"+this.name+",i="+i); } }};
然而在Runnable的子类中没有start() 方法,只有Thread类中才有 。此时视察Thread类,有一个构造函数:public Thread(Runnable targer) 此构造函数接受Runnable的子类实例,也就是说可以通过Thread类来启动Runnable实现多线程 。(start() 可以协调系统的资源):
public class ThreadDemo01 { public static void main(String[] args) { MyThread mt1=new MyThread("线程a"); MyThread mt2=new MyThread("线程b"); new Thread(mt1).start(); new Thread(mt2).start(); }}
3)实际中如何应用这两种实现模式
在程序实现多线程应优先以实现Runnable接口为主,由于实现Runnable接口相比继承Thread类有如下好处:
1.避免点继承的局限,一个类可以继承多个接口 。
2. 利于资源的共享。
以卖票程序为例,通过Thread类实现:
class MyThread extends Thread { private int ticket=10; public void run(){ for(int i=0;i<20;i++) { if(this.ticket>0){ System.out.println("卖票:ticket"+this.ticket--); } } }};
下面通过三个线程对象,同时卖票:
public class ThreadTicket { public static void main(String[] args) { MyThread mt1=new MyThread(); MyThread mt2=new MyThread(); MyThread mt3=new MyThread(); mt1.start();//每个线程都各卖了10张,共卖了30张票 mt2.start();//但实际只有10张票,每个线程都卖自己的票 mt3.start();//没有达到资源共享 }}
假如用Runnable就 可以实现资源共享,下面看例子:
class MyThread implements Runnable{ private int ticket=10; public void run(){ for(int i=0;i<20;i++){ if(this.ticket>0){ System.out.println("卖票:ticket"+this.ticket--); } } }}public class RunnableTicket {public static void main(String[] args) { MyThread mt=new MyThread(); new Thread(mt).start();//同一个mt new Thread(mt).start(); new Thread(mt).start();}};
现在程序中有三个线程,然而一共卖了10张票,也就是说使用Runnable实现多线程可以达到资源共享的目的。
4)Runnable接口和Thread的关系总结
(1) 说白了就是类和接口的区别。Thread是一个类,java中是不允许继承多个父类的,这就是Thread的一个局限性。而使用Runnable就不同了,可以implements多个接口,同时继承一个父类,这样会更加灵活。
(2) 当多个线程需要共享资源时,用Thread很难达到目的,但是用Runnable接口就容易许多了。
(3) 二者的联系:看源码可以发现,Thread其实就是继承了Runnable接口的子类。
取消线程
有时,当一个组件完成或被杀死是,开发者希望有它产生的线程也同样被杀死,例如在某个Acitivity中定义了线程:
private …Thread myThread;
myThread.stop()方法已经被弃用了,因为它会将应用程序置于不可预知的状态,取而代之的是下面的方法,比如在父组件的onStop()方法中加入
if(myThread != null){ Thread dummy = myThread; myThread = null; dummy.interrupt();}
在应用程序层面上还有另外一种方法来完成相同的工作:使用setDaemon(true)方法将所有生成的线程都声明为守护线程,可以确保所有与应用程序关联的线程在应用程序的主线程终结时,也随之被杀死。
//use when initially starting a threadmyThread。setDaemon(true);myThread.start();
设置线程的优先级
Android系统会处理线程的优先级,默认情况下,一个新线程,如myThread,其优先级被定为5。开发者可以在myThread.start()执行之前,通过调用myThread.setPriority(priority)来为线程设定另外的优先级。优先级不能高于Thread.MAX_PRIORITY(10)或者低于Thread.MIN_PRIORITY(1)
Android还提供了另一种设定线程优先级的方法通过android.os.Process.setThreadPriority (int tid, int priority)
priority:【-20, 19】,高优先级 -> 低优先级。在实际操作中,因为setThreadPriority 是一个基于“良好的”Linux值得优先级,可以设定的粒度更细,并且对线程的影响也更加明显。
- Android开发秘籍学习笔记(二)
- Android开发学习笔记秘籍(二十)
- Android开发秘籍学习笔记(一)
- Android开发秘籍学习笔记(三)
- Android开发秘籍学习笔记(四)
- Android开发秘籍学习笔记(五)
- Android开发秘籍学习笔记(六)
- Android开发秘籍学习笔记(七)
- Android开发秘籍学习笔记(八)
- Android开发秘籍学习笔记(九)
- Android开发秘籍学习笔记(十)
- Android开发秘籍学习笔记(十一)
- Android开发秘籍学习笔记(十二)
- Android开发秘籍学习笔记(十三)
- Android开发秘籍学习笔记(十四)
- Android开发笔记学习秘籍(十五)
- Android开发学习笔记秘籍(十六)
- Android开发学习笔记秘籍(十七)
- 第八周项目4--String类的构造
- Thinkphp下的RABC Role的显示和修改
- 求一个二进制数中1的个数
- Objective-C 给分类添加属性——关联对象
- Word Ladder
- Android开发秘籍学习笔记(二)
- Android中Handler的post方法的作用是什么
- 函数式编程很难,这正是你要学习它的原因
- oracle10g/11g 新特性九(数据库诊断)
- 日志功能--yii::trace()和yii::log()
- Dart on Android语言体验
- LeetCode Path Sum
- TableLayout中stretchColumns、shrinkColumns的用法
- 行编辑程序(基于链栈)