Java 学习:多线程

线程

Java 给多线程编程提供了内置的支持。 一条线程指的是进程中一个单一顺序的控制流,一个进程中可以并发多个线程,每条线程并行执行不同的任务。


创建线程:

Java 提供了三种创建线程的方法:

  1. 通过实现 Runnable 接口;
  2. 通过继承 Thread 类本身;
  3. 通过 Callable 和 Future 创建线程。

通过实现 Runnable 接口创建线程:


public class Demo{
    public static void main(String[] args) {
        //创建实现了Runable接口的任务对象
        Test1 t = new Test1();
        //创建线程将任务对象作为Thread的构造参数交给线程
        Thread thread = new Thread(t);
        //调用线程的start方法开启线程,JVM会自动调用任务对象的run方法执行任务
        thread.start();

    }

}

/**
 *创建线程1 通过实现 Runnable 接口;
 */
class Test1 implements Runnable{

    /**
     * 实现Runnable接口的run方法
     */
    @Override
    public void run() {
        //这里是线程要执行的任务
        System.out.println("任务执行...");
    }
}


通过继承 Thread 类本身创建线程:

public class Demo {
    public static void main(String[] args) {
        //创建继承了Thread类的t对象
        Test2 t = new Test2();
        //调用start方法开启线程,JVM会自动调用run方法执行任务
        t.start();

    }

}

/**
 * 创建线程2 通过继承 Thread 类
 */
class Test2 extends Thread{
    /**
     * 重写Thread类的run方法
     */
    @Override
    public void run() {
        //这里是线程要执行的任务
        System.out.println("任务执行...");
    }
}


通过 Callable 和 Future 创建线程:

public class Demo {
    public static void main(String[] args) {
        //创建实现了Callable接口的对象
        Test3 t = new Test3();
        //创建FutureTask对象, 将实现了Callable接口的对象作为构造参数传给FutureTask
        FutureTask futureTask = new FutureTask(t);

        //创建Thread对象,将创建好的FutureTask对象作为构造参数传给Thread,并调用start方法开启线程
        new Thread(futureTask).start();

        try {
            //可以通过futureTask对象的get方法获取线程执行的返回值
            Object o = futureTask.get();
            System.out.println("返回的对象=》 " + o);
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        }

    }

}

/**
 * 创建线程3 通过实现 Callable接口
 */
class Test3 implements Callable {
    /**
     * 实现Callable接口的call方法
     */
    @Override
    public Object call() throws Exception {
        //这里是线程要执行的任务
        System.out.println("任务执行...");

        //返回自己要返回的对象
        return new Object();
    }
}


线程的相关API:

  1. Thread.currentThread().getName() //Thread的静态方法,获取当前线程的名字

  2. Thread.currentThread() //Thread静态方法,返回执行当前代码的线程

  3. Thread.yield() //Thread的静态方法,主动释放当前线程的执行权

  4. Thread.sleep(long millitime) //Thread的静态方法,让当前线程休眠指定时间

  5. void start() //启动当前线程

  6. String getName() //获取线程的名字

  7. void setName() //设置线程的名字

  8. void join() //在线程中插入执行另一个线程,该线程被阻塞,直到插入执行的线程完全执行完毕以后,该线程才继续执行下去

  9. void isAlive() //判断线程是否存活

  10. int getPriority() //获取线程的优先级别

  11. void setPriority(int newPriority) //设置线程的优先级为newPriority

  12. void void setDaemon(boolean on) //将线程设置是否为守护线程,参数true守护,false不守护

  13. void interrupt() //中断线程


线程的分类:

java中的线程分为两类:
守护线程:如垃圾回收,异常处理都是守护类型的线程
户用线程:如主线程,或是程序员创建的线程
注意:当JVM中用户线程全部执行完,不管守护线程是否还有未执行完的,程序都将结束,JVM将退出。


线程的调度:

调度策略:
时间片:线程的调度采用时间片轮转的方式
抢占式:线程优先级高的会抢占CPU

Java的调度方法:

  1. 对相同优先级的线程组成先进先出队列,使用时间片策略
  2. 对优先级高的线程,使用优先调度的抢占式策略

注意:优先级高的线程要抢占优先级低的线程的CPU的执行权。但仅从概率上来说的,优先级高的更有可能被执行,并不意味着只有优先级高的执行完以后才去执行优先级低的。


线程的优先级:

在Thread类内定义了MIN_PRIORITY=1、NORM_PRIORITY=5、MAX_PRIORITY=10三个级别,一半线程优先级默认是NORM_PRIORITY


并发并行:

并发:一个CPU(采用时间片)同时执行多个任务。
并行:多个CPU同时执行多个任务。





posted @ 2021-09-26 15:06  typeof(光)  阅读(24)  评论(0编辑  收藏  举报