为什么我的ThreadLocal的initialValue()不起作用?

问题描述 投票:-1回答:2

我想在java中测试ThreadLocal对象的用法,但似乎我的initialValue()不起作用。而且我在get()之前打电话给set(),它应该按预期返回100的变量ID。这是我的代码:

public class UsageThreadLocal implements Runnable {
    private AnotherThreadID<Long> var;

    public UsageThreadLocal(AnotherThreadID<Long> v) {
        this.var = v;
    }

    public void run() {
        try {
            print("var getThreadID =" + var.get());
            Thread.sleep(200);
            var.set(Thread.currentThread().getId());
            print("var getThreadID =" + var.get());
        } catch (InterruptedException x) {
        }
    }

    private static void print(String msg) {
        String name = Thread.currentThread().getName();
        System.out.println(name + ": " + msg);
    }

    public static void main(String[] args) {
        AnotherThreadID<Long> tid = new AnotherThreadID<Long>() {
            @Override
            public Long initialValue() {
                ID = new Long(100);
                System.out.println("I'm in initialValue()!");
                return ID;
            }
        };
        UsageThreadLocal shared = new UsageThreadLocal(tid);

        try {
            Thread threadA = new Thread(shared, "threadA");
            threadA.start();

            Thread.sleep(50);

            Thread threadB = new Thread(shared, "threadB");
            threadB.start();

            Thread.sleep(50);

            Thread threadC = new Thread(shared, "threadC");
            threadC.start();
        } catch (InterruptedException x) {
        }
    }
}

class AnotherThreadID<T> extends ThreadLocal<T> {
    public T ID;

    @Override
    public void set(T newID) {
        ID = newID;
    }

    @Override
    public T get() {
        return ID;
    }

}

并执行我的代码的结果:

threadA: var getThreadID =null
threadB: var getThreadID =null
threadC: var getThreadID =null
threadA: var getThreadID =9
threadB: var getThreadID =10
threadC: var getThreadID =11

我的代码有什么问题或者我误解了ThreadLocal的用法?

java multithreading initialization thread-local
2个回答
1
投票

问题在于AnotherThreadID的实施。 ThreadLocal是为每个线程保留一个值,你重写get()set()基本上使它不再是一个ThreadLocal

您可以删除AnotherThreadID类,并用AnotherThreadID替换ThreadLocal,然后您的代码应该无需进一步更改即可。


0
投票

AnotherThreadID应该由其线程初始化,但是您在主线程中初始化它。而且你只有一个AnotherThreadID实例。实际上,每个线程都应该有一个实例。

© www.soinside.com 2019 - 2024. All rights reserved.