- 浏览: 201317 次
- 性别:
- 来自: 哈尔滨
文章分类
- 全部博客 (267)
- java.lang (8)
- 问题汇总 (21)
- 异常记录 (20)
- 功能实现 (19)
- 面试总结 (25)
- 技巧总结 (8)
- 常用代码 (4)
- 编程习惯 (3)
- 编码规则 (3)
- java.util (10)
- java.io (1)
- JavaWeb (9)
- MySQL (16)
- SVN (3)
- MyBatis (11)
- Velocity (7)
- 其他知识 (10)
- 人生哲理 (1)
- 人生故事 (1)
- 自我感悟 (1)
- shiro (3)
- 基础知识 (0)
- 问题总结 (1)
- Spring 标签 (1)
- Spring (3)
- 点滴生活 (1)
- DOS (1)
- CAS (4)
- Linux (9)
- Storm (6)
- Shell (1)
- regex (1)
- Collection (4)
- poi (1)
- 经典语句 (1)
- NIO (5)
- concurrent (14)
- RPC (1)
- zookeeper (3)
- 待整理 (2)
- Hadoop (9)
- RabbitMq (2)
- flume (1)
- hive (7)
- hbase (4)
- kafka (1)
- scala (1)
- GC (0)
- java.util.concurrent.atomic (1)
- java.lang.ref (6)
- JVM (2)
- algorithm (1)
- conception (1)
- java key word (1)
- sun.misc (1)
最新评论
Synchronized
一、锁重入
1.概念
关键字 synchronized 拥有锁重入功能,也就是在使用 synchronized 时,当一个线程得到了一个对象的锁后,再次请求此对象时可以再次得到该对象的锁。
2.示例
三个方法,依次调用,获取 第一个方法的锁,执行第二个方法时同样可以获取锁
package com.study.current.thread.day01; /** * 锁重入的机制 * 在获取 m1 的锁后获取 m2 的锁 */ public class SynchronizedDubo1 extends Thread { public synchronized void method1(){ System.out.println("method1"); method2(); } public synchronized void method2(){ System.out.println("method2"); method3(); } public synchronized void method3(){ System.out.println("method3"); } /** * @param args */ public static void main(String[] args) { final SynchronizedDubo1 thread = new SynchronizedDubo1(); Thread t = new Thread(new Runnable() { public void run() { thread.method1(); } }); t.start(); } }
二、父子类
父子类间继承时,使用synchronized 保证线程安全
package com.study.current.thread.day01; /** * 父子关系调用 */ public class SynchronizedDubo2 extends Thread { static class Main{ public int i = 10 ; public synchronized void operationSup(){ i -- ; System.out.println("Main i : "+i); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } } } static class SubMain extends Main{ public synchronized void operationSub(){ while(i> 0){ i -- ; System.out.println("SubMain i : "+i); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } this.operationSup(); } } } /** * @param args */ public static void main(String[] args) { Thread thread = new Thread(new Runnable() { public void run() { SubMain syn = new SubMain(); syn.operationSub(); } }); thread.start(); } }
三、异常
当发生异常时,或中断运行(异常数据对后续功能有影响),或继续运行但保存错误数据的日志
package com.study.current.thread.day01; public class SynchronizedException extends Thread { public int count = 0 ; /** * 注意此处的捕获异常,级别为 Exception 即可以捕获此时的两种 Exception * 执行结果:出现异常,但程序依然在运行 */ public synchronized void operation(){ while(true){ count ++ ; try { Thread.sleep(1000); System.out.println(Thread.currentThread().getName()+" count : "+count); if(count == 10){ System.out.println(Integer.valueOf("a")); } } catch (Exception e) { e.printStackTrace(); System.out.println("log log 10 exception"); } } } /** * @param args */ public static void main(String[] args) { final SynchronizedException exc = new SynchronizedException(); Thread t = new Thread(new Runnable() { public void run() { exc.operation(); } },"t1"); t.start(); } }
四、锁种类
使用 synchronized 声明的方法在某些情况下是由弊端的,比如A线程调用同步的方法执行一个很长时间的任务,那么B线程就必须等待比较长的时间才能执行,这样的情况下可以使用 synchronized 代码块去优化代码执行时间,即减小锁的粒度
锁:
当前对象作为锁
类作为锁
任意对象作为锁
package com.study.current.thread.day01; /** * 锁对象 * 1.当前对象锁 * 2.类锁 * 3.任意对象锁 */ public class ObjectLock extends Thread { public void method1(){ synchronized (this) { // 对象锁,this 指代当前对象 System.out.println("method1"); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } } } public void method2(){ synchronized (ObjectLock.class) { System.out.println("method2"); // 类锁 try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } } } private Object ojt = new Object(); public void method3(){ synchronized (ojt) { // 任意对象锁 System.out.println("method3"); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } } } /** * @param args */ public static void main(String[] args) { final ObjectLock lock = new ObjectLock(); Thread t1 = new Thread(new Runnable() { public void run() { lock.method1(); } }); Thread t2 = new Thread(new Runnable() { public void run() { lock.method2(); } }); Thread t3 = new Thread(new Runnable() { public void run() { lock.method3(); } }); t1.start(); t2.start(); t3.start(); } }
五、String 常量不能作为锁
String 常量作为锁,会造成死循环,锁失效
package com.study.current.thread.day01; /** * String 常量作为锁,会出现死循环 */ public class StringLock { public void method(){ /** * 使用字符串常量当做锁,会出现死循环,即当前的运行结果总是 t1 的线程 * 字符串常量只有一个引用 * 解决: * 可以替换为 new String("") */ synchronized ("字符串常量") { System.out.println("method"); try { while(true){ System.out.println(Thread.currentThread().getName()+" start"); Thread.sleep(1000); System.out.println(Thread.currentThread().getName()+" end"); } } catch (InterruptedException e) { e.printStackTrace(); } } } /** * @param args */ public static void main(String[] args) { final StringLock stringLock = new StringLock(); Thread t1 = new Thread(new Runnable() { public void run() { stringLock.method(); } },"t1"); Thread t2 = new Thread(new Runnable() { public void run() { stringLock.method(); } },"t2"); t1.start(); t2.start(); } }
六、不要试图改变锁
改变当前运行的锁,会造成锁的失效
package com.study.current.thread.day01; /** * 不要修改锁对象 * 会导致锁失效 * 开始几个线程争夺 a 锁, 第一个线程 获取 a ,并把 锁改为 b ,第二个线程则无需等待 a 锁的释放,直接获取 b 锁, * 就不能起到锁的作用 */ public class ChangeLock { private String lock = "abc"; public void changeLock(){ synchronized (lock) { System.out.println(Thread.currentThread().getName() + " start"); try { lock = "bcd" ; Thread.sleep(2000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println(Thread.currentThread().getName()+" end"); } } /** * @param args */ public static void main(String[] args) { final ChangeLock lock = new ChangeLock(); Thread t1 = new Thread(new Runnable() { public void run() { lock.changeLock(); } },"t1"); Thread t2 = new Thread(new Runnable() { public void run() { lock.changeLock(); } },"t2"); t1.start(); t2.start(); } }
七、对象锁,其属性值得改变不影响锁的使用
锁对象的改变问题,当使用一个对象进行加锁的时候,要注意对象本身发生改变的时候,那么持有的锁就不同。
如果对象本身不发生改变,那么依然是同步的,即使是对象的属性发生了改变。
package com.study.current.thread.day01; /** * 对象的属性值的变化,不影响锁的使用 */ public class ModifyLock { private String name ; private String pass ; public synchronized void changeAttribute(String name,String pass){ System.out.println(Thread.currentThread().getName() + " start"); this.setName(name); this.setPass(pass); System.out.println(Thread.currentThread().getName() + " modify name:"+name+" pass:"+pass); try { Thread.sleep(2000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println(Thread.currentThread().getName() + " end"); } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getPass() { return pass; } public void setPass(String pass) { this.pass = pass; } /** * @param args */ public static void main(String[] args) { final ModifyLock lock = new ModifyLock(); Thread t1 = new Thread(new Runnable() { public void run() { lock.changeAttribute("zhangsan", "1111"); } },"t1"); Thread t2 = new Thread(new Runnable() { public void run() { lock.changeAttribute("lisi", "2222"); } },"t2"); t1.start(); t2.start(); } }
发表评论
-
Queue
2017-08-21 21:26 425Queue 一、Queue ConcurrentLink ... -
容器集合
2017-08-19 18:18 370容器 一、同步类容器 1.概念 同步类容器都是线程安全的, ... -
多线程-单例模式
2017-08-17 20:59 327单例模式 一、概念 饿汉模式、懒汉模式 二、示例 ... -
ThreadLocal
2017-08-17 21:02 273ThreadLocal 一、概念 ThreadLocal ... -
线程间通信 wait notify
2017-08-15 22:12 401线程间通信 一、通信 线程通信概念:线程是操作系统中独立的 ... -
Volatile
2017-08-14 22:11 370Volatile 一、概念 volatile : 作用是保 ... -
脏读(数据)
2017-08-13 17:47 414脏读 一、概念 数据写入与数据读出不一致 原因:未对写入 ... -
线程安全
2017-08-12 20:55 354线程安全 一、线程安全 线程安全概念: 当多个线程访问某一 ... -
Lock
2017-04-19 22:39 477Lock 一、 1. public class ... -
ExecutorService
2017-04-17 22:32 760ExecutorService 1. 线程池的意义: 维护一 ... -
CountDownLatch
2017-04-16 12:38 413一、CountDownLatch 一个同步辅助类,在完成一组 ... -
ConcurrentHashMap
2017-04-16 11:01 318一、 hashMap线程不安全hashTable线程安全,对 ... -
BlockingQueue
2017-04-15 22:40 516参考内容:http://tool.oschina.net/ap ...
相关推荐
"Java 中 synchronized 用法详解" Synchronized 是 Java 语言中用于解决多线程共享数据同步问题的关键字。它可以作为函数的修饰符,也可以作为函数内的语句,用于实现同步方法和同步语句块。在 Java 中,...
你还在用synchronized?线程安全相关知识深入剖析
synchronized关键字可以作为函数的修饰符,也可作为函数内的语句,也就是平时说的同步方法和同步语句块。如果 再细的分类,synchronized可作用于instance变量、object reference(对象引用)、static函数和class ...
java锁机制Synchronized java锁机制Synchronized java锁机制Synchronized java锁机制Synchronized
java synchronized的一些小实验,对帮助理解synchronized的使用有一定的帮助。
java里面synchronized用法
Synchronized锁在Spring事务管理下,导致线程不安全。
synchronized的几种示例研究,方法加锁,代码块加锁(this和对象)以及静态方法加锁的示例和效果。基本上包含了synchronized的几种常用的方式。
java多线程中synchronized关键字的用法 解压密码 www.jiangyea.com
This document specifies the third version of the Synchronized Multimedia Integration Language (SMIL, pronounced "smile"). SMIL 3.0 has the following design goals: ● Define an XML-based language...
volatile与synchronized的区别,锁提供了两种主要特性:互斥(mutual exclusion) 和可见性(visibility)
synchronized 测试案例,同步一个对象或者多个对象的案例均有,还有成功和失败案例的对比
我自己的博客所附带的案例源码,我的博客标题名称是"synchronized并发讲解",关注我等待跟多更新
有需要2014版本之前的Synchronized 6-Pulse Generator元器件,提供slx文件下载,直接复制过去即可使用。Matlab表示:如果您的旧版型号包含 同步6脉冲发生器模块,它们将继续工作。但是,为获得最佳性能,请在新型号...
java同步synchronized关键字用法示例
java多线程编程核心技术synchronized实例大全,同步方法,同步语句块,类锁,对象锁全都用代码来展现出来
Synchronized关键字的用法
java中synchronized的使用,java中的锁锁的到底是什么?是括号里的代码块吗?肯定不是的;
synchronized关键字在java中的重要性 以及常用的方法 还有它的详解
java语言 并发编程 ReentrantLock与synchronized区别 详解