Java并发编程之:ThreadGroup

Wesley13
• 阅读 567

线程组ThreadGroup标识一组线程的集合,一旦一个线程归属到一个线程组中,就不能更换其所在的线程组。

使用线程组好处:方便统一管理,线程组合一进行复制,快读定位到一个线程,统一进行一场设置等。

ThreadGroup并不属于java并发包中的内容,它是java.lang中的内容。

基本方法:

1.获取当前线程组名:

Thread.currentThread().getThreadGroup().getName();

在main方法中输出main

2.将线程放入到一个线程组中去

ThreadGroup tg = new ThreadGroup("My Group");
MyThread2 thrd = new MyThread2(tg, "MyThread #1");
MyThread2 thrd2 = new MyThread2(tg, "MyThread #2");
MyThread2 thrd3 = new MyThread2(tg, "MyThread #3");

其中Thread中和ThreadGroup相关的构造函数:

public Thread(ThreadGroup group, Runnable target) {  
    init(group, target, "Thread-" + nextThreadNum(), 0);  
}  
  
  
public Thread(ThreadGroup group, String name) {  
    init(group, null, name, 0);  
}  
  
  
public Thread(ThreadGroup group, Runnable target, String name) {  
    init(group, target, name, 0);  
}  
  
public Thread(ThreadGroup group, Runnable target, String name,  long stackSize) {  
    init(group, target, name, stackSize);  
}  

它们最终都是调用同一个函数:

   private void init(ThreadGroup g, Runnable target, String name,  
                     long stackSize) {  
Thread parent = currentThread();  
SecurityManager security = System.getSecurityManager();  
if (g == null) {  
        //安全检查  
    if (security != null) {  
    g = security.getThreadGroup();  
    }  
  
       //设置线程组  
    if (g == null) {  
    g = parent.getThreadGroup();  
    }  
}  
  
   //检查可达性  
g.checkAccess();  
  
    //是否有权限访问  
if (security != null) {  
    if (isCCLOverridden(getClass())) {  
        security.checkPermission(SUBCLASS_IMPLEMENTATION_PERMISSION);  
    }  
}  
  
    //往线程组添加线程但未启动  
    g.addUnstarted();  
  
this.group = g;  
this.daemon = parent.isDaemon();//是否守护线程  
this.priority = parent.getPriority();//优先级  
this.name = name.toCharArray();  
if (security == null || isCCLOverridden(parent.getClass()))  
    this.contextClassLoader = parent.getContextClassLoader();  
else  
    this.contextClassLoader = parent.contextClassLoader;  
this.inheritedAccessControlContext = AccessController.getContext();  
this.target = target;  
setPriority(priority);  
       if (parent.inheritableThreadLocals != null)  
    this.inheritableThreadLocals =  
    ThreadLocal.createInheritedMap(parent.inheritableThreadLocals);  
       this.stackSize = stackSize;  
       tid = nextThreadID();  
       this.me = this;  
   }  

3、复制线程组:

Thread thrds[] = new Thread[tg.activeCount()];
tg.enumerate(thrds);

这里的activeCount很明显就是取得活动的线程,注意。默认情况 下,连同其子线程组也会进行复制。

4、未捕获异常处理

ThreadGroup中有一个uncaughtException()方法。当线程组中某个线程发生Unchecked exception异常时,由执行环境调用此方法进行相关处理,如果有必要,可以重新定义此方法

统一异常处理:

public class ThreadGroupExec {

    public static void main(String[] args) {
        ThreadGroup threadGroup1 = new ThreadGroup("group1"){
            @Override
            public void uncaughtException(Thread t, Throwable e) {
                System.out.println(t.getName() + ": " + e.getMessage());
            }
        };

        // 这是匿名类写法
        Thread thread1 =
                // 这个线程是threadGroup1的一员
                new Thread(threadGroup1, new Runnable() {
                    @Override
                    public void run() {
                        // 抛出unchecked异常
                        throw new RuntimeException("测试异常");
                    }
                });

        thread1.start();
    }
}

查看构造函数:

public class ThreadGroup implements Thread.UncaughtExceptionHandler {  
    private final ThreadGroup parent;//父亲ThreadGroup  
    String name;//ThreadGroupr 的名称  
    int maxPriority;//线程最大优先级  
    boolean destroyed;//是否被销毁  
    boolean daemon;//是否守护线程  
    boolean vmAllowSuspension;//是否可以中断  
  
    int nUnstartedThreads = 0;//还未启动的线程  
    int nthreads;//ThreadGroup中线程数目  
    Thread threads[];//ThreadGroup中的线程  
  
    int ngroups;//线程组数目  
    ThreadGroup groups[];//线程组数组  

参考:

https://blog.csdn.net/evankaka/article/details/51627380

http://blog.csdn.net/edward\_qing\_lee/article/details/8767612

https://www.cnblogs.com/yiwangzhibujian/p/6212104.html

点赞
收藏
评论区
推荐文章
待兔 待兔
4个月前
手写Java HashMap源码
HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程22
Wesley13 Wesley13
3年前
java ThreadGroup 作用 方法解析(转)
ThreadGroup线程组,java对这个类的描述呢就是“线程组表示一组线程。此外,线程组还可以包括其他线程组。线程组形成一个树,其中除了初始线程组之外的每个线程组都有一个父线程组。允许线程访问关于其线程组的信息,但不允许访问关于其线程组的父线程组或任何其他线程组的信息。”ThreadGroup并不是算是标注容器,因为,最后你会发现这个家伙
Stella981 Stella981
3年前
Executor框架
任务是一组逻辑工作单元,而线程则是使任务异步执行的机制。线程池简化了线程的管理工作,并且java.util.concurrent提供了一种灵活的线程池实现作为Executor框架的一部分。在Java类库中,任务执行的主要抽象不是Thread,而是Executor,如下所示:publicinterfaceExecutor{void
Wesley13 Wesley13
3年前
Java CyclicBarrier介绍
CyclicBarrier(周期障碍)类可以帮助同步,它允许一组线程等待整个线程组到达公共屏障点。CyclicBarrier是使用整型变量构造的,其确定组中的线程数。当一个线程到达屏障时(通过调用CyclicBarrier.await()),它会被阻塞,直到所有线程都到达屏障,然后在该点允许所有线程继续执行。与CountDownLatch不同的
Wesley13 Wesley13
3年前
Java 线程池原理分析
1.简介线程池可以简单看做是一组线程的集合,通过使用线程池,我们可以方便的复用线程,避免了频繁创建和销毁线程所带来的开销。在应用上,线程池可应用在后端相关服务中。比如Web服务器,数据库服务器等。以Web服务器为例,假如Web服务器会收到大量短时的HTTP请求,如果此时我们简单的为每个HTTP请求创建一个处理线程,那么服务器
Wesley13 Wesley13
3年前
JUC
Java5.0在java.util.concurrent包中提供了多种并发容器类来改进同步容器的性能。CountDownLatch一个同步辅助类,在完成一组正在其他线程中执行的操作之前,它允许一个或多个线程一
Wesley13 Wesley13
3年前
JUC——JUC开发简介(一)
前言JUC是Java5.0开始提供的一组专门实现多线程并发处理的开发框架,利用JUC开发架构可以有效的解决实际线程项目开发之中出现的死锁、阻塞、资源访问与公平机制。此笔记主要记录java.util.concurrent开发包之中的各个核心组成类的使用、操作原理分析,并且通过具体的实际代码对多线程的开发实际环境进行原理分析,同时方便自己随时复习掌
Wesley13 Wesley13
3年前
2万字Java并发编程面试题整理(含答案,建议收藏)
Java并发编程1、在java中守护线程和本地线程区别?2、线程与进程的区别?3、什么是多线程中的上下文切换?4、死锁与活锁的区别,死锁与饥饿的区别?5、Java中用到的线程调度算法是什么?6、什么是线程组,为什么在Java中不推荐使用?7、为什么使用Executor框架?8、在Java
Stella981 Stella981
3年前
Noark入门之协议映射
0x00消息控制器消息控制器,主要作用就是为每个模块提供消息处理的入口.这里的消息不仅仅是协议,还有内部指令,事件等等逻辑入口,这也是为了响应线程模型作出的一种支撑,只要入口在此消息控制器内,那必然走期望的线程调度。@Controller用于标识一个类为当前模块的消息控制器入口.@Controller(threadGroup
深入浅出线程池 | 京东云技术团队
一、线程1、什么是线程线程(thread)是操作系统能够进行运算调度的最小单位。它被包含在进程之中,是进程中的实际运作单位。一条线程指的是进程中一个单一顺序的控制流,一个进程中可以并发多个线程,每条线程并行执行不同的任务。2、如何创建线程2.1、JAVA中