• 知识点

“implements Runnable” 和“extends Thread”的不同

  • 具体分析

最近在学习Android中的Handler消息传递机制时,创建新线程有两种方式:一种是实现Runnable接口(implements Runnable)而另一种则是继承Thread类(extends Thread)。而这两种方式有什么异同呢?带着这个疑问,Google了一些资料出来,本着分享给大家同时也方便自己查阅复习,写一篇文章来记录它。

首先看看这两种方式都是怎样的?

 public class ThreadA implements Runnable {
public void run() {
//Code
}
}
//调用 "new Thread(threadA).start()" 来开启线程 public class ThreadB extends Thread {
public ThreadB() {
super("ThreadB");
}
public void run() {
//Code
}
}
//调用 "threadB.start()" 来开启线程

两种方法实现同样的工作但是它们之间还是有一些区别的。

它们之间的不同是:

1.我们都知道,Java是单继承机制,不允许同时继承多个类。因此,当你继承Thread类(extends Thread)后,你就不能再继承其他类了。而你实现Runnable接口就不一样了,你可以继承其他类了。

2.当你继承Thread类时,你的每一个Thread对象创造不同的对象然后关联它们。

而继承Runnable接口则不一样,多个线程共享一个对象。

用一个例子来帮助我们理解:

 class ImplementsRunnable implements Runnable {

      private int counter = 0;

     public void run() {
   counter++;
   System.out.println("ImplementsRunnable : Counter : " + counter);
}
} class ExtendsThread extends Thread {   private int counter = 0; public void run() {
   counter++;
  System.out.println("ExtendsThread : Counter : " + counter);
}
} public class ThreadVsRunnable { public static void main(String args[]) throws Exception {
//多线程共享一个对象
  ImplementsRunnable rc = new ImplementsRunnable();
   Thread t1 = new Thread(rc);
   t1.start();
  Thread.sleep(1000); // 在开启下个线程前先等待1秒
   Thread t2 = new Thread(rc);
   t2.start();
  Thread.sleep(1000); // 在开启下个线程前先等待1秒
   Thread t3 = new Thread(rc);
   t3.start(); //为每一个线程创造新的实例
   ExtendsThread tc1 = new ExtendsThread();
   tc1.start();
   Thread.sleep(1000); // 在开启下个线程前先等待1秒
   ExtendsThread tc2 = new ExtendsThread();
  tc2.start();
  Thread.sleep(1000); // 在开启下个线程前先等待1秒
   ExtendsThread tc3 = new ExtendsThread();
   tc3.start();
}
}

运行结果:

aaarticlea/png;base64,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" alt="" />

从运行的结果,我们可以看出。实现Runnable接口,只创建了一个类的实例,而且被多个线程共享了。因此Counter递增。而继承Thread类,你必须为每一个线程创建不同的实例。因此每个类的实例分配了不同的内存空间,每一个有不同的Counter,它们的值相同。这意味着没有增加因为没有一个对象的引用是相同的。

那什么时候用Runnable接口呢?

当你想要在一组线程中访问相同的资源时,使用Runnable接口。在这种情况下要避免使用Thread类,因为多对象的创建会占用更多的内存,会导致大的性能花费。

PS:Thread类内部实现了Runnable接口

最后,哪种方式最好用呢?

显而易见,当然是实现Runnable接口更好。

Java 中的“implements Runnable” 和“extends Thread”的更多相关文章

  1. Java 中的“implements Runnable” 和“extends Thread”(转)

    知识点 “implements Runnable” 和“extends Thread”的不同 具体分析 最近在学习Android中的Handler消息传递机制时,创建新线程有两种方式:一种是实现Run ...

  2. Java 多线程实现接口Runnable和继承Thread区别(转)

    Java 多线程实现接口Runnable和继承Thread区别 Java中有两种实现多线程的方式.一是直接继承Thread类,二是实现Runnable接口.那么这两种实现多线程的方式在应用上有什么区别 ...

  3. extends:类似于java中的继承特征,extends="struts-default"

    extends:类似于java中的继承特征,extends="struts-default"就是继承struts-default.xml,它里面定义了许多跳转类型.拦截器等一些常用 ...

  4. java 中Handler 和Runnable 的使用 异步发送消息 转

    public class MainActivity extends Activity { TextView text1, text2; Button button; Thread th; @Overr ...

  5. 在java中怎样实现多线程?线程的4种状态

    一.在java中怎样实现多线程? extends Thread implement Runnable 方法一:继承 Thread 类,覆盖方法 run(),我们在创建的 Thread 类的子类中重写 ...

  6. Java 使用线程方式Thread和Runnable,以及Thread与Runnable的区别

    一. java中实现线程的方式有Thread和Runnable Thread: public class Thread1 extends Thread{ @Override public void r ...

  7. extend Thread 和 implements Runnable

    原文地址:extend Thread 和 implements Runnable 一个Thread的实例只能产生一个线程 or: 同一实例(Runnable实例)的多个线程 look: public ...

  8. Java多线程系列--“基础篇”03之 Thread中start()和run()的区别

    概要 Thread类包含start()和run()方法,它们的区别是什么?本章将对此作出解答.本章内容包括:start() 和 run()的区别说明start() 和 run()的区别示例start( ...

  9. java 多线程实现四种方式解析Thread,Runnable,Callable,ServiceExcutor,Synchronized ,ReentrantLock

    1.Thread实现: import java.util.Date; import java.text.SimpleDateFormat; public class MyThread extends ...

随机推荐

  1. 10.29训练赛第一场B题

    题目大意:有n个队伍之间比赛,每两个队伍之间都有一场比赛,因此一共有n(n-1) / 2场比赛,但是这里丢失了一场比赛的记录,现在让你通过n(n-1) /2 -1场仍然存在的比赛记录来判断丢失的那条比 ...

  2. 第8月第22天 python scrapy

    1. cd /Users/temp/Downloads/LagouSpider-master ls ls ls lagou/settings.py cat lagou/settings.py ls p ...

  3. NOI2001 方程的解数(双向搜索)

    solution 一道非常经典的双向搜索题目,先将前3个未知数枚举一遍得到方程的前半部分所有可能的值,取负存入第一个队列中再将后3个未知数枚举一遍,存入第二个队列中.这样我们只要匹配两个队列中相同的元 ...

  4. golang的sort研究

    年前没钱,等发工资.就这么在公司耗着不敢回家,无聊看了下golang的sort源码 type Interface interface { // Len is the number of element ...

  5. 源码安装svn 1.8.9

    2014年5月25日 12:26:14 需要文件: svn apr apr-util sqlite3 serf svn : http://subversion.apache.org/download/ ...

  6. 解决依赖的moduleBuildConfig.DEBUG总是未false的问题

    Android 开发中一般会通过 BuildConfig.DEBUG 判断是否是 Debug 模式,从而做一些在 Debug 模式才开启的特殊操作,比如打印日志.这样好处是不用在发布前去主动修改,因为 ...

  7. WebApi帮助类

    public class HttpClientBase { /// <summary> /// HttpClient实现Post请求 /// </summary> protec ...

  8. 微信小程序Http高级封装 es6 promise

    公司突然要开放微信小程序,持续蒙蔽的我还不知道小程序是个什么玩意. 于是上网查了一下,就开始着手开发..... 首先开发客户端的东西,都有个共同点,那就是  数据请求! 看了下小程序的请求方式大概和a ...

  9. scanf 输入加逗号(或者不加逗号)出现的异常及解决方案

    我们在写 C 语言代码通常 scanf 的格式控制部分都有两种习惯,加逗号与不加逗号,而这两种情况都会因为我们的不同输入习惯产生一定的问题,这里给出另一种方法. 1.不加逗号 #include< ...

  10. shiro中async-supported报错 cvc-complex-type.2.4.a: Invalid content was found starting with element 'async-supported'. One of '{"http://java.sun.com/xml/ns/ javaee":init-param}' is expected.

    最近都在研究shiro这个框架,今天实施了一下,就报了如下错误: cvc-complex-type.2.4.a: Invalid content was found starting with ele ...