`

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();
        }


    }
}
分享到:
评论

相关推荐

    day020-继承加强和设计模式代码和笔记.rar

    1. 单元测试:(掌握) 1. 写一个单元测试类,命名方式:XxxTest(测试类没有main方法) 2.... 选中项目,右键 =&gt; ... 解决了线程安全问题,通过线程隔离有安全问题的数据实现的,底层是通过map保存线程id和值的。

    Pressure-test-for-MySql:由java实现的一个多线程对Mysql数据库测试

    Pressure-test-for-MySql 由java实现的一个多线程对Mysql数据库测试 ...###JDBCUtil工具类的实现: public class JDBCUtil { private JDBCUtil(){}//防止类外构造 Private static ResourceBundle rb=

    HaruRPC:基于java aio 的RPC 远程调用框架

    序列化和反序列的工具类,项目的实现为基于Gson的序列化工具 IOHandler 从Channel中读取数据并交由Serializer处理的类,本身是异步读取数据 在读取数据时 提供读取完成回调 RPCClient 发送RPC请求的客户端 将调用...

    单例设计模式实现总结

    单例模式适用于无状态的工具类、全局信息类等场景。例如日志工具类,在系统中记录日志;假设我们需要统计网站的访问次数,可以设置一个全局计数器。 单例模式的优势有 在内存里只有一个实例,减少了内存开销; 可以...

    Java基础最全笔记文档

    6. 集合工具类Collections、Map集合、集合嵌套、不可变集合 7. Stream流、异常处理 8. Logback日志框架、阶段项目 9. File、方法递归、字符集、IO流(一) 10. IO流(二) 11. 多线程 12. 网络编程 13. 单元测试、...

    javaSE代码实例

    17.7 线程安全的单变量操作 403 17.7.1 atomic包简介 403 17.7.2 atomic包中类的具体使用 404 17.8 障碍器 406 17.8.1 CyclicBarrier类简介 406 17.8.2 CyclicBarrier类的具体使用 407 ...

    Java 基础面试题

    9. mybatis的SqlSession如何保证线程安全 10. Io有哪些流,字节流和字符流的区别 11. String常用api 12. 自动拆装箱发生 13. Collections提供的工具方法 14. String、StringBuffer和StringBuilder区别 15. Map...

    Java开发技术大全(500个源代码).

    demoEnhanceThread.java 使用自己定义的线程类示例 producer_consumer.java 演示生产者-消费者线程 consumer.java 消费者线程 producer.java 生产者线程 common.java 公有类 第9章 示例描述:本章学习运行时...

    java基础案例与开发详解案例源码全

    12.5.2 使用集合工具类同步化集合类对象324 12.5.3 使用JDK5.0后提供的并发集合类324 12.6 用Timer类调度任务325 12.7 本章练习326 第13章 13.1 java.io.File类328 13.1.1 文件和目录是什么?328 13.1.2 Java对文件...

    net学习笔记及其他代码应用

    29.根据线程安全的相关知识,分析以下代码,当调用test方法时i&gt;10时是否会引起死锁?并简要说明理由。 public void test(int i) { lock(this) { if (i&gt;10) { i--; test(i); } } } 答:不会发生死锁,(但...

    JAVA基础课程讲义

    Collections工具类 141 Comparable接口 141 equals和hashcode方法 143  泛型 144 思考作业 145 上机作业 145 第八章 IO技术 146 为什么需要学习IO技术 146 基本概念 146 数据源 146 流的概念 146 第一个简单的IO流...

    JAVA语言程序设计【高清版】.pdf

    201 10.4.2 随机访问文件 202 习题 203 第11章 线程 204 11.1 线程和多线程 204 11.1.1 线程的概念 204 11.1.2 线程的结构 205 11.2 线程的状态 205 11.3 创建线程 206 11.3.1 继承Thread类 206 ...

    javacore:java核心 运算符,控制语句,函数,异常,集合,线程,数组,IO流,网路编程,设计模式,java8,面试相关

    java中数组工具类sort,binarySearch 二维数组 静态初始化 数组的特点 面向对象 对象的创建 成员变量和局部变量 匿名对象 面向对象的三大特征 构造函数 代码块 代码块的说明 this关键字 static关键字 使用static...

    \java超强笔记(超级经典)

    java.util.concurrent 包含了常用的多线程工具,是新的多线程工具的主体。 java.util.concurrent.atomic 包含了不用加锁情况下就能改变值的原子变量。 java.util.concurrent.locks 包含锁定的工具。 ...

    张孝祥Java就业培训教程.pdf

    在以后的章节中,用通俗易懂的手法,紧密联系实际应用的方式,深入浅出地讲解了多线程,常用Java类,Java中的I/O(输入输出)编程,GUI与Applet,网络编程等方面的知识。 本书许多内容都来源于程序员圈子里的非正式...

    C++100天经典实战系(含大量案例源码及通俗讲解教程,effective_c++、STL、综合能力全面提升)

    友元函数与友元类、引用与指针那些事、深入浅出C++虚函数的vptr与vtable、宏那些事、范围解析运算符那些事、从初级到高级的enum那些事、纯虚函数和抽象类、volatile、virtual、using、union、this、struct_class、...

    java编程基础,应用与实例

    10.1 静态类(static class) 146 10.2 成员类(member class) 147 10.3 局部类(local class) 150 10.4 匿名类(anonymous class) 152 10.5 巩固练习 153 第11章 异常处理(exception handing) 154 11.1 ...

    Java常见面试问题整理.docx

    2.方法区(元空间):方法区用于存储已被虚拟机加载的类信息、常量、静态变量,如static修饰的变量加载类的时候就被加载到方法区中。运行时常量池是方法区的一部分,class文件除了有类的字段、接口、方法等描述信息...

Global site tag (gtag.js) - Google Analytics