IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 移动开发 -> JAVA多线程 -> 正文阅读

[移动开发]JAVA多线程

JAVA多线程

线程的创建的方式:

一:继承Thread类

由于JAVA里一个子类只能继承一个父类,所以继承Thread后的线程类无法拥有更多的功能,是最简单的创建线程的方法,学习阶段尝试线程感觉很方便

public class ThreadDemo1 {
    public static void main(String[] args) {

        //3.new一个新线程对象
        Thread t = new MyThread();
        //4.调用start方法启动线程(实际执行的还是run方法)
        t.start();
        for (int i = 0; i < 10; i++) {
            System.out.println("11111111111");
        }
    }
}


/**
    1.定义一个线程类继承Thread类
 */
class MyThread extends Thread {
    /**
        2.重写run方法,里面是定义线程以后要干啥
     */
    @Override
    public void run() {
        for (int i = 0; i < 10; i++) {
            System.out.println("============");
        }

    }
}

二:实现Runnable接口

定义Runnable接口的实现类,只是实现了接口,可以继续继承类和实现接口,扩展性强,Runnable的实现类创建的对象只是任务对象,需要交给Thread进行包装,Thread类才是真正的线程对象

public class ThreadDemo2 {
    public static void main(String[] args) {
        //3.创建一个任务对象
        Runnable target = new MyRunnable();
        //4.把任务对象交给Thread处理
        Thread t = new Thread(target);
        //5.启动线程
        t.start();

        //主线程随便写点东西
        for (int i = 0; i < 10; i++) {
            System.out.println("主线程执行输出:" + i);
        }
    }
}

/**
 * 1.定义一个线程任务类,实现Runnable接口
 */
class MyRunnable implements Runnable {

    /*
        2.重写run方法,定义线程的执行的任务
     */
    @Override
    public void run() {
        for (int i = 0; i < 10; i++) {
            System.out.println("子线程执行输出:" + i);
        }
    }
}

//lambda表达式简化
/*

        new Thread(new Runnable() {
            @Override
            public void run() {
                for (int i = 0; i < 10; i++) {
                    System.out.println("子线程2执行输出:" + i);
                }
            }
        }).start();


        new Thread(() -> {
            for (int i = 0; i < 10; i++) {
                System.out.println("子线程3执行输出:" + i);
            }

        }).start();
        */

三:实现Callable接口,用FutureTask创建新线程

将Callable的实现类包装到FutureTask里,再将FutureTask类作为任务对象包装到Thread类,可以调用FutureTask类的get()方法得到线程执行的返回值

(泛型里面是子线程执行结束后的返回值)

public class ThreadDemo3 {
    public static void main(String[] args) {
        //3.创建Callable 任务对象
        Callable<String> call = new MyCallable(100);

        //4.把Callable任务对象 交给FutureTask对象
        //FutureTask对象的作用1:是Runnable的对象(实现了Runnable接口),可以交给Thread了
        //FutureTask对象的作用2:可以在线程执行完毕之后通过调用其get方法得到线程执行完毕后的结果

        FutureTask<String>f1 = new FutureTask<>(call);
        //5.交给线程处理
        Thread t1  = new Thread(f1);
        //6.启动线程
        t1.start();

        Callable<String> call2 = new MyCallable(200);
        FutureTask<String>f2 = new FutureTask<>(call2);
        Thread t2  = new Thread(f2);
        t2.start();
        /**
        get方法是FutureTask的方法
         */
        try {
            String rs = f1.get();
            System.out.println("线程1"+rs);
        } catch (Exception e) {
            e.printStackTrace();
        }

        try {
            String rs2 = f2.get();
            System.out.println("线程2"+rs2);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}


/**
 * 1.定义一个任务类  实现Callable接口    应该声明线程任务执行完毕后的结果的数据类型
 */
class MyCallable implements Callable<String>{
    private int n;

    public MyCallable(int n) {
        this.n = n;
    }

    public MyCallable() {
    }

    /*
    重写call方法(任务方法)
     */
    @Override
    public String call() throws Exception {
        int sum = 0;
        for (int i = 1; i <=n ; i++) {
            sum+=i;
        }
        return "执行的结果是:"+sum;
    }
}

利用线程池创建新线程

一:Runnable的实现类在线程池里用execute执行

public class ThreadPoolDemo1 {
    public static void main(String[] args) {
        /*
        public ThreadPoolExecutor(int corePoolSize,  指定线程池的线程数量(核心线程)
                              int maximumPoolSize,  指定线程池可支持的最大线程数
                              long keepAliveTime,  指定临时线程的最大存活时间
                              TimeUnit unit,  指定存活世间的单位(秒、分、时、天)
                              BlockingQueue<Runnable> workQueue,  指定任务队列 workQueue
                              ThreadFactory threadFactory,  指定用哪个线程工厂创建线程 :threadFactory
                              RejectedExecutionHandler handler  指定线程忙,任务满的时候,新任务来了的处理方法)
         */
        //1.创建线程池对象
        ExecutorService pool = new ThreadPoolExecutor(3, 5, 6, TimeUnit.SECONDS,
                new ArrayBlockingQueue<>(5), Executors.defaultThreadFactory(),
                new ThreadPoolExecutor.AbortPolicy());//丢弃任务并抛出异常(听说一般用这个)
        //ThreadPoolExecutor.CallerRunsPolicy  由主线程负责调用任务的run方法从而绕过线程池直接执行
        //ThreadPoolExecutor.DiscardPolicy   丢弃任务,但是不抛出异常
        //ThreadPoolExecutor.DiscardOldestPolicy   抛弃队列中等待最久的任务,然后把当前任务加入队列中

        //2.给任务线程池处理
        Runnable target = new MyRunnable();
        pool.execute(target);
        pool.execute(target);
        pool.execute(target);
        pool.execute(target);
        pool.execute(target);
        pool.execute(target);
        pool.execute(target);
        pool.execute(target);

    }
}

二:Callable的实现类用submit执行

public class ThreadPoolDemo2 {
    public static void main(String[] args) throws Exception {
        /*
        public ThreadPoolExecutor(int corePoolSize,  指定线程池的线程数量(核心线程)
                              int maximumPoolSize,  指定线程池可支持的最大线程数
                              long keepAliveTime,  指定临时线程的最大存活时间
                              TimeUnit unit,  指定存活世间的单位(秒、分、时、天)
                              BlockingQueue<Runnable> workQueue,  指定任务队列 workQueue
                              ThreadFactory threadFactory,  指定用哪个线程工厂创建线程 :threadFactory
                              RejectedExecutionHandler handler  指定线程忙,任务满的时候,新任务来了的处理方法)
         */
        //1.创建线程池对象
        ExecutorService pool = new ThreadPoolExecutor(3, 5, 6, TimeUnit.SECONDS,
                new ArrayBlockingQueue<>(5), Executors.defaultThreadFactory(),
                new ThreadPoolExecutor.AbortPolicy());//丢弃任务并抛出异常(听说一般用这个)
        //ThreadPoolExecutor.CallerRunsPolicy  由主线程负责调用任务的run方法从而绕过线程池直接执行
        //ThreadPoolExecutor.DiscardPolicy   丢弃任务,但是不抛出异常
        //ThreadPoolExecutor.DiscardOldestPolicy   抛弃队列中等待最久的任务,然后把当前任务加入队列中

        //2.给任务线程池处理
        Future<String> f1 = pool.submit(new MyCallable(100));
        Future<String> f2 = pool.submit(new MyCallable(200));
        Future<String> f3 = pool.submit(new MyCallable(300));
        Future<String> f4 = pool.submit(new MyCallable(400));
        Future<String> f5 = pool.submit(new MyCallable(500));

        System.out.println(f1.get());
        System.out.println(f2.get());
        System.out.println(f3.get());
        System.out.println(f4.get());
        System.out.println(f5.get());
    }
}

三:使用Executors的工具方法直接得到一个线程池对象

public class ThreadPoolDemo3 {
    public static void main(String[] args) {
        //1.创建固定线程数据的线程池
        //允许请求的任务队列长度是Integer.MAX_VALUE
        ExecutorService pool = Executors.newFixedThreadPool(3);//创建固定线程数量的线程池,有线程异常,就补充一个新的
        //ExecutorService pool = Executors.newSingleThreadExecutor();// z

        //创建线程数量最大上限是Integer.MAX_VALUE
        //ExecutorService pool = Executors.newCachedThreadPool();
        //ExecutorService pool = Executors.newScheduledThreadPool();

        pool.execute(new MyRunnable());
    }
}

Executors的工具方法底层还是采用ThreadPoolExecutor方法创建线程池

线程安全

使用synchronized关键字给线程加锁,一般使用对应的对象作为锁

静态方法可以使用类名.class作为锁

线程通信

使用notify唤醒等待的线程

使用wait将当前线程休眠

public class Phone {

    //实现线程间通信,默认认为手机当前处于等待来电提醒
    private boolean flag = false;

    public void run() {
        //a.负责来电提醒的线程
        new Thread(new Runnable() {
            @Override
            public void run() {
                while (true) {
                    synchronized (Phone.this) {
                        if (!flag) {
                            //代表要来电话提醒了

                            try {
                                System.out.println("有新电话呼入,可以接听");
                                flag = true;
                                Thread.sleep(1000);
                                Phone.this.notify();
                                Phone.this.wait();
                            } catch (Exception e) {
                                e.printStackTrace();
                            }
                        }
                    }
                }
            }
        }).start();
        //b.接电话线程,正式接听

        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    //不断地接听电话
                    while (true) {
                        synchronized (Phone.this) {
                            if (flag) {
                                //可以接听电话了
                                System.out.println("电话已接通,这两人正在聊天");
                                Thread.sleep(1000);
                                flag = false;
                                //唤醒别人,等待自己
                                Phone.this.notify();
                                Phone.this.wait();
                            } else {
                                Phone.this.notify();
                                Phone.this.wait();
                            }
                        }
                    }


                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }).start();
    }

    public static void main(String[] args) {
        //1.创建一部手机对象
        Phone phone = new Phone();
        phone.run();
    }
}
  移动开发 最新文章
Vue3装载axios和element-ui
android adb cmd
【xcode】Xcode常用快捷键与技巧
Android开发中的线程池使用
Java 和 Android 的 Base64
Android 测试文字编码格式
微信小程序支付
安卓权限记录
知乎之自动养号
【Android Jetpack】DataStore
上一篇文章      下一篇文章      查看所有文章
加:2022-04-15 00:12:54  更:2022-04-15 00:16:02 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 21:08:00-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码