Thread.Start()方法运行多线程

Java多线程创建与运行理了一下线程的创建和运行,可以看到线程最终都是通过new一个Thread实例,然后调用start()方法来运行的。

但是我们可以看到,一个线程的所要执行的任务方法体都是重写到run()方法里面的。
但是这里是调用的start()方法来运行线程的,这说明start()方法做了一系列工作来新建一个线程运行run()方法里面的行为,而不是从当前这个main()函数的线程去运行他。

线程的属性
根据线程的属性,我们可以自己设定线程的名称。

        Runnable runnable = ()->{
    
    
            System.out.println(Thread.currentThread().getName());
        };

        Thread threadName = new Thread(runnable);
        // 设置要创建的线程名称
        threadName.setName("codeXT");
        threadName.start();
        //如下方式并不会创建新线程执行run()方法
        threadName.run();

在这里插入图片描述

start()方法由synchronized修饰,synchronized修饰的资源相当于临界资源,一个线程进去之后,其他线程调用会被阻塞挂起。而java线程和操作系统线程对应,会导致用户态到内核态的切换来执行阻塞,会引起上下文切换,时间耗费比较大。在退出synchronized修饰的资源时,会将共享变量的修改刷新到主内存,来保证内存可见性。

    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 */
            }
        }
    }

调用start()时,会判断threadStatus != 0,threadStatus是记录线程的状态,初始默认为0,当线程启动后,threadStatus的值会发生改变,当第二次调用start()时,就会抛出异常。start()方法只会被执行一次,也就是只能开启一个线程。

 if (threadStatus != 0)
            throw new IllegalThreadStateException();

threadStatusvolatile修饰,确保了内存可见性问题,就是说这个变量的值对于其他线程也是立马可见的最新值,会将更新的变量更新到主内存,确保了内存可见性。但是volatile修饰不保证原子性,是非阻塞的。

    private volatile int threadStatus = 0;

Guess you like

Origin blog.csdn.net/qq_37774171/article/details/121402938