今天,短暂的经历了人生的失意后,已经皮实了。我要将今年学的东西进行归纳总结。
Thread类算是源码比较简单的类,现对其进行刨析。后续所有分享都是基于java1.8。
一、Thread类的私有参数
public
class Thread implements Runnable {
//Thread 类继承自Runnable接口,Runnable接口只有一个方法既run方法,所以实现线程的两种方法,继承Tread类和实现Runnable接口本质上都是基于Runnable来实现的,最终都是重写了Runnable接口中的run方法,参考java继承机制。
/* Make sure registerNatives is the first thing <clinit> does. */
private static native void registerNatives();
static {
registerNatives();
}
//这几个变量没有查到被使用过,先放在这,后续研究一下
private volatile String name;
private int priority;
private Thread threadQ;//
private long eetop;
private boolean single_step;
private boolean daemon = false;
private boolean stillborn = false;
//构造函数中会传入的runnable实现的接受者
private Runnable target;
//线程组,一个线程必然有线程组
private ThreadGroup group;
//线程加载器
private ClassLoader contextClassLoader;
//???
private AccessControlContext inheritedAccessControlContext;
//静态变量,使用内部静态类的单例模式,全局存在,用来生成线程名
private static int threadInitNumber;
private static synchronized int nextThreadNum() {
return threadInitNumber++;
}
//threadLocal,后面会单独研究这个类
ThreadLocal.ThreadLocalMap threadLocals = null;
//提供父进程到子进程的threalocal里的局部变量
ThreadLocal.ThreadLocalMap inheritableThreadLocals = null;
//预期堆栈大小,不指定默认为0,0代表忽略这个属性。与平台相关,不建议使用该属性。
private long stackSize;
//JVM使用的变量
private long nativeParkEventPointer;
//线程ID
private long tid;
//静态变量 ++新创建线程后自增
private static long threadSeqNumber;
//JVM变量,线程状态,NEW,RUNNABLE,WAITING,BLOCKED,TIMED_WAITING,TIMED_WAITING
private volatile int threadStatus = 0;
//返回线程ID
private static synchronized long nextThreadID() {
return ++threadSeqNumber;
}
//中断相关 LockSupport
volatile Object parkBlocker;
//interrupt
private volatile Interruptible blocker;
private final Object blockerLock = new Object();
void blockedOn(Interruptible b) {
synchronized (blockerLock) {
blocker = b;
}
}
//线程的优先级常量
public final static int MIN_PRIORITY = 1;//最低级别
public final static int NORM_PRIORITY = 5;
public final static int MAX_PRIORITY = 10;//最高级别
二、Thread 初始化分析
//本地yield方法
public static native void yield();
//本地sleep方法
public static native void sleep(long millis) throws InterruptedException; private void
//初始化方法
init(ThreadGroup g, Runnable target, String name,
long stackSize) {
init(g, target, name, stackSize, null, true);
}
//初始化的完全方法
private void init(ThreadGroup g, Runnable target, String name,
long stackSize, AccessControlContext acc,
boolean inheritThreadLocals) {
if (name == null) {
throw new NullPointerException("name cannot be null");
}
//初始化名字,父线程
this.name = name;
Thread parent = currentThread();//父线程是当前线程
//初始化group,如果有安全线程,就获取安全线程的group,否则获取父线程的安全线程
SecurityManager security = System.getSecurityManager();
if (g == null) {//作为start方法的接收target
//
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();
//加载类加载器
if (security == null || isCCLOverridden(parent.getClass()))
this.contextClassLoader = parent.getContextClassLoader();
else
this.contextClassLoader = parent.contextClassLoader;
//父类
this.inheritedAccessControlContext =
acc != null ? acc : AccessController.getContext();
//将runnable赋值给Thread,设置优先级
this.target = target;
setPriority(priority);
if (inheritThreadLocals && parent.inheritableThreadLocals != null)
this.inheritableThreadLocals =
ThreadLocal.createInheritedMap(parent.inheritableThreadLocals);
//设置栈大小
this.stackSize = stackSize;
//设置线程ID
tid = nextThreadID();
}
@Override
protected Object clone() throws CloneNotSupportedException {
throw new CloneNotSupportedException();
}
//下面有这么些种类的Tread()初始化构造函数,
public Thread() {
init(null, null, "Thread-" + nextThreadNum(), 0);
}
public Thread(Runnable target) {
init(null, target, "Thread-" + nextThreadNum(), 0);
}
Thread(Runnable target, AccessControlContext acc) {
init(null, target, "Thread-" + nextThreadNum(), 0, acc, false);
}
public Thread(ThreadGroup group, Runnable target) {
init(group, target, "Thread-" + nextThreadNum(), 0);
}
public Thread(String name) {
init(null, null, name, 0);
}
public Thread(ThreadGroup group, String name) {
init(group, null, name, 0);
}
public Thread(Runnable target, String name) {
init(null, target, 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);
}
三、Thread常用方法实现分析
1、start()方法
public synchronized void start() {
//threadStatus初始化为0
if (threadStatus != 0)
throw new IllegalThreadStateException();
//通知group添加这个线程
group.add(this);
boolean started = false;
try {
start0();
started = true;//用来在start0异常退出时,从group线程组中移除该thread
} 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 */
}
}
}
//native方法
private native void start0();
//group的方法,通过向线程池里添加线程,有线程池来管理线程
ThreadGroup::void add(Thread t) {
synchronized (this) {
if (destroyed) {
throw new IllegalThreadStateException();
}
if (threads == null) {
threads = new Thread[4];
} else if (nthreads == threads.length) {
threads = Arrays.copyOf(threads, nthreads * 2);
}
threads[nthreads] = t;
// This is done last so it doesn't matter in case the
// thread is killed
nthreads++;
// The thread is now a fully fledged member of the group, even
// though it may, or may not, have been started yet. It will prevent
// the group from being destroyed so the unstarted Threads count is
// decremented.
nUnstartedThreads--;
}
}
//该Thread继承了Runnable,线程实现有两种方法,一种是继承Thread重写run方法,一种是实现Runnable然后通过构造函数赋值给target,如果是第一种相当于重写了下面这个run方法,如果是第二种相当于调用了Runnable实现的run方法
@Override
public void run() {
if (target != null) {
target.run();
}
}
2、exit()方法
//将所有改线程申请的资源清理掉
private void exit() {
if (group != null) {
group.threadTerminated(this);
group = null;
}
/* Aggressively null out all reference fields: see bug 4006245 */
target = null;
/* Speed the release of some of these resources */
threadLocals = null;
inheritableThreadLocals = null;
inheritedAccessControlContext = null;
blocker = null;
uncaughtExceptionHandler = null;
}
3、interrupt()方法
//中断方法
public void interrupt() {
if (this != Thread.currentThread())
checkAccess();
synchronized (blockerLock) {
Interruptible b = blocker;
if (b != null) {
interrupt0(); // Just to set the interrupt flag
b.interrupt(this);
return;
}
}
interrupt0();
}
4、join方法
public final synchronized void join(long millis)
throws InterruptedException {
long base = System.currentTimeMillis();
long now = 0;
if (millis < 0) {
throw new IllegalArgumentException("timeout value is negative");
}
if (millis == 0) {
//自旋等待
while (isAlive()) {
wait(0);
}
} else {
//超时自旋等待
while (isAlive()) {
long delay = millis - now;
if (delay <= 0) {
break;
}
wait(delay);
now = System.currentTimeMillis() - base;
}
}
}
5、sleep()方法
public static void sleep(long millis, int nanos)
throws InterruptedException {
if (millis < 0) {
throw new IllegalArgumentException("timeout value is negative");
}
if (nanos < 0 || nanos > 999999) {
throw new IllegalArgumentException(
"nanosecond timeout value out of range");
}
if (nanos >= 500000 || (nanos != 0 && millis == 0)) {
millis++;
}
sleep(millis);
}
6 、setPriority方法
public final void setPriority(int newPriority) {
ThreadGroup g;
checkAccess();
if (newPriority > MAX_PRIORITY || newPriority < MIN_PRIORITY) {
throw new IllegalArgumentException();
}
if((g = getThreadGroup()) != null) {
if (newPriority > g.getMaxPriority()) {
newPriority = g.getMaxPriority();
}
setPriority0(priority = newPriority);
}
}