【问题标题】:Scenario where extending thread is preferred than implement Runnable? [duplicate]扩展线程比实现 Runnable 更可取的场景? [复制]
【发布时间】:2014-04-23 20:58:29
【问题描述】:
作为一个初学者,我正在阅读关于在 Java 中实现多线程的 2 种方法。
我在 SO 和许多其他线程上阅读了这个 thread。
据说
"prefer runnable" ,仅当您专门针对线程的行为时才扩展线程。
谁能通过提供一小段帮助我理解这一行的 sn-p 来解释专门化 Thread 行为的含义。
【问题讨论】:
标签:
java
multithreading
runnable
【解决方案1】:
选择 Runnable 实现而不是 Thread 扩展有几个原因:
扩展 Thread 的一个合法用例示例是,当您需要设计一个具有自定义属性(例如:缓存资源)的 Thread 类时,该类属于 CachedThreadPool
【解决方案2】:
Java 不支持多重继承,这意味着你只能在 Java 中扩展一个类,所以一旦你扩展了 Thread 类,你就失去了机会,并且不能在 Java 中扩展或继承另一个类,所以这个类是专门为 Thread仅限。
通过extending Thread,您的每个线程都有一个与之关联的唯一对象,而实现Runnable,许多线程可以共享同一个可运行实例。
扩展类通常意味着添加新功能、修改或改进行为。如果我们不对Thread 进行任何修改,那么请改用Runnable 接口。
线程类有一些行为由 JDK 开发人员决定,当您想对其进行一些修改时,您可以使用 Thread 类扩展您的类并进行修改。
【解决方案3】:
因为java不支持多继承。
如果你有一个名为 Person 的类。
class Person{
String name;
int age;
}
然后你想创建一个扩展 Person 的类 Man
class Man extends Person{
}
现在您已经使用 extends 关键字声明 Man 是一个人。那么如果你想让Man像线程一样执行,你不能再扩展Thread,因为Java不支持多继承。所以只需使用Runnable接口,它可以与其他接口一起实现。
class Man extends Person implements Runnable{
public void run()[
}
}
编辑:
“仅当您专门研究线程的行为时才扩展线程”意味着您的类只是一个没有其他功能的线程,因为当您的类包含其他功能时,您需要扩展其他超类而不是 Thread 类。我之前提到过,java不支持多继承,所以只有在你专门研究线程的行为时才扩展线程。
【解决方案4】:
您应该像扩展其他库类一样扩展Thread。
以List 为例,更具体地说是ArrayList,您可以在其上添加额外的行为,例如在添加某个谓词失败时拒绝某个值。
然后你可以称之为PredicatedArrayList。
是否要在此处扩展 ArrayList 仍然是一个争论,但这个争论不适合这个问题。
因此,扩展线程的一个示例是在特定时间后杀死自己的线程。然后你会得到SuicidingThread extends Thread,它可能需要一个构造函数来花时间。
这甚至强化了您应该将实际任务放在Runnable 中的论点。
比如Runnable somethingRunnable = new SomeClass();,其中SomeClass implements Runnable。
现在您可以执行以下任一操作:
Thread someThread = new Thread(somethingRunnable);
Thread someThread = new SuicidingThread(somethingRunnable, 5, TimeUnit.DAYS);
所以这将是一个扩展线程的用例。
【解决方案5】:
专业化意味着,扩展现有线程类的功能。根据应用程序的要求,它可以是任何东西。我在下面提到的那个在逻辑上可能不正确。
public class MyThread extends Thread{
@Override
public void interrupt() {
if(thread has started some operation on database){
//roll back transaction
}
super.interrupt();
}
}
在这里,在中断线程之前,我们可以检查当前是否有任何数据库操作正在运行并回滚。虽然它可以从中断的 catch 块中完成,但如果您在应用程序的不同位置创建大量此线程的实例,则从扩展类处理它会减少行数。这只是一个例子,没有人会这样使用它。 :)