2.1.4synchronized方法与锁对象
为了证明线程锁的是对象
测试
package com.cky.bean; /**
* Created by chenkaiyang on 2017/12/4.
*/
public class MyObject {
public void methodA () {
try {
System.out.println("begin methodA ThName=" +Thread.currentThread().getName());
Thread.sleep(5000);
System.out.println("end");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
package com.cky.thread; import com.cky.bean.MyObject; /**
* Created by chenkaiyang on 2017/12/4.
*/
public class ThreadA extends Thread{
private MyObject mo;
public ThreadA (MyObject mo) {
this.mo = mo;
}
@Override
public void run() {
super.run();
mo.methodA();
}
}
package com.cky.thread; import com.cky.bean.MyObject; /**
* Created by chenkaiyang on 2017/12/4.
*/
public class ThreadB extends Thread{
private MyObject mo;
public ThreadB (MyObject mo) {
this.mo = mo;
}
@Override
public void run() {
super.run();
mo.methodA();
}
}
package com.cky.test; import com.cky.bean.MyObject;
import com.cky.thread.ThreadA;
import com.cky.thread.ThreadB; /**
* Created by chenkaiyang on 2017/12/2.
*/
public class Test {
public static void main(String[] args){
MyObject myObject = new MyObject();
ThreadA threadA = new ThreadA(myObject);
threadA.setName("A");
ThreadB threadB = new ThreadB(myObject);
threadB.setName("B");
threadA.start();
threadB.start();
}
}
D:\it\jdk1.8\bin\java -Didea.launcher.port=7533 "-Didea.launcher.bin.path=D:\it\idea\IntelliJ IDEA 2016.3.3\bin" -Dfile.encoding=UTF-8 -classpath "D:\it\jdk1.8\jre\lib\charsets.jar;D:\it\jdk1.8\jre\lib\deploy.jar;D:\it\jdk1.8\jre\lib\ext\access-bridge-64.jar;D:\it\jdk1.8\jre\lib\ext\cldrdata.jar;D:\it\jdk1.8\jre\lib\ext\dnsns.jar;D:\it\jdk1.8\jre\lib\ext\jaccess.jar;D:\it\jdk1.8\jre\lib\ext\jfxrt.jar;D:\it\jdk1.8\jre\lib\ext\localedata.jar;D:\it\jdk1.8\jre\lib\ext\nashorn.jar;D:\it\jdk1.8\jre\lib\ext\sunec.jar;D:\it\jdk1.8\jre\lib\ext\sunjce_provider.jar;D:\it\jdk1.8\jre\lib\ext\sunmscapi.jar;D:\it\jdk1.8\jre\lib\ext\sunpkcs11.jar;D:\it\jdk1.8\jre\lib\ext\zipfs.jar;D:\it\jdk1.8\jre\lib\javaws.jar;D:\it\jdk1.8\jre\lib\jce.jar;D:\it\jdk1.8\jre\lib\jfr.jar;D:\it\jdk1.8\jre\lib\jfxswt.jar;D:\it\jdk1.8\jre\lib\jsse.jar;D:\it\jdk1.8\jre\lib\management-agent.jar;D:\it\jdk1.8\jre\lib\plugin.jar;D:\it\jdk1.8\jre\lib\resources.jar;D:\it\jdk1.8\jre\lib\rt.jar;F:\springboot\threaddemo\out\production\threaddemo;D:\it\idea\IntelliJ IDEA 2016.3.3\lib\idea_rt.jar" com.intellij.rt.execution.application.AppMain com.cky.test.Test
begin methodA ThName=A
begin methodA ThName=B
end
end
结果如上分析,代码调用是异步随机执行。
然后在方法中加同步关键字
package com.cky.bean; /**
* Created by chenkaiyang on 2017/12/4.
*/
public class MyObject {
synchronized public void methodA () {
try {
System.out.println("begin methodA ThName=" +Thread.currentThread().getName());
Thread.sleep(5000);
System.out.println("end");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
D:\it\jdk1.8\bin\java -Didea.launcher.port=7534 "-Didea.launcher.bin.path=D:\it\idea\IntelliJ IDEA 2016.3.3\bin" -Dfile.encoding=UTF-8 -classpath "D:\it\jdk1.8\jre\lib\charsets.jar;D:\it\jdk1.8\jre\lib\deploy.jar;D:\it\jdk1.8\jre\lib\ext\access-bridge-64.jar;D:\it\jdk1.8\jre\lib\ext\cldrdata.jar;D:\it\jdk1.8\jre\lib\ext\dnsns.jar;D:\it\jdk1.8\jre\lib\ext\jaccess.jar;D:\it\jdk1.8\jre\lib\ext\jfxrt.jar;D:\it\jdk1.8\jre\lib\ext\localedata.jar;D:\it\jdk1.8\jre\lib\ext\nashorn.jar;D:\it\jdk1.8\jre\lib\ext\sunec.jar;D:\it\jdk1.8\jre\lib\ext\sunjce_provider.jar;D:\it\jdk1.8\jre\lib\ext\sunmscapi.jar;D:\it\jdk1.8\jre\lib\ext\sunpkcs11.jar;D:\it\jdk1.8\jre\lib\ext\zipfs.jar;D:\it\jdk1.8\jre\lib\javaws.jar;D:\it\jdk1.8\jre\lib\jce.jar;D:\it\jdk1.8\jre\lib\jfr.jar;D:\it\jdk1.8\jre\lib\jfxswt.jar;D:\it\jdk1.8\jre\lib\jsse.jar;D:\it\jdk1.8\jre\lib\management-agent.jar;D:\it\jdk1.8\jre\lib\plugin.jar;D:\it\jdk1.8\jre\lib\resources.jar;D:\it\jdk1.8\jre\lib\rt.jar;F:\springboot\threaddemo\out\production\threaddemo;D:\it\idea\IntelliJ IDEA 2016.3.3\lib\idea_rt.jar" com.intellij.rt.execution.application.AppMain com.cky.test.Test
begin methodA ThName=A
end
begin methodA ThName=B
end
结果分析:
调用关键字synchronized声明的方法一定是排队运行的,只有共享的资源才需要同步,如果不是共享的资源,根本没有必要同步。
那如果其他的方法被调用会有什么效果。
测试
继续更改MyObject
package com.cky.bean; /**
* Created by chenkaiyang on 2017/12/4.
*/
public class MyObject {
synchronized public void methodA () {
try {
System.out.println("begin methodA ThName=" +Thread.currentThread().getName());
Thread.sleep(5000);
System.out.println("end");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public void methodB() {
try {
System.out.println("begin methodB ThName=" +Thread.currentThread().getName());
Thread.sleep(5000);
System.out.println("end");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
package com.cky.thread; import com.cky.bean.MyObject; /**
* Created by chenkaiyang on 2017/12/4.
*/
public class ThreadA extends Thread{
private MyObject mo;
public ThreadA (MyObject mo) {
this.mo = mo;
}
@Override
public void run() {
super.run();
mo.methodA();
}
}
package com.cky.thread; import com.cky.bean.MyObject; /**
* Created by chenkaiyang on 2017/12/4.
*/
public class ThreadB extends Thread{
private MyObject mo;
public ThreadB (MyObject mo) {
this.mo = mo;
}
@Override
public void run() {
super.run();
mo.methodB();
}
}
package com.cky.test; import com.cky.bean.MyObject;
import com.cky.thread.ThreadA;
import com.cky.thread.ThreadB; /**
* Created by chenkaiyang on 2017/12/2.
*/
public class Test {
public static void main(String[] args){
MyObject myObject = new MyObject();
ThreadA threadA = new ThreadA(myObject);
threadA.setName("A");
ThreadB threadB = new ThreadB(myObject);
threadB.setName("B");
threadA.start();
threadB.start();
}
}
D:\it\jdk1.8\bin\java -Didea.launcher.port=7536 "-Didea.launcher.bin.path=D:\it\idea\IntelliJ IDEA 2016.3.3\bin" -Dfile.encoding=UTF-8 -classpath "D:\it\jdk1.8\jre\lib\charsets.jar;D:\it\jdk1.8\jre\lib\deploy.jar;D:\it\jdk1.8\jre\lib\ext\access-bridge-64.jar;D:\it\jdk1.8\jre\lib\ext\cldrdata.jar;D:\it\jdk1.8\jre\lib\ext\dnsns.jar;D:\it\jdk1.8\jre\lib\ext\jaccess.jar;D:\it\jdk1.8\jre\lib\ext\jfxrt.jar;D:\it\jdk1.8\jre\lib\ext\localedata.jar;D:\it\jdk1.8\jre\lib\ext\nashorn.jar;D:\it\jdk1.8\jre\lib\ext\sunec.jar;D:\it\jdk1.8\jre\lib\ext\sunjce_provider.jar;D:\it\jdk1.8\jre\lib\ext\sunmscapi.jar;D:\it\jdk1.8\jre\lib\ext\sunpkcs11.jar;D:\it\jdk1.8\jre\lib\ext\zipfs.jar;D:\it\jdk1.8\jre\lib\javaws.jar;D:\it\jdk1.8\jre\lib\jce.jar;D:\it\jdk1.8\jre\lib\jfr.jar;D:\it\jdk1.8\jre\lib\jfxswt.jar;D:\it\jdk1.8\jre\lib\jsse.jar;D:\it\jdk1.8\jre\lib\management-agent.jar;D:\it\jdk1.8\jre\lib\plugin.jar;D:\it\jdk1.8\jre\lib\resources.jar;D:\it\jdk1.8\jre\lib\rt.jar;F:\springboot\threaddemo\out\production\threaddemo;D:\it\idea\IntelliJ IDEA 2016.3.3\lib\idea_rt.jar" com.intellij.rt.execution.application.AppMain com.cky.test.Test
begin methodA ThName=A
begin methodB ThName=B
end
end
结果分析:虽然线程A先持有object对象的锁,但是线程B完全可以异步调用非synchronized类型的方法。
继续再methodB方法上加上synchronized
package com.cky.bean; /**
* Created by chenkaiyang on 2017/12/4.
*/
public class MyObject {
synchronized public void methodA () {
try {
System.out.println("begin methodA ThName=" +Thread.currentThread().getName());
Thread.sleep(5000);
System.out.println("end");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
synchronized public void methodB() {
try {
System.out.println("begin methodB ThName=" +Thread.currentThread().getName());
Thread.sleep(5000);
System.out.println("end");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
D:\it\jdk1.8\bin\java -Didea.launcher.port=7537 "-Didea.launcher.bin.path=D:\it\idea\IntelliJ IDEA 2016.3.3\bin" -Dfile.encoding=UTF-8 -classpath "D:\it\jdk1.8\jre\lib\charsets.jar;D:\it\jdk1.8\jre\lib\deploy.jar;D:\it\jdk1.8\jre\lib\ext\access-bridge-64.jar;D:\it\jdk1.8\jre\lib\ext\cldrdata.jar;D:\it\jdk1.8\jre\lib\ext\dnsns.jar;D:\it\jdk1.8\jre\lib\ext\jaccess.jar;D:\it\jdk1.8\jre\lib\ext\jfxrt.jar;D:\it\jdk1.8\jre\lib\ext\localedata.jar;D:\it\jdk1.8\jre\lib\ext\nashorn.jar;D:\it\jdk1.8\jre\lib\ext\sunec.jar;D:\it\jdk1.8\jre\lib\ext\sunjce_provider.jar;D:\it\jdk1.8\jre\lib\ext\sunmscapi.jar;D:\it\jdk1.8\jre\lib\ext\sunpkcs11.jar;D:\it\jdk1.8\jre\lib\ext\zipfs.jar;D:\it\jdk1.8\jre\lib\javaws.jar;D:\it\jdk1.8\jre\lib\jce.jar;D:\it\jdk1.8\jre\lib\jfr.jar;D:\it\jdk1.8\jre\lib\jfxswt.jar;D:\it\jdk1.8\jre\lib\jsse.jar;D:\it\jdk1.8\jre\lib\management-agent.jar;D:\it\jdk1.8\jre\lib\plugin.jar;D:\it\jdk1.8\jre\lib\resources.jar;D:\it\jdk1.8\jre\lib\rt.jar;F:\springboot\threaddemo\out\production\threaddemo;D:\it\idea\IntelliJ IDEA 2016.3.3\lib\idea_rt.jar" com.intellij.rt.execution.application.AppMain com.cky.test.Test
begin methodB ThName=B
end
begin methodA ThName=A
end Process finished with exit code 0
结果分析:
1)A线程先持有对象锁,B线程可以异步方法调用object对象中非同步的方法
2)A线程先持有对象锁,B线程此时如果想要调用B线程中其他的同步方法,则需要等待A线程释放才行
2.1.4synchronized方法与锁对象的更多相关文章
- 【翻译十八】java-并发之锁对象
Lock Objects Synchronized code relies on a simple kind of reentrant lock. This kind of lock is easy ...
- 锁对象Lock
Lock 实现提供了比使用synchronized 方法和语句可获得的更广泛的锁定操作,它能以更优雅的方式处理线程同步问题: public class LockTest { publicstaticv ...
- python 全栈开发,Day42(Thread类的其他方法,同步锁,死锁与递归锁,信号量,事件,条件,定时器,队列,Python标准模块--concurrent.futures)
昨日内容回顾 线程什么是线程?线程是cpu调度的最小单位进程是资源分配的最小单位 进程和线程是什么关系? 线程是在进程中的 一个执行单位 多进程 本质上开启的这个进程里就有一个线程 多线程 单纯的在当 ...
- 锁对象-Lock: 同步问题更完美的处理方式 (ReentrantReadWriteLock读写锁的使用/源码分析)
Lock是java.util.concurrent.locks包下的接口,Lock 实现提供了比使用synchronized 方法和语句可获得的更广泛的锁定操作,它能以更优雅的方式处理线程同步问题,我 ...
- wait() ,notify() ,notifyAll(),synchronized 和同步方法锁,对象锁的联系,关系,区别;
一直不明白一个问题,因为在书上关于生产者和消费者的例子里看到一段这样的代码,估计很多人都和我一样迷惑 public synchronized void set(String name, String ...
- java锁对象
在Java5中,专门提供了锁对象,利用锁可以方便的实现资源的封锁,用来控制对竞争资源并发访问的控制,这些内容主要集中在java.util.concurrent.locks 包下面,里面有三个重要的接口 ...
- SAP 锁对象 基本概念与基本操作 SE11
一.SAP为什么要设置锁: 1,保持数据的一致性 假设几个用户要訪问相同的资源,须要找到一种同步訪问的方法去保持数据的一致性.比方说,在航班预订系统中,须要检查还有没有空座位,当检 ...
- Java 学习笔记之 Synchronized锁对象
Synchronized锁对象: Synchronized取得的锁都是对象锁,而不是把一段代码或方法当作锁,哪个线程执行带synchronized关键字的方法,哪个线程就持有该方法所属对象的锁,那么其 ...
- 锁对象Lock-同步问题更完美的处理方式
Lock是java.util.concurrent.locks包下的接口,Lock 实现提供了比使用synchronized 方法和语句可获得的更广泛的锁定操作,它能以更优雅的方式处理线程同步问题,我 ...
随机推荐
- 在textarea中鼠标指定的位置插入字符或表情
有些时候我们已经在textarea中输入了一些字符,然后想在鼠标指定的位置插入表情或者字符,这就需要用到jquery的一个小插件了. 代码如下: (function ($) { $.fn.extend ...
- oracle 数据库密码过期
查询密码过期策略 SELECT * FROM dba_profiles s WHERE s.profile='DEFAULT' AND resource_name='PASSWORD_LIFE_TIM ...
- C# 获取 存储过程 返回值
C#获取存储过程的返回值,这一方法,总是容易忘,今天给贴出来,以方便下次使用 存储过程: CREATE PROCEDURE [dbo].[Proc_GetInfo] ), ) out ...
- spring batch遇到的一些问题
1.Spring Batch - A job instance already exists: JobInstanceAlreadyCompleteException 这是因为JobParameter ...
- django POST表单的使用
环境如下:django 1.7.8 版本. 1.在POST表单的时候会出现这个错误提示. 禁止访问 (403) CSRF验证失败. 相应中断. Help Reason given for failur ...
- MySQL学习笔记-大纲
软件程序性能测试在之前<品味性能之道>系列中已经大量提到,讲解了很多测试方法.测试观念.测试思想等等.最近准备深入MySQL进行学习并总结.分别查阅<MySQL性能调优与架构设计&g ...
- gcc产生类型转换告警
问题背景: 看 https://www.cnblogs.com/sinaxyz/p/4525208.html 这个篇blog时候,发现在应用层代码中,函数 int open_netlink() 中,有 ...
- RecyclerView错误
1. java.lang.NoClassDefFoundError: android.support.v7.widget.RecyclerView 这个错误真TM见鬼,明明jar包里面就有这个类,工程 ...
- install virtualenv
$ [sudo] pip install virtualenv $ mkdir ~/envs $ virtualenv ~/envs/lsbaws/ $ cd ~/envs/lsbaws/ $ ls ...
- C#调用开源图像识别类库tessnet2
首先下载tessnet2_32.dll及相关语言包,将dll加入引用 private tessnet2.Tesseract ocr = new tessnet2.Tesseract();//声明一个O ...