package com.neuedu;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.FutureTask;
/*
*/
//1.创建一个实现callable的实现类
class MTchread implements Callable<Integer> {
//2.实现call方法,将此线程需要执行的操作声明在call()中
@Override
public Integer call() throws Exception {
int sum = 0;
for (int i = 1; i < 100 ; i++) {
if (i % 2 ==0){
System.out.println(i);
sum += i;
}
}
return sum;
}
}
public class First {
public static void main(String[] args) {
// 3.创建callable的接口实现类的对象
MTchread num = new MTchread();
//4.将此callable的接口实现类的对象作为接口传递到FutureTask构造器中,创建futureTask对象
FutureTask<Integer> task = new FutureTask<Integer>(num);
//5.将Futuretask的对象作为参数传递到Thread类的构造器中,创建Thread对象,并调用start()方法;
new Thread(task).start();
try {
//获取Callable中call方法的返回值
//get()返回值即为futuretask构造器参数callable实现类重写的call()方法
Integer sum = task.get();
System.out.println("总和为:" + sum);
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
}
}
package java2;
import java.util.concurrent.Executor;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.ThreadPoolExecutor;
class NumberThread implements Runnable{
@Override
public void run() {
for (int i = 0; i <= 100 ; i++) {
if (i % 2 ==0){
System.out.println(Thread.currentThread().getName()+ ":" + i);
}
}
}
}
class NumberThread1 implements Runnable{
@Override
public void run() {
for (int i = 0; i <= 100 ; i++) {
if (i % 2 !=0){
System.out.println(Thread.currentThread().getName()+ ":" + i);
}
}
}
}
public class ThreadPool {
public static void main(String[] args) {
//1. 提供制定线程数量的线程池
ExecutorService Service = Executors.newFixedThreadPool(10);
ThreadPoolExecutor Service1 = (ThreadPoolExecutor) Service;
//设置线程池的属性 体现线程的管理
Service1.setCorePoolSize(15);
System.out.println(Service.getClass());
//2. 执行制定的线程的操作,需要提供实现Runnable接口或Callable接口实现类的对象
Service.execute(new NumberThread());//适合使用于Runnable
Service.execute(new NumberThread1());
//Service.submit();//适合使用于Callable
//3.关闭连接池
Service.shutdown();
}
}
面试题:如何理解实现Callable接口的方式创建多线程比实现Runnable接口创建多线程的方式强大?
- call()方法是可以有返回值的;
- call()方法可以抛出异常,被外面的操作捕获,获取异常的信息;
- Callable是支持泛型的;
泛型。即通过参数化类型来实现在同一份代码上操作多种数据类型。泛型(Genericity)的字面意思是指具有在多种数据类型上皆可操作的含意,与模板有些相似。优点:泛型类和泛型方法同时具备可重用性、类型安全和效率,这是非泛型类和非泛型方法无法具备的。泛型通常用与集合以及作用于集合的方法一起使用。
面试题:创建多线程有几种方式:继承Thread类;实现Runnable方法;实现Callable方法;使用线程池;