热门标签 | HotTags
当前位置:  开发笔记 > 人工智能 > 正文

深入分析JAVASynchronized关键字

这篇文章主要介绍了析JAVASynchronized关键字的相关知识,文中代码非常详细,帮助大家更好的理解和学习,感兴趣的朋友可以了解下

并发一致性的概念?

  是利用锁的机制来实现同步的,锁机制有如下两种特性:

    互斥性:即在同一时间只允许一个线程持有某个对象锁,通过这种特性来实现多线程中的协调机制,这样在同一时间只有一个线程对需同步的代码块(复合操作)进行访问。互斥性我们也往往称为操作的原子性。

    可见性:必须确保在锁被释放之前,对共享变量所做的修改,对于随后获得该锁的另一个线程是可见的(即在获得锁时应获得最新共享变量的值),否则另一个线程可能是在本地缓存的某个副本上继续操作从而引起不一致。

Synchronized的用法?

  1.同步方法

    同步非静态方法

/**
 * Synchronized关键字的用法
 * @author Administrator
 *
 */
public class SynchronizeDemo01 {

  /**
   * 修饰非静态方法
   * @Description: TODO
   * @returnType: void
   */
  public synchronized void accessResources1(){
    try {
      TimeUnit.SECONDS.sleep(2);
      System.out.println(Thread.currentThread().getName()+" is running!");
    } catch (InterruptedException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
  }

  public static void main(String[] args) {

    //非静态方法的测试
    SynchronizeDemo01 demo01 = new SynchronizeDemo01();
    for (int i = 0; i <5; i++) {
      new Thread(demo01::accessResources1).start();
    }

  }

}

     同步静态方法

/**
 * Synchronized关键字的用法
 * @author Administrator
 *
 */
public class SynchronizeDemo01 {
  /**
   * 修饰静态方法
   * @Description: TODO
   * @returnType: void
   */
  public synchronized static void accessResources0(){
    try {
      TimeUnit.SECONDS.sleep(2);
      System.out.println(Thread.currentThread().getName()+" is running!");
    } catch (InterruptedException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
  }

  public static void main(String[] args) {
    //静态方法的测试
    for(int i=0;i<5;i++){
      new Thread(SynchronizeDemo01::accessResources0).start();
    }

  }

}

  2.同步代码块

    代码块对象,获取对象锁,在 Java 中,每个对象都会有一个 monitor 对象,这个对象其实就是 Java 对象的锁,通常会被称为“内置锁”或“对象锁”。类的对象可以有多个,所以每个对象有其独立的对象锁,互不干扰。

/**
 * Synchronized关键字的用法
 * @author Administrator
 *
 */
public class SynchronizeDemo01 {

  /**
   * synchronized代码块(对象),this指的是当前对象
   * @Description: TODO
   * @returnType: void
   */
  public void accessResources2(){
    synchronized(this){
      try {
        TimeUnit.SECONDS.sleep(2);
        System.out.println(Thread.currentThread().getName()+" is running!");
      } catch (InterruptedException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
      }
    }
  }


  public static void main(String[] args) {
    //非静态方法的测试
    SynchronizeDemo01 demo01 = new SynchronizeDemo01();
    for (int i = 0; i <5; i++) {
      new Thread(demo01::accessResources2).start();
    }

  }

}

    代码块 (类.class),获取类锁,在 Java 中,针对每个类也有一个锁,可以称为“类锁”,类锁实际上是通过对象锁实现的,即类的 Class 对象锁。每个类只有一个 Class 对象,所以每个类只有一个类锁。

/**
 * Synchronized关键字的用法
 * @author Administrator
 *
 */
public class SynchronizeDemo01 {

  /**
   * synchronized代码块(类.class)
   * @Description: TODO
   * @returnType: void
   */
  public void accessResources3(){
    synchronized(SynchronizeDemo01.class){
      //有Class对象的所有的对象都共同使用这一个锁
      try {
        TimeUnit.SECONDS.sleep(2);
        System.out.println(Thread.currentThread().getName()+" is running!");
      } catch (InterruptedException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
      }
    }
  }
  public static void main(String[] args) {
    //非静态方法的测试
    SynchronizeDemo01 demo01 = new SynchronizeDemo01();
    for (int i = 0; i <5; i++) {
      new Thread(demo01::accessResources3).start();
    }

  }

}

Java对象的monitor对象的作用?

  1.当某一线程想要占有这个对象的时候,首先判断monitor 的计数器是不是0,如果是0表示还没有线程占有,这个时候线程可以占有这个对象,并且对这个对象的monitor+1;如果不为0,表示这个线程已经被其他线程占有,那么这个线程需要等待。当线程释放占有权的时候,monitor-1。

  2. 同一线程可以对同一对象进行多次加锁,+1,+1,重入性

Synchronized代码块的加锁机制?

  1.对代码块的加锁,通过反编译文件,发现在Monitorenter和Monitorexit中间是加锁的部分

  2.对方法的加锁,通过反编译文件,发现标有ACC_SYNCHRONIZED标识的为加锁方法

 Java虚拟机中几种锁的对比?

  无状态锁:没有加锁

  偏向锁:在对象第一次被某一线程占有的时候,会将“是否偏向锁”字段置为1,“锁标志位”记为01,写入线程号,当其他的线 程访问的时候,就会发生 竞争,如果竞争失败则升级为轻量级锁。偏向锁更加偏向第一次访问的线程获取锁成功。

     轻量级锁:线程有交替适用,互斥性不是很强,当偏向锁通过CAS算法获取锁失败,把锁标志位置为00。

  重量级锁:强互斥,锁标志位为10,等待时间长

以上就是深入分析JAVA Synchronized关键字的详细内容,更多关于JAVA Synchronized关键字的资料请关注其它相关文章!


推荐阅读
  • 计算机网络复习:第五章 网络层控制平面
    本文探讨了网络层的控制平面,包括转发和路由选择的基本原理。转发在数据平面上实现,通过配置路由器中的转发表完成;而路由选择则在控制平面上进行,涉及路由器中路由表的配置与更新。此外,文章还介绍了ICMP协议、两种控制平面的实现方法、路由选择算法及其分类等内容。 ... [详细]
  • 本文将介绍如何使用 Go 语言编写和运行一个简单的“Hello, World!”程序。内容涵盖开发环境配置、代码结构解析及执行步骤。 ... [详细]
  • 题目描述:给定n个半开区间[a, b),要求使用两个互不重叠的记录器,求最多可以记录多少个区间。解决方案采用贪心算法,通过排序和遍历实现最优解。 ... [详细]
  • 深入理解C++中的KMP算法:高效字符串匹配的利器
    本文详细介绍C++中实现KMP算法的方法,探讨其在字符串匹配问题上的优势。通过对比暴力匹配(BF)算法,展示KMP算法如何利用前缀表优化匹配过程,显著提升效率。 ... [详细]
  • 探讨一个显示数字的故障计算器,它支持两种操作:将当前数字乘以2或减去1。本文将详细介绍如何用最少的操作次数将初始值X转换为目标值Y。 ... [详细]
  • 本文详细介绍了Java编程语言中的核心概念和常见面试问题,包括集合类、数据结构、线程处理、Java虚拟机(JVM)、HTTP协议以及Git操作等方面的内容。通过深入分析每个主题,帮助读者更好地理解Java的关键特性和最佳实践。 ... [详细]
  • 本文探讨如何设计一个安全的加密和验证算法,确保生成的密码具有高随机性和低重复率,并提供相应的验证机制。 ... [详细]
  • 深入解析:手把手教你构建决策树算法
    本文详细介绍了机器学习中广泛应用的决策树算法,通过天气数据集的实例演示了ID3和CART算法的手动推导过程。文章长度约2000字,建议阅读时间5分钟。 ... [详细]
  • 在金融和会计领域,准确无误地填写票据和结算凭证至关重要。这些文件不仅是支付结算和现金收付的重要依据,还直接关系到交易的安全性和准确性。本文介绍了一种使用C语言实现小写金额转换为大写金额的方法,确保数据的标准化和规范化。 ... [详细]
  • 在给定的数组中,除了一个数字外,其他所有数字都是相同的。任务是找到这个唯一的不同数字。例如,findUniq([1, 1, 1, 2, 1, 1]) 返回 2,findUniq([0, 0, 0.55, 0, 0]) 返回 0.55。 ... [详细]
  • 本文探讨了卷积神经网络(CNN)中感受野的概念及其与锚框(anchor box)的关系。感受野定义了特征图上每个像素点对应的输入图像区域大小,而锚框则是在每个像素中心生成的多个不同尺寸和宽高比的边界框。两者在目标检测任务中起到关键作用。 ... [详细]
  • 网络攻防实战:从HTTP到HTTPS的演变
    本文通过一系列日记记录了从发现漏洞到逐步加强安全措施的过程,探讨了如何应对网络攻击并最终实现全面的安全防护。 ... [详细]
  • 本文深入探讨了Linux系统中网卡绑定(bonding)的七种工作模式。网卡绑定技术通过将多个物理网卡组合成一个逻辑网卡,实现网络冗余、带宽聚合和负载均衡,在生产环境中广泛应用。文章详细介绍了每种模式的特点、适用场景及配置方法。 ... [详细]
  • 本文探讨了如何在给定整数N的情况下,找到两个不同的整数a和b,使得它们的和最大,并且满足特定的数学条件。 ... [详细]
  • 深度学习理论解析与理解
    梯度方向指示函数值增加的方向,由各轴方向的偏导数综合而成,其模长表示函数值变化的速率。本文详细探讨了导数、偏导数、梯度等概念,并结合Softmax函数、卷积神经网络(CNN)中的卷积计算、权值共享及池化操作进行了深入分析。 ... [详细]
author-avatar
mobiledu2502882737
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有