好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

java ThreadGroup的作用及方法详解

 

ThreadGroup的作用及方法

ThreadGroup线程组,java对这个类的描述呢就是

[线程组表示一组线程。此外,线程组还可以包括其他线程组。线程组形成一个树,其中除了初始线程组之外的每个线程组都有一个父线程组。

允许线程访问关于其线程组的信息,但不允许访问关于其线程组的父线程组或任何其他线程组的信息。]

ThreadGroup并不是算是标注容器,因为,最后你会发现这个家伙是没有public的 add,remove方法的。那怎么把线程放到线程组里面呢?

答案是 在new Thread(参数),将ThreadGroup当做参数传进去。

 

Field

?

1

2

3

4

5

6

7

8

9

10

private final ThreadGroup parent; // 线程组的线程组,final 表名 线程组 不可以随便变更

String name; //名字

int maxPriority; //这个线程组 的元素 例如 线程 线程组的最大优先级,具体实现是 当线程或者线程组自身设定优先级的时候,总是取  自己父线程组的优先级和要设定的优先级的最小值

boolean destroyed; //判断是否销毁了

boolean daemon; //当守护进程线程组的最后一个线程停止或最后一个线程组被销毁时,将自动销毁该线程组。

int nUnstartedThreads = 0 ;

int nthreads; //这个线程组  里面的线程数量

Thread threads[]; //线程数组 ,持有 线程的引用

int ngroups; //这个线程组  里面的线程组数量

ThreadGroup groups[]; //线程组数组 ,持有 线程组的引用

 

私有构造方法

创建不在任何线程组中的空线程组。

此方法用于创建系统线程组。

?

1

private ThreadGroup()

 

公共构造方法

?

1

2

3

4

5

6

7

//创建一个新线程组。这个新组的父线程组是指定的线程组parent。线程组的 名字 就是name

会对 parent 调用checkAccess() 确定当前运行的线程是否具有修改此线程组的权限(比如 设置setDaemon)。有可能会抛出SecurityException异常

public ThreadGroup(ThreadGroup parent, String name)

//构造一个新线程组。这个新组的父线程组是当前运行线程的线程组。 就是调用上面的方法

public ThreadGroup(String name) {

     this (Thread.currentThread().getThreadGroup(), name);

}

 

公共方法

?

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 final String getName() //返回线程组名字

//返回父线程组  parent 调用checkAccess() 确定当前运行的线程是否具有修改此线程组的权限。

//有可能会抛出SecurityException异常

public final ThreadGroup getParent()

public final int getMaxPriority() //返回线程组优先级

//测试此线程组是否是守护进程线程组。当守护进程线程组的最后一个线程停止或最后一个线程组被销毁时,将自动销毁该线程组。

public final boolean isDaemon()

public synchronized boolean isDestroyed() //测试该线程组是否已被销毁。

public final void setDaemon( boolean daemon) //将线程组设置成守护线程组 ,会检查 当前线程是否具有权限 修改线程组

  //设定当前线程组以及子线程组的 优先级,取pri和当前线程组的父线程组的优先级的较小值为准。

  //这个之所以会限制 Thread的最大优先级

  //具体实现是 当线程或者线程组自身设定优先级的时候,总是取  自己父线程组的优先级和要设定的优先级的最小值

  //会检查 当前线程是否具有权限 修改线程组

public final void setMaxPriority( int pri)

  //测试,当前这个线程组是否是 g线程组的父线程 或者参数

public final boolean parentOf(ThreadGroup g)

  //检查 当前线程是否具有权限 修改线程组  比如在当前线程中 用线程组自己本身调用它自己的一些方法 ,都会检查

public final void checkAccess()

//返回此线程组及其子线程组中活动线程数量的估计值。递归地遍历此线程组中的所有子组。 如果当前线程组已经destroyed,返回0

public int activeCount()

//将线程组的中线程 活动线程放入list[]里面 会自动扩大这个数组,如果{@code recurse}为{@code true},则此方法递归枚举此线程组的所有子组,并引用这些子组中的每个活动线程

                                              //注意这个声明数组的方式

public int enumerate(Thread list[], boolean recurse)

//和上面方法类似  只不过 下面这个 ThreadGroup

public int enumerate(ThreadGroup list[])

public int enumerate(ThreadGroup list[], boolean recurse)

  //返回此线程组及其子组中活动组的数量的估计值。递归地遍历此线程组中的所有子组。

public int activeGroupCount()

//interrupt此线程组中的所有线程。包括 子线程组中的线程

public final void interrupt()

 

特殊的一个方法

?

1

public void uncaughtException(Thread t, Throwable e)

这个方法呢,作用很简单 使 t 线程 抛出一个 Throwable e的异常。这个e 异常 也是你自己定义的。如果前面设置了,

?

1

2

3

4

Thread.setDefaultUncaughtExceptionHandler((t, e) -> {

     System.out.println( "默认的  " +t.getName());

     System.out.println( "默认的  " +e);

});

那么,在上面自定义的Throwable 会被这个捕获,如果没有设置,就打印标注错误流。对这个方法,存在的意义 比较困惑

?

1

2

3

4

5

6

7

Thread.setDefaultUncaughtExceptionHandler((t, e) -> {

     System.out.println( "默认的  " +t.getName());

     System.out.println( "默认的  " +e);

});

ThreadGroup threadGroup = new ThreadGroup( "father" );

Thread two = new Thread(threadGroup, "two" );

threadGroup.uncaughtException(two, new IllegalAccessException( "ssss" ));

运行结果

 

线程组(ThreadGroup类)

线程组表示一个线程的集合。线程组也可以包含其他线程组。线程执行完就会被回收。

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

private static void methodA() {

     MyThread my = new MyThread() ;

        

     //创建线程类对象

        

     Thread t1 = new Thread(my, "线程1" ) ;

     Thread t2 = new Thread(my, "线程2" ) ;

        

     //public final ThreadGroup getThreadGroup()返回该线程所属的线程组

     ThreadGroup tg1 = t1.getThreadGroup() ;

     ThreadGroup tg2 = t2.getThreadGroup() ;

        

     //public final String getName():返回线程组的名称

     System.out.println(tg1.getName()); //main

     System.out.println(tg2.getName()); //main

        

     //所有的线程它默认的线程组名称:main(主线程),主线程是包含在线程组里面的

     System.out.println(Thread.currentThread().getThreadGroup().getName()); //main

}

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

private static void methodB() {

        //public ThreadGroup(String name)构造一个新线程组

     ThreadGroup tg = new ThreadGroup( "新的线程组" ) ;

        

     MyThread my = new MyThread() ;

    

         //Thread(ThreadGroup group, Runnable target, String name)

     Thread t1 = new Thread(tg, my, "线程1" ) ;

     Thread t2 = new Thread(tg, my, "线程2" ) ;

        

     //直接获取线程组名称

     System.out.println(t1.getThreadGroup().getName());

     System.out.println(t2.getThreadGroup().getName());

}

以上为个人经验,希望能给大家一个参考,也希望大家多多支持。

原文链接:https://blog.csdn.net/a1064072510/article/details/87455525

查看更多关于java ThreadGroup的作用及方法详解的详细内容...

  阅读:13次