`

Static工具类线程安全问题

 
阅读更多
1.静态方法
    无论是静态方法还是实例方法,在内存中都只有一份代码,也就是只占用一份内存空间
方法属于一个程序块,只有当别人调用它时才会调到内存里面去执行,也就是说当前有多少个线程在执行就有多少组方法块里的局部变量

2.静态变量
    只存在一份,多个线程公用一份,一个线程修改就会影响其他线程

3.结论
   静态方法是使用得当是线程安全的,因为每次调用会创建一份私有块,如果是静态变量是的的话就要加锁挥着其他处理。

4.实例

class User{
    private int id;
    private String name;

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

public class StaticTest {
    private static int count = 0;
    private static int counts = 0;

    /**
     * 不会存在并发问题
     *
     * @return
     */
    public static String getTestStr() {
        String xx = Thread.currentThread().toString();
        try {
            Thread.sleep(10);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return xx;
    }

    /**
     * 存不存在并发问题与传入的变量有关
     * 假如thread a和thread b都在操作对象a则存在
     * @param user
     * @return
     */
    public static String getTestUser(User user) {
        String str = "id: " + user.getId() + "name: " + user.getName();
        try {
            Thread.sleep(10);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return str;
    }

    /**
     * 存在并发问题
     *
     * @return
     */
    public static int getTestCount() {
        count++;
        count++;
        count++;
        count++;
        count++;
        try {
            Thread.sleep(10);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        count++;
        count++;
        count++;
        count++;
        count++;
        return count;
    }

    /**
     * 不存在并发问题
     *
     * @return
     */
    public synchronized static int getTestCountS() {
        counts++;
        counts++;
        counts++;
        counts++;
        counts++;
        try {
            Thread.sleep(10);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        counts++;
        counts++;
        counts++;
        counts++;
        counts++;
        return counts;
    }

    public static void main(String[] args) {
        User user = new User();
        for (int i = 0 ; i < 1000 ; i++){
            final int finalI = i;
            Thread thread = new Thread(new Runnable() {
                @Override
                public void run() {
                    User userTmp = new User();
                    user.setId(finalI);
                    user.setName(Thread.currentThread().toString());
                    userTmp.setId(finalI);
                    userTmp.setName(Thread.currentThread().toString());
                    //局部变量不存在问题
                    System.out.println("getTestStr: " + Thread.currentThread()  + StaticTest.getTestStr());
                    //与user有关
                    System.out.println("getTestUser: " + Thread.currentThread() + StaticTest.getTestUser(user));
                    System.out.println("getTestUseS: " + Thread.currentThread()  + StaticTest.getTestUser(userTmp));

                    //线程不安全
                    System.out.println("getTestCount: "  + Thread.currentThread() + StaticTest.getTestCount() % 10);

                    //安全但是慢需要加锁
                    System.out.println("getTestCountS: "  + Thread.currentThread() + StaticTest.getTestCountS() % 10);
                }
            });
            thread.start();
        }


    }
}
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics