前言
线程组,顾名思义,就是线程的组,逻辑类似项目组,用于管理项目成员,线程组就是用来管理线程。
每个线程都会有一个线程组,如果没有设置将会有些默认的初始化设置
而在java中线程组则是使用类ThreadGroup 进行抽象描述
构造器
private ThreadGroup() {
this.name = "system"; //设置线程组名称
this.maxPriority = Thread.MAX_PRIORITY; //线程组最大优先级
this.parent = null; //父线程组为空
}
public ThreadGroup(String name) { //将线程组和线程名称传递给下面的构造器
this(Thread.currentThread().getThreadGroup(), name);
}
public ThreadGroup(ThreadGroup parent, String name) { //将信息传递给下一个构造器
this(checkParentAccess(parent), parent, name);
}
private ThreadGroup(Void unused, ThreadGroup parent, String name) {
this.name = name; //线程名称赋值
this.maxPriority = parent.maxPriority; //线程组最大优先级是父线程组的最大优先级
this.daemon = parent.daemon; //是否为守护线程,取决于父线程组
this.vmAllowSuspension = parent.vmAllowSuspension;
this.parent = parent; //父线程组
parent.add(this); //将此线程组添加到父线程组
}
属性
private final ThreadGroup parent; //父线程组
String name; //线程名称
int maxPriority; //最大优先级
boolean destroyed; //是否销毁
boolean daemon; //是否为守护
boolean vmAllowSuspension;
int nUnstartedThreads = 0; //未启动线程数
int nthreads; //线程总数
Thread threads[]; //线程数组
int ngroups; //线程组数量
ThreadGroup groups[]; //线程组数组
方法
Get / Set 方法
public final String getName() { return name; } //返回线程组名称
public final ThreadGroup getParent() { if (parent != null) parent.checkAccess(); return parent; } //返回父线程组
public final int getMaxPriority() { return maxPriority; } //返回最大优先级
public final boolean isDaemon() { return daemon; } //是否为守护线程组
public synchronized boolean isDestroyed() { return destroyed; } //是否被销毁
public final void setDaemon(boolean daemon) { checkAccess(); this.daemon = daemon; } //设置是否为守护
public final boolean parentOf(ThreadGroup g) { //当前线程组 是否 为线程组g的父线程组
for (; g != null ; g = g.parent) {
if (g == this) {
return true;
}
} return false;
}
//设置最大优先级
public final void setMaxPriority(int pri) {
int ngroupsSnapshot;
ThreadGroup[] groupsSnapshot;
synchronized (this) {
checkAccess(); //权限效验
if (pri < Thread.MIN_PRIORITY || pri > Thread.MAX_PRIORITY) { //必须在范围之内
return;
}
//父线程不为空,选择参数pri和父线程组最大优先级中最小的;否则为参数pri
maxPriority = (parent != null) ? Math.min(pri, parent.maxPriority) : pri;
ngroupsSnapshot = ngroups;//线程组数赋值
if (groups != null) { //线程数组不为空
groupsSnapshot = Arrays.copyOf(groups, ngroupsSnapshot); //线程组复制
} else {
groupsSnapshot = null;
}
}
//设置所有线程组最大优先级
for (int i = 0 ; i < ngroupsSnapshot ; i++) {
groupsSnapshot[i].setMaxPriority(pri);
}
}
enumerate()方法:把此线程组中的所有活动子组的引用复制到指定线程数组中。
public int enumerate(Thread list[]) {
checkAccess();
return enumerate(list, 0, true);
}
public int enumerate(Thread list[], boolean recurse) {
checkAccess();
return enumerate(list, 0, recurse);
}
private int enumerate(Thread list[], int n, boolean recurse) {
int ngroupsSnapshot = 0;
ThreadGroup[] groupsSnapshot = null;
synchronized (this) {
if (destroyed) { //如果销毁,退出
return 0;
}
int nt = nthreads;//将线程数赋值给nt
if (nt > list.length - n) { //如果nt大于它,就将其设置为它。
nt = list.length - n;
}
//将线程组中的线程,赋值给list线程集合
for (int i = 0; i < nt; i++) {
if (threads[i].isAlive()) {
list[n++] = threads[i];
}
}
if (recurse) {
ngroupsSnapshot = ngroups;
if (groups != null) {
groupsSnapshot = Arrays.copyOf(groups, ngroupsSnapshot);
} else {
groupsSnapshot = null;
}
}
}
if (recurse) {
for (int i = 0 ; i < ngroupsSnapshot ; i++) {
n = groupsSnapshot[i].enumerate(list, n, true);
}
}
return n;
}
enumerate()方法:把此线程组中的所有活动子组的引用复制到指定线程组数组中
public int enumerate(ThreadGroup list[]) {
checkAccess();
return enumerate(list, 0, true);
}
public int enumerate(ThreadGroup list[], boolean recurse) {
checkAccess();
return enumerate(list, 0, recurse);
}
private int enumerate(ThreadGroup list[], int n, boolean recurse) {
int ngroupsSnapshot = 0;
ThreadGroup[] groupsSnapshot = null;
synchronized (this) {
if (destroyed) {
return 0;
}
int ng = ngroups;
if (ng > list.length - n) {
ng = list.length - n;
}
if (ng > 0) {
System.arraycopy(groups, 0, list, n, ng);
n += ng;
}
if (recurse) {
ngroupsSnapshot = ngroups;
if (groups != null) {
groupsSnapshot = Arrays.copyOf(groups, ngroupsSnapshot);
} else {
groupsSnapshot = null;
}
}
}
if (recurse) {
for (int i = 0 ; i < ngroupsSnapshot ; i++) {
n = groupsSnapshot[i].enumerate(list, n, true);
}
}
return n;
}
统计活动线程/线程组估计数
//活动线程估计数
public int activeCount() {
int result;
int ngroupsSnapshot;
ThreadGroup[] groupsSnapshot;
synchronized (this) {
if (destroyed) {
return 0;
}
result = nthreads;
ngroupsSnapshot = ngroups;
if (groups != null) {
groupsSnapshot = Arrays.copyOf(groups, ngroupsSnapshot);
} else {
groupsSnapshot = null;
}
}
for (int i = 0 ; i < ngroupsSnapshot ; i++) {
result += groupsSnapshot[i].activeCount();
}
return result;
}
//活动线程组的估计数
public int activeGroupCount() {
int ngroupsSnapshot;
ThreadGroup[] groupsSnapshot;
synchronized (this) {
if (destroyed) {
return 0;
}
ngroupsSnapshot = ngroups;
if (groups != null) {
groupsSnapshot = Arrays.copyOf(groups, ngroupsSnapshot);
} else {
groupsSnapshot = null;
}
}
int n = ngroupsSnapshot;
for (int i = 0 ; i < ngroupsSnapshot ; i++) {
n += groupsSnapshot[i].activeGroupCount();
}
return n;
}
interrupt() 中断线程组中所有线程
public final void interrupt() {
int ngroupsSnapshot;
ThreadGroup[] groupsSnapshot;
synchronized (this) {
checkAccess();
//循环中断当前线程组的线程
for (int i = 0 ; i < nthreads ; i++) {
threads[i].interrupt();
}
ngroupsSnapshot = ngroups;
if (groups != null) {
groupsSnapshot = Arrays.copyOf(groups, ngroupsSnapshot);
} else {
groupsSnapshot = null;
}
}
//循环中断包含的所有线程组中的线程
for (int i = 0 ; i < ngroupsSnapshot ; i++) {
groupsSnapshot[i].interrupt();
}
}
destory() 销毁此线程组及其所有子组。
public final void destroy() {
int ngroupsSnapshot;
ThreadGroup[] groupsSnapshot;
synchronized (this) {
checkAccess();
if (destroyed || (nthreads > 0)) { //如果当前线程已销毁 或 当前线程组内还有线程 抛出异常.
throw new IllegalThreadStateException();
}
ngroupsSnapshot = ngroups; //线程组数
if (groups != null) {
groupsSnapshot = Arrays.copyOf(groups, ngroupsSnapshot); //线程组数组复制
} else {
groupsSnapshot = null;
}
//父线程组不为空 进行销毁清空操作
if (parent != null) {
destroyed = true;
ngroups = 0;
groups = null;
nthreads = 0;
threads = null;
}
}
//循环销毁线程组内所有线程组
for (int i = 0 ; i < ngroupsSnapshot ; i += 1) {
groupsSnapshot[i].destroy();
}
if (parent != null) {
parent.remove(this);
}
}
add() 将指定的线程组添加到此组。
private final void add(ThreadGroup g){
synchronized (this) {
if (destroyed) {
throw new IllegalThreadStateException();
}
if (groups == null) { //线程组数组为空,新建长度为4
groups = new ThreadGroup[4];
} else if (ngroups == groups.length) { //不为空,扩容2倍
groups = Arrays.copyOf(groups, ngroups * 2);
}
groups[ngroups] = g;
ngroups++; //线程组数量自增1
}
}
remove() 从该组中移除指定的线程组。
private void remove(ThreadGroup g) {
synchronized (this) {
if (destroyed) {
return;
}
for (int i = 0 ; i < ngroups ; i++) {
//循环找到线程组中指定的线程,进行移除操作
if (groups[i] == g) {
ngroups -= 1;
System.arraycopy(groups, i + 1, groups, i, ngroups - i);
groups[ngroups] = null;
break;
}
}
//如果当前线程组内无线程,唤醒其他所有线程
if (nthreads == 0) {
notifyAll();
}
//此线程组啥都没有了,就销毁
if (daemon && (nthreads == 0) &&
(nUnstartedThreads == 0) && (ngroups == 0))
{
destroy();
}
}
}
还有一些方法没有介绍到,可以结合源码进行详细学习。