zoukankan      html  css  js  c++  java
  • JAVA之多线程

    一、多线程介绍

      1、进程:进程指正在运行的程序。确切的来说,当一个程序进入内存运行,即变成一个进程,进程是处于运行过程中的程序,并且具有一定独立功能。

      2、线程:线程是进程中的一个执行单元,负责当前进程中程序的执行,一个进程中至少有一个线程。一个进程中是可以有多个线程的,这个应用程序也可以称之为多线程程序。

      简而言之:一个程序运行后至少有一个进程,一个进程中可以包含多个线程

      3、程序运行原理:

          分时调度

          所有线程轮流使用 CPU 的使用权,平均分配每个线程占用 CPU 的时间。

          抢占式调度

          优先让优先级高的线程使用 CPU,如果线程的优先级相同,那么会随机选择一个(线程随机性),Java使用的为抢占式调度。

      4、主线程:jvm启动后,必然有一个执行路径(线程)从main方法开始的,一直执行到main方法结束,这个线程在java中称之为主线程。

            当程序的主线程执行时,如果遇到了循环而导致程序在指定位置停留时间过长,则无法马上执行下面的程序,需要等待循环结束后能够执行。

    二、创建线程的方式

      1、继承Thread类

        1)继承Thread类:因为Thread类用来描述线程,具备线程应该有功能。那为什么不直接创建Thread类的对象呢?如下代码:

    Thread t1 = new Thread();
    t1.start();//这样做没有错,但是该start调用的是Thread类中的run方法,而这个run方法没有做什么事情,更重要的是这个run方法中并没有定义我们需要让线程执行的代码。

        2)创建线程的目的是什么?

        是为了建立程序单独的执行路径,让多部分代码实现同时执行。也就是说线程创建并执行需要给定线程要执行的任务。

        对于之前所讲的主线程,它的任务定义在main函数中。自定义线程需要执行的任务都定义在run方法中。

        Thread类run方法中的任务并不是我们所需要的,只有重写这个run方法。既然Thread类已经定义了线程任务的编写位置(run方法),那么只要在编写位置(run方法)中定义任务代码即可。所以进行了重写run方法动作。

        3)多线程内存图解

       获取线程名称:

       Thread.currentThread()获取当前线程对象

       Thread.currentThread().getName();获取当前线程对象的名称

    class MyThread extends Thread {  //继承Thread
        MyThread(String name){
            super(name);
        }
        //复写其中的run方法
        public void run(){
            for (int i=1;i<=20 ;i++ ){
                System.out.println(Thread.currentThread().getName()+",i="+i);
            }
        }
    }
    class ThreadDemo {
        public static void main(String[] args)     {
            //创建两个线程任务
            MyThread d = new MyThread();
            MyThread d2 = new MyThread();
            d.run();//没有开启新线程, 在主线程调用run方法
            d2.start();//开启一个新线程,新线程调用run方法
        }
    }

      2、实现Runnable接口

        1)创建线程的另一种方法是声明实现 Runnable 接口的类。

              该类然后实现 run 方法。然后创建Runnable的子类对象,传入到某个线程的构造方法中,开启线程

        2)接口中的方法

               

           Thread类构造方法

          

        3)创建线程的步骤。

          1、定义类实现Runnable接口。

          2、覆盖接口中的run方法。。

          3、创建Thread类的对象

          4、将Runnable接口的子类对象作为参数传递给Thread类的构造函数。

          5、调用Thread类的start方法开启线程。

    public class Demo02 {
        public static void main(String[] args) {
            //创建线程执行目标类对象
            Runnable runn = new MyRunnable();
            //将Runnable接口的子类对象作为参数传递给Thread类的构造函数
            Thread thread = new Thread(runn);
            Thread thread2 = new Thread(runn);
            //开启线程
            thread.start();
            thread2.start();
            for (int i = 0; i < 10; i++) {
                System.out.println("main线程:正在执行!"+i);
            }
        }
    }

    自定义线程执行任务类

    public class MyRunnable implements Runnable{
    
        //定义线程要执行的run方法逻辑
        @Override
        public void run() {
            
            for (int i = 0; i < 10; i++) {
                System.out.println("我的线程:正在执行!"+i);
            }
        }
    }

      4)实现Runable的好处

        第二种方式实现Runnable接口避免了单继承的局限性,所以较为常用。

        实现Runnable接口的方式,更加的符合面向对象,线程分为两部分,一部分线程对象,一部分线程任务。继承Thread类,线程对象和线程任务耦合在一起。

        一旦创建Thread类的子类对象,既是线程对象,有又有线程任务。实现runnable接口,将线程任务单独分离出来封装成对象,类型就是Runnable接口类型。

        Runnable接口对线程对象和线程任务进行解耦。

    三、线程的匿名内部类

      使用线程的内匿名内部类方式,可以方便的实现每个线程执行不同的线程任务操作。

      方式1:创建线程对象时,直接重写Thread类中的run方法  

    new Thread() {
                public void run() {
                    for (int x = 0; x < 40; x++) {
                        System.out.println(Thread.currentThread().getName()
                                + "...X...." + x);
                    }
                }
            }.start();

      方式2:使用匿名内部类的方式实现Runnable接口,重新Runnable接口中的run方法

    Runnable r = new Runnable() {
                public void run() {
                    for (int x = 0; x < 40; x++) {
                        System.out.println(Thread.currentThread().getName()
                                + "...Y...." + x);
                    }
                }
            };
            new Thread(r).start();

       

  • 相关阅读:
    【LeetCode】Validate Binary Search Tree
    【LeetCode】Search in Rotated Sorted Array II(转)
    【LeetCode】Search in Rotated Sorted Array
    【LeetCode】Set Matrix Zeroes
    【LeetCode】Sqrt(x) (转载)
    【LeetCode】Integer to Roman
    贪心算法
    【LeetCode】Best Time to Buy and Sell Stock III
    【LeetCode】Best Time to Buy and Sell Stock II
    CentOS 6 上安装 pip、setuptools
  • 原文地址:https://www.cnblogs.com/luzhijin/p/13434524.html
Copyright © 2011-2022 走看看