美文网首页
继承Thread类实现多线程

继承Thread类实现多线程

作者: 秋笙fine | 来源:发表于2019-01-16 00:28 被阅读0次

    Thread类是一个支持多线程的功能类,只要有一个子类它就可以实现多线程。

    除此之外,所有程序的起点是main方法,所有线程也有一个自己的起点,run方法,多线程的每个主体类之中都必须覆写Thread类中所提供的run()方法。

    public void run()
    

    这个方法没有返回值,表明了线程一旦开始无法停止。

    下面看一个示例:

    package TestDemo;
    
    
    
    class MyThread extends Thread{
        private String name;
        public MyThread(String name){
            this.name=name;
        }
        @Override
        public void run() {
            for (int i = 0; i < 200; i++) {
                System.out.println(this.name+"==>"+i);
            }
        }
    }
    public class TestDemo{
        
        public static void main(String[] args) {
            MyThread thread1=new MyThread("ThreadA");
            MyThread thread2=new MyThread("ThreadB");
            MyThread thread3=new MyThread("ThreadC");
    
            thread1.run();
            thread2.run();
            thread3.run();
    
        
        }
        
    
    }
    

    本线程类的功能是实现一个循环输出操作,我们的线程和进程一样,都必须轮流抢占资源。多线程的执行应该是多个线程并发执行。而我们上面的结果是:


    image.png

    顺序执行,显然与初衷不符。因此并没有真正启动多线程,真正启动多线程的是Thread类种的start()方法。

    public void start();
    

    但是调用此方法执行的方法体是run()方法定义的。我们将方法改为start()方法。

    package TestDemo;
    
    
    
    class MyThread extends Thread{
        private String name;
        public MyThread(String name){
            this.name=name;
        }
        @Override
        public void run() {
            for (int i = 0; i < 200; i++) {
                System.out.println(this.name+"==>"+i);
            }
        }
    }
    public class TestDemo{
        
        public static void main(String[] args) {
            MyThread thread1=new MyThread("ThreadA");
            MyThread thread2=new MyThread("ThreadB");
            MyThread thread3=new MyThread("ThreadC");
    
            thread1.start();
            thread2.start();
            thread3.start();
        }
    }
    
    image.png

    的确实现了并发执行的真-多线程。

    疑问?为什么多线程启动不是调用run()而是调用start()方法?

    我们打开jdk的安装路径,查看以下src压缩包中,Thread类中start()方法的源码:

     public synchronized void start() {
            /**
             * This method is not invoked for the main method thread or "system"
             * group threads created/set up by the VM. Any new functionality added
             * to this method in the future may have to also be added to the VM.
             *
             * A zero status value corresponds to state "NEW".
             */
            if (threadStatus != 0)
                throw new IllegalThreadStateException();
    
            /* Notify the group that this thread is about to be started
             * so that it can be added to the group's list of threads
             * and the group's unstarted count can be decremented. */
            group.add(this);
    
            boolean started = false;
            try {
                start0();
                started = true;
            } finally {
                try {
                    if (!started) {
                        group.threadStartFailed(this);
                    }
                } catch (Throwable ignore) {
                    /* do nothing. If start0 threw a Throwable then
                      it will be passed up the call stack */
                }
            }
        }
        private native void start0();
    
    

    首先发现start方法中throw了一个IllegalThreadStateException() ,此方法没有try catch处理,也没有在start()方法上添加throws继续向调用start方法的上层抛出,这是一个RuntimeException,属于选择性异常,如果一个线程重复启动,就会抛出这个异常。

    此外在start()方法中,调用了一个start0方法,使用native进行声明。

    这里就引出了一个,Java中有一门技术叫JNI,这们技术能:使用Java调用本机操作系统提供的函数。但是这样的技术有一个缺点,不能够离开特定的操作系统。

    如果想要线程能够执行,需要操作系统来进行资源分配,需要由JVM负责根据不同的操作系统而实现。(JVM跨平台跨操作系统调用资源,实现多线程 因而start0方法在不同的操作系统上有不同的体现)

    即JVM不仅需要实现多线程的执行代码,还要根据不同的操作系统实现资源的分配,这种跨平台实现的方法,任何一个计算机软件问题都可以通过添加一个中间件来解决,嗯= =这个中间件,就是我们的start()方法了。

    相关文章

      网友评论

          本文标题:继承Thread类实现多线程

          本文链接:https://www.haomeiwen.com/subject/cuzudqtx.html