多线程编程-线程间通信-ThreadLocal(七)

1,ThreadLocal类主要解决的是每个线程绑定自己的值,这里存储的是每个线程私有的数据,解决了变量在不同线程间的隔离性。

测试代码:

public class Tools {
	public static ThreadLocal tl = new ThreadLocal();
}
public class ThreadA extends Thread {

	@Override
	public void run() {
		try {
			for(int i=0; i<10; i++){
				Tools.tl.set("ThreadA "+(i+1));
				System.out.println("ThreadA get value="+Tools.tl.get());
			}
			Thread.sleep(2000);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}
}
public class ThreadB extends Thread {

	@Override
	public void run() {
		try {
			for(int i=0; i<10; i++){
				Tools.tl.set("ThreadB "+(i+1));
				System.out.println("ThreadB get value="+Tools.tl.get());
			}
			Thread.sleep(2000);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}
}
public class RunTest {

	public static void main(String[] args) {
		ThreadA ta = new ThreadA();
		ThreadB tb = new ThreadB();
		ta.start();
		tb.start();
	}
}
运行结果:

ThreadB get value=ThreadB 1
ThreadA get value=ThreadA 1
ThreadA get value=ThreadA 2
ThreadA get value=ThreadA 3
ThreadA get value=ThreadA 4
ThreadA get value=ThreadA 5
ThreadA get value=ThreadA 6
ThreadA get value=ThreadA 7
ThreadA get value=ThreadA 8
ThreadA get value=ThreadA 9
ThreadA get value=ThreadA 10
ThreadB get value=ThreadB 2
ThreadB get value=ThreadB 3
ThreadB get value=ThreadB 4
ThreadB get value=ThreadB 5
ThreadB get value=ThreadB 6
ThreadB get value=ThreadB 7
ThreadB get value=ThreadB 8
ThreadB get value=ThreadB 9
ThreadB get value=ThreadB 10

每个线程都取出了自己设置的值。

2,ThreadLocal第一次get会返回null,可以通过重载其方法initialValue来设置默认值。

测试代码:

public class Tools {
	public static ThreadLocalExt tl = new ThreadLocalExt();
}
class ThreadLocalExt extends ThreadLocal{

	@Override
	protected Object initialValue() {
		System.out.println("default value not null.");
		return new Date().getTime();
	}
}
public class ThreadA extends Thread {

	@Override
	public void run() {
		try {
			Thread.sleep(2000);
			System.out.println("ThreadA get value="+Tools.tl.get());
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}
}
public class ThreadB extends Thread {

	@Override
	public void run() {
		try {
			Thread.sleep(8000);
			System.out.println("ThreadB get value="+Tools.tl.get());
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}
}
public class RunTest {

	public static void main(String[] args) {
		ThreadA ta = new ThreadA();
		ThreadB tb = new ThreadB();
		ta.start();
		tb.start();
		if(Tools.tl.get() == null){
			System.out.println("main thread 还没有设置过值");
			Tools.tl.set(new Date().getTime());
		}
		System.out.println("main thread ,tl="+Tools.tl.get());
	}
}
运行结果:

default value not null.
main thread ,tl=1516241174168
default value not null.
ThreadA get value=1516241176167
default value not null.
ThreadB get value=1516241182168

每个线程都有自己的初始值。

3,InheritableThreadLocal的使用

类InheritableThreadLocal,可以让子线程取得从父线程继承下来的。

测试代码:

public class Tools {
	public static InheritableThreadLocalExt tl = new InheritableThreadLocalExt();
}
class InheritableThreadLocalExt extends InheritableThreadLocal{
	@Override
	protected Object initialValue() {
		System.out.println("default value not null.");
		return new Date().getTime();
	}

	@Override
	protected Object childValue(Object parentValue) {
		System.out.println("child value inheritable.");
		return parentValue+"-child change value";
	}
	
}
public class RunTest {

	public static void main(String[] args) {
		if(Tools.tl.get() == null){
			System.out.println("main thread 还没有设置过值");
			Tools.tl.set(new Date().getTime());
		}
		System.out.println("main thread ,tl="+Tools.tl.get());
		ThreadA ta = new ThreadA();
		ThreadB tb = new ThreadB();	
		ta.start();
		tb.start();		
	}
}
ThreadA,ThreadB的代码不变,但是RunTest.java代码稍微有改动,就是把ThreadA,ThreadB的对象创建放在了主线程的这句:System.out.println("main thread ,tl="+Tools.tl.get());之后。如果把线程A,B的创建放在这句调用之前,A,B线程不会继承父线程(主线程)的值。

protected Object childValue(Object parentValue) {}是在继承的同时,可以对值做修改。

运行结果:

default value not null.
main thread ,tl=1516245837214
child value inheritable.
child value inheritable.
ThreadA get value=1516245837214-child change value
ThreadB get value=1516245837214-child change value

可以看到,虽然线程A,B都有几秒的延迟,但是获取的时间都是main线程的InheritableThreadLocal的时间。






评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值