synchronized修饰静态方法与实例方法
一、synchronized修饰实例方法:
synchronized修饰实例方法,实际上是对调用该方法的对象加锁。
场景1:同一实例对象在两个线程中分别调用该对象的两个同步实例方法
public class Car {public synchronized void runing1(Thread thread){System.out.println(thread.getName()+ " car1 得到锁");System.out.println("------ car1 is running ------");working();System.out.println(thread.getName()+ " car1 释放锁");System.out.println();}public synchronized void runing2(Thread thread){System.out.println(thread.getName()+ " car2 得到锁");System.out.println("------ car2 is running ------");working();System.out.println(thread.getName()+ " car2 释放锁");System.out.println();}public static void working(){try{Thread.sleep(1000);}catch(InterruptedException e){e.printStackTrace();}}
}
public class Test01 {public static void main(String[] args) {Car car = new Car();//线程1Thread t1 = new Thread(){@Overridepublic void run() {car.runing1(Thread.currentThread()); //同步实例方法1}};t1.start();//线程2Thread t2 = new Thread(){@Overridepublic void run() {car.runing2(Thread.currentThread()); //同步实例方法2}};t2.start();}
}
结果:两个线程依次执行,说明产生互斥,因为实例方法加锁针对的是实例对象,当前对象调用一个synchronized方法时,其他同步方法需要等待其执行结束并释放锁之后才能执行。
场景二:两个对象在两个线程中分别调用同一个同步实例方法
public class test02 {public static void main(String[] args) {Car car1 = new Car();Car car2 = new Car();//线程1 对象1Thread t1 = new Thread(){@Overridepublic void run() {car1.runing1(Thread.currentThread()); //同步实例方法1}};t1.start();//线程2 对象2Thread t2 = new Thread(){@Overridepublic void run() {car2.runing1(Thread.currentThread()); //同步实例方法1}};t2.start();}
}
结果 :两个线程同时进行,因为是两个对象,实例方法加锁针对的是实例对象,并不是方法,所以可以并发执行,不会互斥。
此外,同一个对象分别在两个线程中分别调用同步实例方法和非同步方法(未用synchronized修饰的方法),不会出现互斥,这里不再展示。synchronized关键字可以保证被它修饰的方法或者代码块在任意时刻只能有一个线程执行,而不会限制其他非synchronized方法。非synchronized方法不需要占有该对象,因此不会互斥。
synchronized修饰类方法:
synchronized修饰静态方法,实际上是对该类进行加锁,而不属于某个对象。
场景一:用类直接在两个线程中调用两个不同的同步静态方法
public class Car {public static synchronized void staticRuning1(Thread thread){System.out.println(thread.getName()+ " static car1 得到锁");System.out.println("------ static car1 is running ------");working();System.out.println(thread.getName()+ " static car1 释放锁");System.out.println();}public static synchronized void staticRuning2(Thread thread){System.out.println(thread.getName()+ " static car2 得到锁");System.out.println("------ static car2 is running ------");working();System.out.println(thread.getName()+ " static car2 释放锁");System.out.println();}public static void working(){try{Thread.sleep(1000);}catch(InterruptedException e){e.printStackTrace();}}
}
public class test02 {public static void main(String[] args) {//线程1 类Thread t1 = new Thread(){@Overridepublic void run() {Car.staticRuning1(Thread.currentThread()); //同步类方法1}};t1.start();//线程2 类Thread t2 = new Thread(){@Overridepublic void run() {Car.staticRuning2(Thread.currentThread()); //同步类方法2}};t2.start();}
}
结果:产生互斥,因为对静态方法加锁,实际上是对类加锁,类只有一个。因此当一个同步静态方法被访问时,该类已处于被锁状态。此时其他同步静态方法不能被访问(未用synchronized修饰的静态方法仍可以访问)
场景二:两个线程分别调用同步类方法和同步实例方法
public class test03 {public static void main(String[] args) {Car car = new Car();//线程1 实例对象Thread t1 = new Thread(){@Overridepublic void run() {car.runing1(Thread.currentThread()); //同步实例方法1}};t1.start();//线程2 类Thread t2 = new Thread(){@Overridepublic void run() {Car.staticRuning2(Thread.currentThread()); //同步类方法2 //面试中一个面试官问如果静态方法通过实例来调用,那锁的是实例还是类呢?//当然还是类了,这里可以把Car.staticRuning2改成car.staticRuning2,通过实例对象来调用静态方法//结果还是一样的。}};t2.start();}
}
结果:不会互斥,锁对象不同,一个是对实例对象加锁,一个对类加锁,这里直接调用Car类Car.staticRuning2(Thread.currentThread())
其实跟调用car对象 car.staticRuning2(Thread.currentThread())
效果一样,因为静态方法不属于某个实例,而属于类本身。
synchronized修饰静态方法与实例方法相关推荐
- java中synchronized修饰静态方法和非静态方法有什么区别?
Synchronized修饰非静态方法 Synchronized修饰非静态方法,实际上是对调用该方法的对象加锁,俗称"对象锁". Java中每个对象都有一个锁,并且是唯一的.假设分 ...
- 使用synchronized修饰静态方法和非静态方法有什么区别
前言 最近被问到了这个问题,第一次回答的也是很不好,在此参考网上答案进行整理记录.供大家学习参考. Synchronized修饰非静态方法 Synchronized修饰非静态方法,实际上是对调用该方法 ...
- java synchronized 静态_Java之Synchronized修饰实例方法和静态方法
一.Synchronized修饰实例方法,实际上是对调用该方法的对象加锁,俗称"对象锁" 情况一:同一个对象在两个线程中分别访问该对象的两个同步实例方法 结果:会产生互斥 原因 ...
- Java多线程--synchronized修饰普通方法和修饰静态方法的区别
初始化一个对象时,会自动生成一个与该对象对应的对象锁,被synchronized 修饰的方法就得依靠对象锁工作.当多线程同时访问某个被synchronized修饰的方法时,一旦某个进程抢得对象锁之后, ...
- synchronized修饰方法
文章目录 前言 一.Synchronized修饰非静态方法 二.Synchronized修饰静态方法 三.类锁和对象锁的访问是不冲突的 四.总结 前言 直接说结论: 1.Synchronized修饰非 ...
- java 内存 静态_Java内存的 静态方法和实例方法的区别及使用场景
注意:变量指基本数据类型非对象,局部变量不能被静态修饰 1.(静态)成员变量存放在data segment区(数据区),字符串常量也存放在该区 2.非静态变量,new出来的对象存放在堆内存,所有局部变 ...
- Java内存的一点理解, 静态方法和实例方法的区别及使用场景
注意:变量指基本数据类型非对象,局部变量不能被静态修饰 1.(静态)成员变量存放在data segment区(数据区),字符串常量也存放在该区 2.非静态变量,new出来的对象存放在堆内存,所有局部变 ...
- python通过对象不能调用类方法和静态方法_Python实例方法、类方法和静态方法
Python类的组成主要包含两个部分,类的属性和类的方法.类的属性是对数据的封装,这些数据是用来描述类所抽象的事物的特征:类的方法是用来表示对象的特定行为.Python的类的方法又可以进一步细分为三种 ...
- synchronized 修饰方法
今天看到看到一个有意识的问题.记录一下 public class Test {synchronized void SayHello1() {} } 问synchronized修饰的方法代码块会同步么? ...
最新文章
- ORACLE空值漫谈2
- 微软云计算 Windows Azure“腾云驾雾”
- 是否应该提供一个dao.insertIgnoreNull ? (像updateIgnoreNull一样)
- Maven - 基础入门与安装配置
- Tableau中的行级数据安全性——第2部分
- 精心整理 | R语言中文社区历史文章合集(作者篇)
- 华为服务器升腾芯片,华为公布昇腾910芯片架构细节:7nm+ EUV工艺、32核达芬奇...
- tibco rv java实例_基于python使用tibco ems代码实例
- thermal系列(4)-Thermal Core框架
- win8连接wifi成功但受限制_用于 手机热点或WIFI网络的IM143DTU使用手册
- java解释单片机按高位在前低位在后协议输出的数字
- 服务器nvme硬盘识别不了,解决部分主板无法识别NVMe协议的固态硬盘问题
- error while loading shared libraries: libnsl.so.1: cannot open shared object file: No such
- win7下制作ubuntu安装u盘
- 百度云 php api接口调用 签名计算
- 2019年第四季度书单
- 干货全拿走-用ExcelVBA做个股多模型交叉验证择时交易套利及回测系统
- 远程实习的实习证明上会注明是远程实习么?
- Javaswing+MySQL实现超市收银管理系统(含源码、包运行)
- mmap函数使用与实例详解