实现/创建线程的四种方式

方式1:通过Thread

Thread类本质上是实现了Runnable接口的实例,代表一个线程的实例。启动线程的唯一方法就是通过Thread类的start()实例方法,如果执行run()只是当做一个普通的方法执行【没有用新的线程执行】。start()方法是一个native方法,它将启动一个新的线程,并执行run()方法。

class MyThread extends Thread{
    @Override
    public void run() {
        super.run();
        System.out.println(Thread.currentThread().getName());
    }
}
public class Method1 {
    public static void main(String[] args) {
        MyThread myThread1 = new MyThread();

        System.out.println(Thread.currentThread().getName());

        myThread1.start();
    }
}

 

方式2:实现Runnable接口

import java.util.concurrent.*;

class MyThread implements Runnable{
    @Override
    public void run() {
        System.out.println(Thread.currentThread().getName() + " 线程创建方式1");
    }
}
public class Method2 {
    public static void main(String[] args) throws InterruptedException, ExecutionException {

        System.out.println(Thread.currentThread().getName());
        MyThread mythread1 = new MyThread();
        
//        ExecutorService es = Executors.newFixedThreadPool(2);
//        for (int i = 0; i < 2; i ++) {
//            Future f = es.submit(mythread1);
//            System.out.println(f);
//        }
//        es.shutdown();  

      
//        new Thread(mythread1).start();

//        FutureTask<?> ft = new FutureTask<Void>(mythread1, null);
//        new Thread(ft).start();
//        System.out.println(ft.get());
    }
}

 

方式3:实现Callable接口

 

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.*;

class MyThread implements Callable<String>{
    private String s;

    public MyThread(String s) {
        this.s = s;
    }

    @Override
    public String call() throws Exception {
        return s;
    }
}
public class Method3{
    public static void main(String[] args) throws ExecutionException, InterruptedException {
        /* 运行方式1 */
        // 创建一个线程对象
        MyThread myThread = new MyThread("启动线程方式1");
        // 启动线程,直接用Thread不行,需要借助FutureTask
        FutureTask<String> ft = new FutureTask<String>(myThread);
        // 由于FutureTask实现了Runnable所以可以传给Thread,但是这样运行是没有结果的。
        new Thread(ft).start(); 
        // 通过FutureTask可以获得执行的结果
        System.out.println(ft.get());
        
        
        
        /* 运行方式2【线程池执行】 */
        // 创建一个线程池--ExecutorService中所有submit方法都将返回一个Future。
        ExecutorService pool = Executors.newFixedThreadPool(10);

        // 创建多个有返回值的任务
        List<Future> list = new ArrayList<Future>();
        for (int i = 0; i < 10; i ++){
            Callable c = new MyThread(i + "");
            // 执行任务[线程池执行]    并获得Future对象
            Future f = pool.submit(c);
            list.add(f);
        }

        // 关闭线程池
        pool.shutdown();

        // 获取所有并发任务的运行结果
        for (Future f:list){
            // 从Future对象上获取任务的返回值,并输出到控制台
            System.out.println("result: " + f.get().toString());
        }
    }
}

 FutureTask解析:

// 由于FutureTask实现了Runnable,因此可以将它提交给Executor来执行,或者直接通过Thread调用它的run()方法
public class FutureTask<V> implements RunnableFuture<V>
public interface RunnableFuture<V> extends Runnable, Future<V> {
    void run();
}

构造函数: 

// 两个构造函数--可以传入callable实现接口
public FutureTask(Callable<V> callable) {
        if (callable == null)
            throw new NullPointerException();
        this.callable = callable;
        this.state = NEW;       // ensure visibility of callable
}

/**
 * @param runnable the runnable task
 * @param result the result to return on successful completion. If
 * you don't need a particular result, consider using
 * constructions of the form:
 * {@code Future<?> f = new FutureTask<Void>(runnable, null)}
 * @throws NullPointerException if the runnable is null
 */

// 可以传入Runnable实现接口,但是new FutureTask<Void>(runnable, null)}
public FutureTask(Runnable runnable, V result) {
        this.callable = Executors.callable(runnable, result); // 依然使用的是callable
        this.state = NEW;       // ensure visibility of callable
}

FutureTask实现了RunnableFuture的run()方法:

// 调用Thread.start()时,JVM会调用run()方法
public void run() {
        if (state != NEW ||
            !UNSAFE.compareAndSwapObject(this, runnerOffset,
                                         null, Thread.currentThread()))
            return;
        try {
            Callable<V> c = callable;
            if (c != null && state == NEW) {
                V result;
                boolean ran;
                try {
                    result = c.call();  // 调用了call方法
                    ran = true;
                } catch (Throwable ex) {
                    result = null;
                    ran = false;
                    setException(ex);
                }
                if (ran)
                    set(result);  // ---调用set方法
            }
        } finally {
            runner = null;
            int s = state;
            if (s >= INTERRUPTING)
                handlePossibleCancellationInterrupt(s);
        }
    }

protected void set(V v) {
        // state从NEW变为了COMPLETING
        if (UNSAFE.compareAndSwapInt(this, stateOffset, NEW, COMPLETING)) {
            outcome = v; // 将返回值v放入到outcome中
            // state从COMPLETING变为了NORMAL
            UNSAFE.putOrderedInt(this, stateOffset, NORMAL); // final state
            finishCompletion();
        }
    }
public V get() throws InterruptedException, ExecutionException {
        int s = state;
        if (s <= COMPLETING) // 如果还没有完成则阻塞
            s = awaitDone(false, 0L);
        return report(s);
    }
private V report(int s) throws ExecutionException {
        Object x = outcome;
        if (s == NORMAL) // 如果完成--状态变成了NORMAL
            return (V)x;  // 返回结果
        if (s >= CANCELLED)
            throw new CancellationException();
        throw new ExecutionException((Throwable)x);
    }

方式4:基于线程池的方法

package chapter6;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class Method4 {
    public static void main(String[] args) {
        int i = 0;
        ExecutorService threadPool = Executors.newFixedThreadPool(10);

        while(i ++ < 10){
            threadPool.execute(new Runnable() { // 提交多个线程任务,并执行
                @Override
                public void run() {
                    System.out.println(Thread.currentThread().getName() + " is running..");
                    try{
                        Thread.sleep(3000);
                    } catch (InterruptedException e){
                        e.printStackTrace();
                    }
                }
            });
        }

        threadPool.shutdown();
    }
}

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值