`
shuai1234
  • 浏览: 972173 次
  • 性别: Icon_minigender_1
  • 来自: 山西
社区版块
存档分类
最新评论

java 同步锁(synchronized)

    博客分类:
  • java
 
阅读更多

java中cpu分给每个线程的时间片是随机的并且在java中好多都是多个线程共用一个资源,比如火车卖票,火车票是一定的,但卖火车票的窗口到处都有,每个窗口就相当于一个线程,这么多的线程共用所有的火车票这个资源。如果在一个时间点上,两个线程同时使用这个资源,那他们取出的火车票是一样的(座位号一样),这样就会给乘客造成麻烦。比如下面程序:

[java] view plain copy
 
 print?
  1. package com.pakage.ThreadAndRunnable;  
  2.   
  3. public class Runnable_demo implements Runnable{  
  4.     private int ticket=10;  
  5.     public Runnable_demo(){       
  6.     }  
  7.     @Override  
  8.     public void run() {  
  9.         for(int i=0;i<20;i++){  
  10.                 if(this.ticket>0){  
  11.                     //休眠1s秒中,为了使效果更明显,否则可能出不了效果  
  12.                     try {  
  13.                         Thread.sleep(1000);  
  14.                     } catch (Exception e) {  
  15.                         e.printStackTrace();  
  16.                     }  
  17.                     System.out.println(Thread.currentThread().getName()+"号窗口卖出:"+this.ticket--+"号票");  
  18.                 }  
  19.               
  20.         }  
  21.     }  
  22.       
  23.      public static void main(String args[]){  
  24.          Runnable_demo demo=new Runnable_demo();  
  25.          //基于火车票创建三个窗口  
  26.          new Thread(demo,"a").start();  
  27.          new Thread(demo,"b").start();  
  28.          new Thread(demo,"c").start();  
  29.      }  
  30.       
  31. }  

程序运行结果:


我们可以看到c号窗口和和b号窗口都卖出了10号票,并且a号和b号窗口分别卖出了0号和-1号票。造成这种情况的原因是1、c线程和b线程在ticket=10的时候,c线程取出10号票以后,ticket还没来的及减1,b线程就取出了ticket此时ticket还等于10;2、在ticket=1时,c线程取出了1号票,ticket还没来的及减1,a、b线程就先后进入了if判断语句,这时ticket减1了,那么当a、b线程取票的时候就取到了0号和-1号票。

出现了上述情况怎样改变呢,我们可以这样做:当一个线程要使用火车票这个资源时,我们就交给它一把锁,等它把事情做完后在把锁给另一个要用这个资源的线程。这样就不会出现上述情况。 实现这个锁的功能就需要用到synchronized这个关键字。

synchronized这个关键字有两种用法1、放方法名前形成同步方法;2、放在块前构成同步块。

1、使用同步方法将上面的例子该为:

[java] view plain copy
 
 print?
  1. package com.pakage.ThreadAndRunnable;  
  2.   
  3. public class Runnable_demo implements Runnable{  
  4.     private int ticket=10;  
  5.     public Runnable_demo(){       
  6.     }  
  7.     @Override  
  8.     public void run() {  
  9.         for(int i=0;i<20;i++){  
  10.                 if(this.ticket>0){  
  11.                     //休眠1s秒中,为了使效果更明显,否则可能出不了效果  
  12.                     try {  
  13.                         Thread.sleep(1000);  
  14.                     } catch (Exception e) {  
  15.                         e.printStackTrace();  
  16.                     }  
  17.                     this.sale();  
  18.                 }  
  19.               
  20.         }  
  21.     }  
  22.       
  23.     public synchronized void sale(){  
  24.         if(this.ticket>0){  
  25.             System.out.println(Thread.currentThread().getName()+"号窗口卖出:"+this.ticket--+"号票");  
  26.         }  
  27.     }  
  28.       
  29.      public static void main(String args[]){  
  30.          Runnable_demo demo=new Runnable_demo();  
  31.          //基于火车票创建三个窗口  
  32.          new Thread(demo,"a").start();  
  33.          new Thread(demo,"b").start();  
  34.          new Thread(demo,"c").start();  
  35.      }  
  36.       
  37. }  

程序的输出结果为:

2、使用同步块修改上面的例子:

[java] view plain copy
 
 print?
  1. package com.pakage.ThreadAndRunnable;  
  2.   
  3. public class Runnable_demo implements Runnable{  
  4.     private int ticket=10;  
  5.     public Runnable_demo(){       
  6.     }  
  7.     @Override  
  8.     public void run() {  
  9.         for(int i=0;i<20;i++){  
  10.             <span style="color:#ff0000">synchronized</span>(this){  
  11.                 if(this.ticket>0){  
  12.                     //休眠1s秒中,为了使效果更明显,否则可能出不了效果  
  13.                     try {  
  14.                         Thread.sleep(1000);  
  15.                     } catch (Exception e) {  
  16.                         e.printStackTrace();  
  17.                     }  
  18.                     System.out.println(Thread.currentThread().getName()+"号窗口卖出:"+this.ticket--+"号票");  
  19.                 }  
  20.             }  
  21.               
  22.         }  
  23.     }  
  24.       
  25.      public static void main(String args[]){  
  26.          Runnable_demo demo=new Runnable_demo();  
  27.          //基于火车票创建三个窗口  
  28.          new Thread(demo,"a").start();  
  29.          new Thread(demo,"b").start();  
  30.          new Thread(demo,"c").start();  
  31.      }  
  32.       
  33. }  

程序的输出结果:

分享到:
评论

相关推荐

    Java 同步锁 wait notify 学习心得

    ### Java同步锁原理 在Java中,`synchronized`关键字用于实现线程同步,即确保同一时刻只有一个线程可以访问特定的代码块或方法。这种机制通过内部维护一个锁来实现,每个对象都有一个内置锁,这个锁可以被任何拥有...

    java锁机制Synchronizedjava锁机制Synchronized

    Java 锁机制 Synchronized 是 Java 语言中的一种同步机制,用于解决多线程并发访问共享资源时可能出现的一些问题。 Java 锁机制 Synchronized 的概念 在 Java 中,每个对象都可以被看作是一个大房子,其中有多个...

    Java 同步锁(synchronized)详解及实例

    Java中的同步锁,即`synchronized`关键字,是Java多线程编程中用于解决并发问题的重要机制。它确保了对共享资源的互斥访问,防止数据的不一致性。当我们有多线程环境并涉及到共享数据时,可能会出现竞态条件,就像...

    java同步synchronized关键字用法示例

    Java中的`synchronized`关键字是多线程编程中的一个重要概念,用于控制并发访问共享资源时的同步机制。在Java中,当多个线程试图同时访问和修改同一块代码或数据时,可能会导致数据不一致的问题。为了解决这个问题,...

    详细解读java同步之synchronized解析

    【Java同步之synchronized解析】 Java中的`synchronized`关键字是实现多线程同步的重要机制,它确保了在并发环境中对共享资源的访问是线程安全的。以下是对`synchronized`的详细解读: ### 1. synchronized的特性 ...

    支持10000同步锁,Spring Boot,Java

    文件名`java_demo_synchronized`可能包含的是关于Java同步锁的示例代码,可以从中学习如何在实际项目中应用同步锁策略。通过深入理解同步锁的工作原理和优化技巧,我们可以构建出高效、高并发的Spring Boot应用程序...

    基于Java synchronized同步锁实现线程交互.pdf

    "基于Java synchronized同步锁实现线程交互" Java多线程能够提高CPU利用效率,但也容易造成线程不安全、线程死锁等问题。Java synchronized同步锁可以保证同一时刻只有一个线程操作同一资源,使用wait()、notify()...

    java-syn.zip_Java syn_Java syn锁_java同步锁syn_java锁 syn_syn同步事务锁

    Java 同步锁是Java多线程编程中的关键概念,用于确保多个线程在访问共享资源时能够有序、安全地进行。在这个主题中,我们将详细探讨Java中的同步机制,包括同步方法、同步代码块、synchronized关键字以及其背后的...

    java中synchronized用法

    Synchronized 是 Java 语言中用于解决多线程共享数据同步问题的关键字。它可以作为函数的修饰符,也可以作为函数内的语句,用于实现同步方法和同步语句块。在 Java 中,synchronized 关键字可以作用于 instance 变量...

    java 多线程synchronized互斥锁demo

    总结来说,Java中的`synchronized`关键字是实现线程同步的关键,它通过互斥锁确保对共享资源的访问是线程安全的。在多线程编程中,合理使用`synchronized`可以有效避免竞态条件,保证程序的正确性和稳定性。对于...

    Java线程及同步(synchronized)样例代码

    - **同步锁的选择**:使用了一个名为`threadCounterLock`的静态变量作为锁对象,确保每次只有一个线程能进入`synchronized`代码块。 - **循环和休眠处理**:在`run`方法中,线程会持续运行直到达到预设的时间点(30...

    java 偏向锁、轻量级锁及重量级锁synchronized原理.docx

    总的来说,Java的`synchronized`通过对象头的Mark Word和Monitor对象实现了线程安全的同步机制,同时引入了偏向锁、轻量级锁和自旋锁等优化手段,以平衡性能和线程安全性。理解这些锁的工作原理对于编写高性能的并发...

    java里面synchronized用法.doc

    Java 中的 synchronized 用法详解 Java 中的 synchronized 关键字是用于解决多线程并发问题的重要工具之一。它可以被用于方法、代码块和变量上,以实现对共享资源的互斥访问控制。本文将对 Java 中的 synchronized ...

    [JAVA][synchronized的使用]

    在Java编程语言中,`synchronized`关键字是一个至关重要的概念,它主要用于实现线程同步,以确保多线程环境下的数据一致性与安全性。本篇文章将深入探讨`synchronized`的使用,包括其基本原理、使用方式以及实际应用...

    java Thread & synchronized & concurrent 线程、同步、并发

    在Java编程语言中,线程(Thread)、同步(synchronized)和并发(Concurrency)是核心概念,它们在多任务处理和高效系统设计中扮演着重要角色。本文将深入探讨这三个主题,以及它们如何相互作用以确保程序的正确性...

    java的线程同步机制synchronized关键字的理解_.docx

    Java 线程同步机制中 synchronized 关键字的理解 Java 的线程同步机制是为了解决多个线程共享同一片存储空间所带来的访问冲突问题。其中,synchronized 关键字是 Java 语言中解决这种冲突的重要机制。 ...

    解析Java编程之Synchronized锁住的对象

    在Java编程中,synchronized关键字是用于同步的关键字,它可以用于锁住一个对象,以实现线程同步。但是,在使用synchronized关键字时,需要了解锁住的到底是哪个对象,否则可能出现问题。 在Java中,synchronized...

    java同步锁的正确使用方法(必看篇)

    Java 同步锁的正确使用方法 Java 同步锁是 Java 编程语言中的一种机制,用于解决多线程环境下的线程安全问题。正确使用同步锁可以确保多线程环境下的数据安全和线程安全。 同步锁的分类 ------------ 同步锁有三...

    Java synchronized使用案例

    Java中的`synchronized`关键字是多线程编程中的一个重要概念,用于控制并发访问共享资源,以保证数据的一致性和完整性。这个关键词提供了互斥锁机制,防止多个线程同时执行同一段代码,确保了线程安全。 一、`...

Global site tag (gtag.js) - Google Analytics