今天领导问了个问题说单例模式中,对象的变量是否是线程安全的。起初都不太确定,后来本着装的目的,试了一下,结果是否定的。在多线程环境下,对象的成员变量是不安全的。
package com.zhuyang.test;
public class Singleton {
private static final Singleton singleton;
//variable will be updated in muti-thread
private int count;
static {
singleton = new Singleton();
}
public static synchronized Singleton getInstance() {
return singleton;
}
public int getCount() {
return count;
}
public void setCount(int count) {
this.count = count;
}
}
上面的代码是一段标准的单例模式。 其中有个成员变量count.他的值,会再多线程环境下不断修改。
package com.zhuyang.test;
public class Test {
/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
ThreadTest t1=new ThreadTest(1111);
ThreadTest t2=new ThreadTest(2222);
ThreadTest t3=new ThreadTest(3333);
ThreadTest t4=new ThreadTest(4444);
ThreadTest t5=new ThreadTest(5555);
ThreadTest t6=new ThreadTest(6666);
ThreadTest t7=new ThreadTest(7777);
t1.start();
t2.start();
t3.start();
t4.start();
t5.start();
t6.start();
t7.start();
}
}
class ThreadTest extends Thread {
private int threadID;
public ThreadTest(int threadID) {
this.threadID = threadID;
}
@Override
public void run() {
Singleton singleton = Singleton.getInstance();
singleton.setCount(threadID);
System.out.println(this.getName()+"is updating count value is="+this.getThreadID()+", count value of singleton is="+singleton.getCount());
}
public int getThreadID() {
return threadID;
}
public void setThreadID(int threadID) {
this.threadID = threadID;
}
}
运行上面的代码结果:
Thread-0is updating count value is=1111, count value of singleton is=4444
Thread-4is updating count value is=5555, count value of singleton is=4444
Thread-5is updating count value is=6666, count value of singleton is=4444
Thread-2is updating count value is=3333, count value of singleton is=4444
Thread-6is updating count value is=7777, count value of singleton is=4444
Thread-3is updating count value is=4444, count value of singleton is=4444
Thread-1is updating count value is=2222, count value of singleton is=4444
说明,多线程中,单例模式并非线程安全,即便是加上了synchronized关键字。
那么如何做到线程安全呢?做法就是把对象给synchronized掉,看代码。
package com.zhuyang.test;
public class Test {
/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
ThreadTest t1=new ThreadTest(1111);
ThreadTest t2=new ThreadTest(2222);
ThreadTest t3=new ThreadTest(3333);
ThreadTest t4=new ThreadTest(4444);
ThreadTest t5=new ThreadTest(5555);
ThreadTest t6=new ThreadTest(6666);
ThreadTest t7=new ThreadTest(7777);
t1.start();
t2.start();
t3.start();
t4.start();
t5.start();
t6.start();
t7.start();
}
}
class ThreadTest extends Thread {
private int threadID;
public ThreadTest(int threadID) {
this.threadID = threadID;
}
@Override
public void run() {
Singleton singleton = Singleton.getInstance();
synchronized (singleton) {
singleton.setCount(threadID);
System.out.println(this.getName()+"is updating count value is="+this.getThreadID()+", count value of singleton is="+singleton.getCount());
}
}
public int getThreadID() {
return threadID;
}
public void setThreadID(int threadID) {
this.threadID = threadID;
}
}
结果:
Thread-0is updating count value is=1111, count value of singleton is=1111
Thread-1is updating count value is=2222, count value of singleton is=2222
Thread-2is updating count value is=3333, count value of singleton is=3333
Thread-3is updating count value is=4444, count value of singleton is=4444
Thread-4is updating count value is=5555, count value of singleton is=5555
Thread-6is updating count value is=7777, count value of singleton is=7777
Thread-5is updating count value is=6666, count value of singleton is=6666
分享到:
相关推荐
Java中懒汉单例设计模式线程安全测试,单例设计模式的测试
在多线程环境下,线程安全的单例模式尤为重要,因为如果不正确实现,可能会导致多个线程同时创建多个实例,违反了单例模式的基本原则。 在Java中,单例模式通常有以下几种实现方式: 1. 饿汉式(静态常量): ...
线程安全的单例模式在多线程环境下尤其重要,因为不正确的实现可能导致多个线程创建多个实例,这违反了单例模式的基本原则。C++11引入了新的特性,如std::mutex和std::call_once,使得实现线程安全的单例模式变得...
### 线程安全的单例模式详解 #### 一、单例模式简介 单例模式(Singleton Pattern)是软件开发中最常用的创建型设计模式之一,它的主要目标是确保一个类只有一个实例,并提供一个全局访问点。单例模式在很多场景下...
Java 单例模式线程安全问题详解 Java 单例模式线程安全问题是指在 Java 中实现单例模式时,如何确保线程安全的问题。单例模式是指在整个应用程序生命周期中,只有一个实例存在的设计模式。这种模式可以提高性能,...
使用"懒汉模式"与"饿汉模式"实现c++的单例模式,并且确保了单例模式的第一次实例化的线程安全,以及程序结束时,单例对象的资源收回,以防内存资源的泄漏
单例模式三种线程安全的表达方式,其中枚举方式的单例是最安全的
在C++编程中,单例模式是一种常用的软件设计模式,它保证一个类只有一个实例,并提供一个全局访问点。在这个特定的场景中,我们讨论的是一个实现了单例模式的日志类,该类专为多线程环境设计,具备日志等级控制、...
然而,如果我们想要在类级别实现线程安全的单例模式,就需要考虑多线程环境下的并发问题。 在给出的代码中,首先定义了一个装饰器`Singleton`,它的目的是确保每次调用时返回的是同一个实例。装饰器内部维护了一个...
总结起来,多线程环境下的单例模式实现需要注意线程安全问题,尤其是懒汉式单例,需要采取适当的同步措施来防止多线程环境下的实例化问题。此外,对于不同场景的需求,可以选择不同的实现方式来优化性能和资源使用。
内容概要:本文详尽地阐述了 C# 中单例模式的设计思想以及其实现方式,并且特别针对单例模式的线例安全提供了多种解决方案,包括锁(lock),最终给出了一段非线程安全和一段线程安全版本的代码供参考。 适合人群:C# ...
单例模式是软件设计模式中的一种经典模式,其主要目的是确保一个类只有一个实例,并提供一个全局访问点。这种模式在很多场景下非常有用,比如控制共享资源、管理配置对象等。下面将详细介绍七种常见的单例模式实现...
单例模式是软件设计模式中的一种经典模式,它保证了类只有一个实例存在,并提供一个全局访问点。在Java等面向对象编程语言中,单例模式常用于管理共享资源,如数据库连接池、线程池或者配置文件等。结合工厂模式,...
单例模式是软件设计模式中的一种经典模式,用于确保一个类只有一个实例,并提供一个全局访问点。在Java中,有多种实现单例模式的方法,每种都有其特点和适用场景。接下来,我们将深入探讨这些实现方式。 首先,我们...
单例模式是软件设计模式中的一种,它保证一个类只有一个实例,并提供一个全局访问点。在C#中,单例模式常用于管理共享资源或控制类的实例化过程,以提高性能、节约系统资源,特别是在整个应用程序生命周期内只需要一...
**设计模式——单例模式** 在软件工程中,设计模式是一种在特定场景下解决常见问题的标准方案,可以被复用并提升代码质量。单例模式是设计模式中的一种,它保证一个类只有一个实例,并提供一个全局访问点。这种模式...
1 教科书里的单例模式 我们都很清楚一个简单的单例模式该怎样去实现:构造函数声明为private或protect防止被外部函数实例化,内部保存一个private static的类指针保存唯一的实例,实例的动作由一个public的类方法...
在Java中,实现单例模式有多种方式,但最常见的问题是线程安全问题。例如,上述代码展示了一个简单的单例实现,称为"饿汉式"单例,因为无论是否需要,它都会在类加载时立即创建实例。这种方式虽然简单,但在多线程...
下面将详细介绍在Unity中涉及的三种单例模式:C#经典单例、Unity内置单例以及一种线程安全的改进版单例。 1. C#经典单例: 这是最常见的单例实现方式,通常通过私有构造函数和一个静态方法来保证只有一个实例。在...