逸帅 发表于 2021-4-28 19:23

多线程优先级失效原因分析

# 问题描述:

<font color=#999AAA >多个线程同时运行,给重要的线程设置优先级高,不重要的设置优先级低,但是实际运行过程中,重要的线程不一定每次都先运行。 </font>

代码:
```java

public class ThreadDemo3 implements Runnable {
    public StringBuffer log = new StringBuffer();

    @Override
    public void run() {
      for (int i = 1; i <= 100; i++) {
            log.append((Thread.currentThread()).getName() + ":" + i + " ");
            if (i % 10 == 0) {
                log.append("\n");
            }
      }
    }
    public static void main(String[] args) throws Exception {
      ThreadDemo3 threadDemo3 = new ThreadDemo3();
      Thread xc1 = new Thread(threadDemo3, "线程1");
      Thread xc2 = new Thread(threadDemo3, "线程2");
      //设置优先级
      xc1.setPriority(Thread.MAX_PRIORITY);
      xc2.setPriority(Thread.MIN_PRIORITY);

      xc1.start();
      xc2.start();

      Thread.sleep(2000);
      System.out.println(threadDemo3.log);
    }

}

```
结果:线程一的优先级高,反而后执行

!(http://tc.glulu7.cn/2021-04-28-094736.png)


<hr style=" border:solid; width:100px; height:1px;" color=#000000 size=1">

# 原因分析:

<font color=#999AAA >处理器是多核的。
这段代码在单核CPU上一定是先线程一后线程二的,但是现在处理器都是多核的,多核CPU是可以真正实现多个线程同时运行的,而不是简单的快速切换的假象,每个核心都能够负责一个线程,有可能线程一对应的核心,调度比较慢,线程二调度快一点,所以造成了线程二先运行的</font>



这就是线程即使设置了优先级,运行任然具有随机性的原因

<hr style=" border:solid; width:100px; height:1px;" color=#000000 size=1">

# 解决方案:

你可以把你的CPU核心关掉一些,只留下一个核心工作,再运行这个。

关闭多核CPU核心的方法:
开始,运行,输入:MSCONFIG再点 BOOT.INI 找到高级选项,点开 /NUMPROC9(N)= 里面只选1就关掉另外的核了,如果你是四核,里面有1 2 3 4可选,点2就是只能当双核用,以此类推。

PS:我的是Mac系统,没有进行测试,有没有大佬测试一下?给个准确的回复看看不,探索的路上,大家一起加油!



# 怎么让一个线程一定优先运行?

不管是t1、t2、t3谁先运行,最终的结果,一定是t1先运行完,然后是t2运行完,最后是t3

```java
public static void main(String[] args) {
      final Thread T1 = new Thread(new Runnable() {
            public void run() {
                System.out.println("T1 run");
            }
      });
      final Thread T2 = new Thread(new Runnable() {
            public void run() {
                System.out.println("T2 run");
                try{
                  T1.join();
                }catch (Exception e){
                  e.printStackTrace();
                }
                System.out.println("T2 run end");
            }
      });
      Thread T3 = new Thread(new Runnable() {
            public void run() {
                System.out.println("T3 run");
                try{
                  T2.join();
                }catch (Exception e){
                  e.printStackTrace();
                }
                System.out.println("T3 run end");
            }
      });
      T1.start();
      T2.start();
      T3.start();

    }
```

ghimi 发表于 2021-4-28 19:46

用循环屏障(CylicBarrier) 和 CountDownLatch 是不是可以屏蔽线程的可见性吧,
楼主的方法是吧 t1 线程暴露给了 t2,把t2线程暴露给t3是不是不太好?
而且平时应该用的是线程池,线程之间是隔离的吧?

逸帅 发表于 2021-4-28 21:46

ghimi 发表于 2021-4-28 19:46
用循环屏障(CylicBarrier) 和 CountDownLatch 是不是可以屏蔽线程的可见性吧,
楼主的方法是吧 t1 线程暴 ...

大佬,嘿嘿,JUC我还没学,才准备看看多线程,等我学完JVM、JUC,再回来看你的,是不是就能看懂了{:301_978:}

ghimi 发表于 2021-4-28 22:08

逸帅 发表于 2021-4-28 21:46
大佬,嘿嘿,JUC我还没学,才准备看看多线程,等我学完JVM、JUC,再回来看你的,是不是就能看懂了{:301_9 ...

嗯嗯,加油{:1_921:}{:1_921:}
页: [1]
查看完整版本: 多线程优先级失效原因分析