精华内容
下载资源
问答
  • Thread类

    千次阅读 2018-03-25 15:41:09
    1 start方法 start()用来启动一个线程,当调用start方法后,系统才会开启一个新的线程来执行用户定义的子任务,在这个过程中,会为相应的线程分配需要...注意,继承Thread类必须重写run方法,在run方法中定义具体要...

     1 start方法

      start()用来启动一个线程,当调用start方法后,系统才会开启一个新的线程来执行用户定义的子任务,在这个过程中,会为相应的线程分配需要的资源。

      2 run方法

      run()方法是不需要用户来调用的,当通过start方法启动一个线程之后,当线程获得了CPU执行时间,便进入run方法体去执行具体的任务。注意,继承Thread类必须重写run方法,在run方法中定义具体要执行的任务。

    补充:用start()方法来启动线程,是真正实现了多线程,通过调用Thread类的start()方法来启动一个线程,这时此线程处于就绪(可运行)状态,并没有运行,一旦得到cpu时间片,就开始执行run()方法,无需等待run方法执行完毕,即可继续执行下面的代码。

    所以说:

    start()方法是真正实现了多线程run()方法只是一个普通的方法。

      3 sleep方法

      sleep方法有两个重载版本:

    1
    2
    3
    sleep(long millis)     //参数为毫秒
     
    sleep(long millis,int nanoseconds)    //第一参数为毫秒,第二个参数为纳秒
      
      sleep相当于让线程睡眠,交出CPU,让CPU去执行其他的任务。

         但是有一点要非常注意,sleep方法不会释放锁,也就是说如果当前线程持有对某个对象的锁,则即使调用sleep方法,其他线程也无法访问这个对象。看下面这个例子就清楚了:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    public class Test {
         
        private int i = 10;
        private Object object = new Object();
         
        public static void main(String[] args) throws IOException  {
            Test test = new Test();
            MyThread thread1 = test.new MyThread();
            MyThread thread2 = test.new MyThread();
            thread1.start();
            thread2.start();
        
         
         
        class MyThread extends Thread{
            @Override
            public void run() {
                synchronized (object) {
                    i++;
                    System.out.println("i:"+i);
                    try {
                        System.out.println("线程"+Thread.currentThread().getName()+"进入睡眠状态");  
                        Thread.currentThread().sleep(10000);
                    catch (InterruptedException e) {
                        // TODO: handle exception
                    }
                    System.out.println("线程"+Thread.currentThread().getName()+"睡眠结束");
                    i++;
                    System.out.println("i:"+i);
                }
            }
        }
    }

    Thread.currentThread().getName() 此方法的作用是获取线程名

    输出结果:

      从上面输出结果可以看出,当Thread-0进入睡眠状态之后,Thread-1并没有去执行具体的任务。只有当Thread-0执行完之后,此时Thread-0释放了对象锁,Thread-1才开始执行。

      注意,如果调用了sleep方法,必须捕获InterruptedException异常或者将该异常向上层抛出。当线程睡眠时间满后,不一定会立即得到执行,因为此时可能CPU正在执行其他的任务。所以说调用sleep方法相当于让线程进入阻塞状态。

      4)yield方法

      调用yield方法会让当前线程交出CPU权限,让CPU去执行其他的线程。它跟sleep方法类似,同样不会释放锁。但是yield不能控制具体的交出CPU的时间,另外,yield方法只能让拥有相同优先级的线程有获取CPU执行时间的机会。

      注意,调用yield方法并不会让线程进入阻塞状态,而是让线程重回就绪状态,它只需要等待重新获取CPU执行时间,这一点是和sleep方法不一样的。

      5)join方法

      join方法有三个重载版本:

    1
    2
    3
    join()
    join(long millis)     //参数为毫秒
    join(long millis,int nanoseconds)    //第一参数为毫秒,第二个参数为纳秒

       假如在main线程中,调用thread.join方法,则main方法会等待thread线程执行完毕或者等待一定的时间。如果调用的是无参join方法,则等待thread执行完毕,如果调用的是指定了时间参数的join方法,则等待一定的时间。

      看下面一个例子:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    public class Test {
         
        public static void main(String[] args) throws IOException  {
            System.out.println("进入线程"+Thread.currentThread().getName());
            Test test = new Test();
            MyThread thread1 = test.new MyThread();
            thread1.start();
            try {
                System.out.println("线程"+Thread.currentThread().getName()+"等待");
                thread1.join();
                System.out.println("线程"+Thread.currentThread().getName()+"继续执行");
            catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        
         
        class MyThread extends Thread{
            @Override
            public void run() {
                System.out.println("进入线程"+Thread.currentThread().getName());
                try {
                    Thread.currentThread().sleep(5000);
                catch (InterruptedException e) {
                    // TODO: handle exception
                }
                System.out.println("线程"+Thread.currentThread().getName()+"执行完毕");
            }
        }
    }

    结果:Thread-0调用完毕后才继续执行main线程

    wait方法会让线程进入阻塞状态,并且会释放线程占有的锁,并交出CPU执行权限。

    由于wait方法会让线程释放对象锁,所以join方法同样会让线程释放对一个对象持有的锁。具体的wait方法使用在后面文章中给出。

      6)interrupt方法

      interrupt,顾名思义,即中断的意思。单独调用interrupt方法可以使得处于阻塞状态的线程抛出一个异常,也就说,它可以用来中断一个正处于阻塞状态的线程;另外,通过interrupt方法和isInterrupted()方法来停止正在运行的线程。

      下面看一个例子:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    public class Test {
         
        public static void main(String[] args) throws IOException  {
            Test test = new Test();
            MyThread thread = test.new MyThread();
            thread.start();
            try {
                Thread.currentThread().sleep(2000);
            catch (InterruptedException e) {
                 
            }
            thread.interrupt();
        
         
        class MyThread extends Thread{
            @Override
            public void run() {
                try {
                    System.out.println("进入睡眠状态");
                    Thread.currentThread().sleep(10000);
                    System.out.println("睡眠完毕");
                catch (InterruptedException e) {
                    System.out.println("得到中断异常");
                }
                System.out.println("run方法执行完毕");
            }
        }
    }

       输出结果:

      

      从这里可以看出,通过interrupt方法可以中断处于阻塞状态的线程。那么能不能中断处于非阻塞状态的线程呢?看下面这个例子:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    public class Test {
         
        public static void main(String[] args) throws IOException  {
            Test test = new Test();
            MyThread thread = test.new MyThread();
            thread.start();
            try {
                Thread.currentThread().sleep(2000);
            catch (InterruptedException e) {
                 
            }
            thread.interrupt();
        
         
        class MyThread extends Thread{
            @Override
            public void run() {
                int i = 0;
                while(i<Integer.MAX_VALUE){
                    System.out.println(i+" while循环");
                    i++;
                }
            }
        }
    }

       运行该程序会发现,while循环会一直运行直到变量i的值超出Integer.MAX_VALUE。所以说直接调用interrupt方法不能中断正在运行中的线程。

      但是如果配合isInterrupted()能够中断正在运行的线程,因为调用interrupt方法相当于将中断标志位置为true,那么可以通过调用isInterrupted()判断中断标志是否被置位来中断线程的执行。比如下面这段代码:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    public class Test {
         
        public static void main(String[] args) throws IOException  {
            Test test = new Test();
            MyThread thread = test.new MyThread();
            thread.start();
            try {
                Thread.currentThread().sleep(2000);
            catch (InterruptedException e) {
                 
            }
            thread.interrupt();
        
         
        class MyThread extends Thread{
            @Override
            public void run() {
                int i = 0;
                while(!isInterrupted() && i<Integer.MAX_VALUE){
                    System.out.println(i+" while循环");
                    i++;
                }
            }
        }
    }

       运行会发现,打印若干个值之后,while循环就停止打印了。

      但是一般情况下不建议通过这种方式来中断线程,一般会在MyThread类中增加一个属性 isStop来标志是否结束while循环,然后再在while循环中判断isStop的值。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    class MyThread extends Thread{
            private volatile boolean isStop = false;
            @Override
            public void run() {
                int i = 0;
                while(!isStop){
                    i++;
                }
            }
             
            public void setStop(boolean stop){
                this.isStop = stop;
            }
        }

       那么就可以在外面通过调用setStop方法来终止while循环。

      7)stop方法

      stop方法已经是一个废弃的方法,它是一个不安全的方法。因为调用stop方法会直接终止run方法的调用,并且会抛出一个ThreadDeath错误,如果线程持有某个对象锁的话,会完全释放锁,导致对象状态不一致。所以stop方法基本是不会被用到的。

      8)destroy方法

      destroy方法也是废弃的方法。基本不会被使用到。

      以下是关系到线程属性的几个方法:

      1)getId

      用来得到线程ID

      2)getName和setName

      用来得到或者设置线程名称。

      3)getPriority和setPriority

      用来获取和设置线程优先级。

      4)setDaemon和isDaemon

      用来设置线程是否成为守护线程和判断线程是否是守护线程。

      守护线程和用户线程的区别在于:守护线程依赖于创建它的线程,而用户线程则不依赖。举个简单的例子:如果在main线程中创建了一个守护线程,当main方法运行完毕之后,守护线程也会随着消亡。而用户线程则不会,用户线程会一直运行直到其运行完毕。在JVM中,像垃圾收集器线程就是守护线程。

      Thread类有一个比较常用的静态方法currentThread()用来获取当前线程。

      在上面已经说到了Thread类中的大部分方法,那么Thread类中的方法调用到底会引起线程状态发生怎样的变化呢?下面一幅图就是在上面的图上进行改进而来的:

    展开全文
  • 使用Thread类的构造方法创建线程Thread(target=func,args=(a,b)),其中线程t1、t2的参数分别为args=(1,5), args=(10,20)。线程t1运行结束等待5秒,再开始t2线程。其中函数func为 func(a,b): for i in range(x, ...

    使用Thread类的构造方法创建线程Thread(target=func,args=(a,b)),其中线程t1、t2的参数分别为args=(1,5), args=(10,20)。线程t1运行结束等待5秒,再开始t2线程。其中函数func为
    func(a,b):
    for i in range(x, y):
    print(i)
    time.sleep(10)
    分别运行线程t1,t2后,再查看这两个线程的状态。`

    import threading,time
    def func(x,y):
        for i in range(x,y):
            print(i)
        time.sleep(10)
    t1=threading.Thread(target=func,args=(1,5))
    t1.start()
    t1.join(5)
    t2=threading.Thread(target=func,args=(10,20))
    t2.start()
    

    运行结果:
    在这里插入图片描述

    展开全文
  • 线程 创建和启动线程的两种方式 实现Runnable接口 继承Thread类 重写唯一方法run() 1.实现Runnable接口,必须重写Runnable接口的唯一run()方法。 启动线程的方法(在主程序中):启动线程需要由三步来执行。 1).首先...

    创建线程的两种方法

    1.实现Runnable接口,必须重写Runnable接口的唯一run()方法。

    (能实用接口就不要从Thread类继承,实现接口比较的灵活,而继承Thread类实现起来太麻烦)

    class Runner1 implements Runnable{      
        public void run(){
           for(int i=0; i<100;i++){
             System.out.println("Runnable1 :" +i);
           }  
    }

    启动线程的方法(在主程序中)启动线程需要由三步来执行。

        1).首先创建一个自己线程对象    例如 Runner1 r = new Runner1();

        2).new一个Thread对象(例如对象r)   例如Thread t = new Thread(r);

        3).必须调用Thread类的start方法       例如 t.start();




    2.从Thread类继承去创建一个线程(不推荐使用)。

    class Runner1 extends Thread{
       for(int i=0; i<100;i++){
             System.out.println("Runnable1 :" +i);
           }   
     }

     启动线程的方法(在主程序中)这里启动线程需要由两步来执行

      1).首先创建一个自己线程对象    例如 Runner1 r = new Runner1();

      2).必须调用Thread类的start方法       例如 r.start(); 






    展开全文
  • 1.继承Thread类 2.实现Runnable接口 推荐使用Runnable接口,基于以下四点: 1.使用 Runnable 接口适合多个相同程序代码的线程去处理同一资源的情况。 2.继承Thread类有一个缺点就是单继承,而实现Runnable接口则...

    线程的两种基本实现方法:

    1.继承Thread类
    2.实现Runnable接口

    推荐使用Runnable接口,基于以下四点:

     1.使用 Runnable 接口适合多个相同程序代码的线程去处理同一资源的情况,
        把虚拟CPU(线程)同程序的代码,数据有效的分离,较好地体现了面向对象的设计思想。 
     2.继承Thread类有一个缺点就是单继承,而实现Runnable接口则弥补了它的缺点,可以实现多继承。
     3.有利于程序的健壮性,代码能够被多个线程共享,代码与数据是独立的。
     4.使用 Runnable 接口来实现多线程使得我们能够在一个类中包容所有的代码,有利于封装。

    具体代码实现:

    //线程的测试类
    public class testThread{
    public static void main(String args[]){
    Thread    thread1=new threadOne("one");
    Thread    thread2=new threadTwo("two");
    thread1.start();
    thread2.start();
    }
    }
    
    //方法一
    //通过继承Thread类来构建线程
    //需要覆盖run()方法
    class threadOne extends Thread{
    String name;
    threadOne(String name)
    {
    this.name=name;
    }
    public void run()
    {
    for(int i=0;i<=9;i++)
    System.out.println("Current thread is "+name);
    }
    }
    
    //方法二
    //通过实现Runnable接口来构建线程
    //需要覆盖run()方法
    class threadTwo implements Runnable{
    String name;
    threadTwo(String name)
    {
    this.name=name;
    }
    public void run()
    {
    for(int i=0;i<=9;i++)
    System.out.println("Current thread is "+name);
    }
    }


    展开全文
  • Thread类、Runnable接口详解

    千次阅读 2019-12-26 23:08:02
    Thread类想必都不陌生,第一次学习多线程的时候就一定会接触Thread类。本篇主要从Thread类的定义、使用、注意事项、源码等方面入手,全方位的讲解Thread类。 Thread 我们经常会被问到这样一个问题: Java开启一个新...
  • Java并发编程——解析Thread类

    千次阅读 多人点赞 2019-08-28 22:05:20
    Callable 接口3.3 继承 Thread 类3.4 实现接口 VS 继承 Thread四、Thread类详解4.1 线程运行状态4.1.1 start()方法4.1.2 run 方法4.1.3 sleep 方法4.1.4 yield方法4.1.5 join方法4.1.6 int...
  • 2,复写Thread类中的run方法。 目的:将自定义代码存储在run方法。让线程运行。//run();仅仅是对象调用方法。而线程创建了,并没有运行。 3,调用线程的start方法, 该方法两个作用:启动线程,调用run方法...
  • 就是Thread类 * * 创建线程的第一种方式:继承Thread类。 * 步骤: * 1.定义类继承Thread。 * 2.复写Thread中的run方法,让线程运行。 * 目的:将自定义方法存储在run方法中,让线程运行。 * 3.调用线程
  • Thread的wait方法理解

    千次阅读 2017-11-08 23:07:50
    wait方法是Object对象的方法。线程与锁是分不开的,线程的同步、等待、唤醒都与对象锁是密不可分的。...只有通过以下四个方法可以主动唤醒: 1. notify 2. notifyAll 3. Thread.interrupt() 4. 等待时间过完...
  • 1.wait和notify不仅仅是普通方法或同步工具,更重要的是它们是Java中两个线程之间的通信机制 。对语言设计者而言,如果不能通过Java关键字(例如synchronized)实现此通信机制,同时又要确保这个机...
  • Java 并发:Thread 深度解析

    万次阅读 多人点赞 2017-01-11 20:44:31
     Java 中 Thread类 的各种操作与线程的生命周期密不可分,了解线程的生命周期有助于对Thread类中的各方法的理解。一般来说,线程从最初的创建到最终的消亡,要经历创建、就绪、运行、阻塞 和 消亡 五个状态。在线程...
  • 为什么wait,notify,notifyAll声明在Object中而不是在Thread中这个问题是一个非常有名的java核心面试题,在各种级别的Java开发者面试中都会出现
  • 2、覆写Thread类的run方法。 自定义代码放在run方法中,让线程运行 3、调用线程的star方法, 该线程有两个作用:启动线程,调用run方法。 代码示例: class Test extends Thread { //private String name; ...
  • Thread 的join方法解释

    万次阅读 2018-09-03 12:39:50
     Thread类中的join方法的主要作用就是同步,它可以使得线程之间的并行执行变为串行执行。具体看代码:   public class JoinTest { public static void main(String [] args) throws InterruptedException { ...
  • C#中 Thread类的使用

    千次阅读 2015-02-12 17:32:58
    Thread类是比较常用的一个类,这里总结了一些基本的使用方法和程序示例,以备以后查用。 https://msdn.microsoft.com/zh-cn/library/system.threading.thread.aspx using System; using
  • C#中,可以使用Thread类来处理(包含创建,启动,挂起,恢复,终止等操作)线程。本文将介绍如何使用Thread类来创建与启动新线程。 Thread类类位于System.Threading命名空间中。 1、线程创建与启动 实例化一个...
  • 多线程——继承Thread 和实现Runnable 接口的区别

    万次阅读 热门讨论 2017-07-11 14:24:39
    java中我们想要实现多线程常用的有两种方法,继承Thread 和实现Runnable 接口,有经验的程序员都会选择实现Runnable接口 ,其主要原因有以下两点: 首先,java只能单继承,因此如果是采用继承Thread方法,那么...
  • 启动一个新的线程,不是直接调用Thread子类的对象的run方法,而是调用Thread子类对象的start方法,start方法是从Thread类中继承的方法Thread类对象的start方法将产生一个新的线程,并在该线程上运行该Thread类对象...
  • Thread类-Flash中的线程概念

    千次阅读 2008-04-15 14:09:00
    我们就发现Java中线程是比较好的方法,于是我们就参照Java的Thread类,就写一个Flash的Thread类,这个类调用起来多了一两行代码,但是比较好控制和管理。和Java中Thread类非常相似。今天我也把它贴出
  • C++多线程(一)thread类

    万次阅读 多人点赞 2018-04-10 16:28:29
    与 C++11 多线程相关的头文件地方 C++11 新标准中引入了四个头文件来支持多线程编程,他们分别是&lt;atomic&gt; ,&...:该头文主要声明了两个, std::atomic 和 std::atomic_flag...
  • Thread(target)之run()方法

    千次阅读 2017-02-10 22:12:25
    不论是继承Thread类创建线程还是实现Runnable接口创建线程,启动线程一般都是调用Thread类的start()方法,然后由虚拟机自动调用Thread类的run()方法。Thread源码中如下:可以发现调用过程 1.首先打开start()方法: ...
  • [Chrome源码阅读] 理解Thread类实现

    千次阅读 2012-08-24 15:18:21
    Chrome中的Thread类实现比较有意思,没有复杂的接口,没有很多可调控的参数,譬如线程优先级什么的。 线程类Thread定义在base命名空间里,是一个比较通用的基础类。位于文件src\base\thread.h。Thread继承于...
  • Java Thread类的 yield()、join()

    万次阅读 2014-08-16 22:34:30
    // 可能还会执行 本线程: 以下语句不一定紧接着上面的语句被执行,可能其他线程的先执行了 System.out.println("second: " + Thread.currentThread().getName() ); } public static void main...
  • Visual C#中的多线程编程——(THREAD类,THREADPOOL类,TIMER类)C#是.Net平台的通用开发工具,它能够建造所有的.Net应用。在.Net中所有线程都运行在应用程序域(AppDomain)中,这也许让你想到Win32进程,实际上它们...
  • 通过调用Thread类的 start()方法来启动一个线程,这时此线程处于就绪(可运行)状态,并没有运行,一旦得到cpu时间片,就开始执行run()方法,这里方法 run()称为线程体,它包含了要执行的这个线程的内容,Run方法...
  • Thread线程的详细解释

    千次阅读 2016-01-14 10:23:48
    概述 软件包 使用 树 已过时 索引 帮助  JavaTM 2 Platform ...摘要: 嵌套 | 字段 | 构造方法 | 方法 详细信息: 字段 | 构造方法 | 方法  -----------------------------------------
  • 在本教程中,我们将讨论Thread类中的不同*join()*方法&nbsp;&nbsp;。我们将详细介绍这些方法和一些示例代码。 与&nbsp;&nbsp;wait()和notify()方法一样,*join()*是另一种线程间同步机制。 ...
  • C++11标准库会提供类thread(std::thread)。若要运行一个线程,可以创建一个类thread的实体,其初始参数为一个函数对象,以及该函数对象所需要的参数。通过成员函数std::thread::join()对线程会合的支持,一个线程...
  • Thread

    千次阅读 2015-07-12 22:57:05
    Thread

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 240,157
精华内容 96,062
关键字:

以下哪些是thread类的方法