高并发编程(二)创建线程的12种姿势
JDK1.5创建线程的6种姿势
姿势1、2:
继承Thread并重写run()方法,Thread类中的start方法会去调用系统的方法执行相应的线程。实际上Thread也是实现了Runable接口的,从该类的文档中我们能找到。
public class createThread extends Thread {
@Override
public void run() {
System.out.println("Thread init....");
}
}
Thread t1=new Thread(new Runnable() {
@Override
public void run() {
System.out.println("Thread1 init....");
}
});
对比:姿势1和姿势2无任何本质区别,姿势1是用继承类实现,姿势2是用内部类实现。
姿势3、4
实现Runable接口,并重写run()方法,启动线程必须要使用Thread类的start()方法
public class createRunnable implements Runnable {
@Override
public void run() {
System.out.println("Runnable init....");
}
}
Runnable r1=new Runnable() {
@Override
public void run() {
System.out.println("Runnable1 init....");
}
};
对比:姿势3、4的区别和1、2区别一样,姿势1、2和姿势3、4的区别在于一个是通过继承实现,一个是通过接口实现。接口实现相较于继承类实现方式更加灵活,具体优势参见单继承多实现。
姿势5、6
实现Callable接口
public class createCallable implements Callable<String> {
@Override
public String call() throws Exception {
System.out.println("Callable init....");
return "ok";
}
}
Callable<String> c1=new Callable<String>() {
@Override
public String call() throws Exception {
System.out.println("Callable1 init....");
return "ok";
}
};
对比:姿势5、6的区别和3、4区别一样,姿势5、6和姿势3、4的区别在于实现callable接口的线程可以具有返回值。
Jdk1.8创建线程的6种姿势
姿势7
函数式编程实现Thread创建线程
Thread t2=new Thread(()->{
System.out.println("Thread2 init....");
});
姿势8
函数式编程实现Runnable创建线程
Runnable r2=()->{System.out.println("Runnable2 init....");};
姿势9
函数式编程实现Callable创建线程
Callable<String> c2= (()->{
System.out.println("Callable2 init....");
return "ok";
});
姿势10、11
CompletableFuture创建线程
CompletableFuture<Void> cf=CompletableFuture.runAsync(()->{
System.out.println("CompletableFuture init....");
});
CompletableFuture<String> cf1=CompletableFuture.supplyAsync(()->{
System.out.println("CompletableFuture init....");
return "ok";
});
姿势12
Java1.8集合方式创建线程
List<String> lists=Arrays.asList("a","b","c");
lists.parallelStream().forEach((n)->{System.out.println(n);});
打印结果:
b
c
a
你会发现结果并未按照塞入时的顺序,这是因为Stream实现了并行流进行输出,即实现了多个线程处理打印。