0 0

关于++操作线程安全问题的疑惑5

public class TestSynchronizedThread  implements Runnable{

	private static Integer si = 0;

        private static AtomicInteger flag = new AtomicInteger();  
	
	@Override
	public void run() {
		for(int k=0;k<200000;k++){
			synchronized(si){
				si++;
			}
		}
	}
 public static void main(String[] args) throws InterruptedException{  
        TestMultiThread t1 = new TestMultiThread();  
        TestMultiThread t2 = new TestMultiThread();  
        ExecutorService exec1 = Executors.newCachedThreadPool();  
        ExecutorService exec2 = Executors.newCachedThreadPool();  
        exec1.execute(t1);  
        exec2.execute(t2);  
        while(true){  
            if(flag.intValue()==2){   
                System.out.println("si>>>>>"+si);           
                break;  
            }  
            Thread.sleep(50);  
        }  
  
          
    }  
}

这段代码最后结果si打印出来小于400000,为什么加了synchronized后++操作还会产生中间状态,而我在JVM字节码中并未找到相应的证据佐证。
下面是主要JVM字节码:
   0:   iconst_0
   1:   istore_1
   2:   iload_1
   3:   ldc     #2; //int 200000
   5:   if_icmpge       55
   8:   getstatic       #3; //Field si:Ljava/lang/Integer;
   11:  dup
   12:  astore_2
   13:  monitorenter
   14:  getstatic       #3; //Field si:Ljava/lang/Integer;
   17:  astore_3
   18:  getstatic       #3; //Field si:Ljava/lang/Integer;
   21:  invokevirtual   #4; //Method java/lang/Integer.intValue:()I
   24:  iconst_1
   25:  iadd
   26:  invokestatic    #5; //Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
   29:  dup
   30:  putstatic       #3; //Field si:Ljava/lang/Integer;
   33:  astore  4
   35:  aload_3
   36:  pop
   37:  aload_2
   38:  monitorexit
   39:  goto    49
   42:  astore  5
   44:  aload_2
   45:  monitorexit
   46:  aload   5
   48:  athrow
   49:  iinc    1, 1
   52:  goto    2
   55:  return

希望各位大侠能帮小弟指点一下迷津。
2012年7月30日 08:31

1个答案 按时间排序 按投票排序

0 0

采纳的答案

si++执行后,都会指向一个新的对象。
synchronized(si),每次进来时si并不是同一个对象。不同对象的上的锁当然不行了。

2012年7月30日 09:14

相关推荐

    理解原子操作,CAS加锁是线程安全的.docx

    ### 理解原子操作与CAS加锁:确保线程安全的关键 #### 一、引言 在现代软件开发中,尤其是多线程环境中,如何有效地处理并发问题是一大挑战。Java作为主流的编程语言之一,提供了多种工具和技术来解决这一问题。...

    Java 线程间数据交换的疑惑

    此外,如果变量是通过对象引用传递的,还需要确保对象的状态修改也是线程安全的。 总之,`volatile`关键字在Java并发编程中扮演着重要的角色,它能帮助开发者解决线程间数据交换的部分问题,但并不是万能的。理解和...

    AS/400-多线程编程技术.pdf

    在多线程环境下调用C程序时,需要特别注意线程安全问题,确保调用的库函数能够正确处理并发访问。 ##### 1.6 多线程编程的通讯问题 多线程编程中的通讯问题是确保程序正确执行的关键。常见的通讯机制包括信号量、...

    来自IBM的多线程编程

    初始化阶段需要注意线程安全问题,例如避免在初始化时使用非线程安全的函数。 **4.3 线程的特有数据(threadspecificdata)** 线程特有的数据可以用于存储每个线程的私有信息,避免线程间的数据冲突。 **4.4 调用不...

    《多线程编程技术》

    多线程环境下数据库操作和数据处理需要特别注意线程安全性和数据一致性。 #### 线程的基本管理操作 多线程编程涉及一系列线程管理和控制操作,如线程的创建、终止、同步等。 ##### 2.1 线程的属性 线程的属性...

    多线程编程技术《Programming Multithreaded applications

    确保程序初始化阶段正确处理线程安全问题是至关重要的,特别是在使用全局变量和静态变量时。 ##### 线程的特有数据(thread specific data) 线程特有数据是指在线程中局部存储的数据,可以在每个线程中拥有独立的...

    java多线程学习笔记02(csdn)————程序.pdf

    Java多线程编程是开发高并发应用的关键技术之一。在这个学习笔记中,主要讨论了Java中的线程同步机制,包括volatile关键字、...在设计多线程程序时,应充分考虑线程安全、性能和可维护性,合理利用这些同步机制。

    关于CoreJava同步的疑惑例子

    这些操作应该在多线程环境下是安全的,因此可能使用`synchronized`关键字来保护这些操作。 - `TransferRunnable.java`可能包含一个实现了`Runnable`接口的类,这个类代表转账任务。在`run()`方法中,它可能调用`...

    来自IBM的(POSIX).

    多线程编程需要考虑的操作系统支持、库函数的线程安全性等问题。 **1.4 活动作业组(Activation group)** - **基本资料**: 活动作业组用于组织相关线程,便于资源管理和调度。 - **注意事项**: 需要关注线程间的...

    操作系统原理课后答案(第四版)+作者庞丽萍)

    讨论了线程的创建、调度、同步和通信,以及多线程的优势与问题。 3. **内存管理**:讲解了虚拟内存、分页、分段、页表、地址映射、内存保护、内存碎片及优化技术。 4. **存储器层次结构**:涵盖高速缓存(Cache)的...

    解决java中的疑惑

    5. **字符串操作**:Java中的String是不可变的,这可能导致性能问题。了解StringBuilder和StringBuffer的使用场景,以及如何高效地操作字符串,是必备技能。 6. **集合框架**:List、Set和Map接口以及它们的实现类...

    caozuoxit.zip_操作系统 第三版 答案

    多线程和并发编程是现代操作系统设计的热点,第三版教材可能会深入讨论多线程的实现机制,以及如何在多线程环境下进行有效的资源管理和同步。 内存管理负责在计算机系统中分配和回收内存空间,它需要保证内存的有效...

    操作系统大学课件

    操作系统安全性和稳定性也是重要的讨论点,例如权限控制、访问控制列表(ACL)、容错技术和故障恢复策略。 最后,课件中提供的习题将帮助学生巩固所学知识,通过解决实际问题来提升对操作系统的理解。论坛地址则...

    (完整word版)LinuxPthread深入解析.doc

    Linux Pthread 深入解析 1. 线程特点 线程是操作系统调度的基本单位,具有轻量级的特点。在Linux系统中,每个线程都有自己的...在处理并发问题时,要特别关注线程安全和资源管理,以防止竞态条件和死锁等问题的发生。

    计算机操作系统课后答案

    10. **操作系统的并发与并行**:多线程,线程同步与通信,线程池的概念。 通过阅读和对比这些课后答案,学习者可以深化对以上知识点的理解,解决在自学过程中遇到的疑惑,提高解决问题的能力。同时,理解并应用这些...

    Java中遇到的问题和解决方案.docx

    - 并发编程是Java开发中的难点之一,主要涉及到并发控制、线程安全等问题。 - **并发工具类**如CountDownLatch、CyclicBarrier等的使用场景和原理。 - **线程池**的配置和使用也是考察的重点之一。 #### 三、...

    think in java 4 练习题答案

    本压缩包包含的“练习题答案”无疑是学习过程中的一大辅助资料,可以帮助读者检验自己的理解,解决学习中的疑惑。 在Java的学习过程中,理解和掌握以下几个关键知识点至关重要: 1. **基础语法**:Java是一种静态...

    jdt.rar_C# 进度条_C#进度显示_c进度条_进度条

    9. **多线程安全**:在多线程环境下,确保更新进度条的操作是线程安全的至关重要。在C#中,可以使用`Invoke`或`BeginInvoke`方法来确保UI更新在正确的线程上执行。 综上所述,"jdt.rar"可能包含的资源可能涵盖如何...

    Java常见问题集锦 java_faq.rar

    2. **语法问题**:如变量声明、数据类型、运算符、控制结构(条件语句、循环语句)等常见疑惑。 3. **异常处理**:如何使用try-catch-finally语句块,理解不同类型的异常以及何时抛出异常。 4. **集合框架**:...

Global site tag (gtag.js) - Google Analytics