同步的实现当然是采用锁了,java中使用锁的两个基本工具是 synchronizedLock

==========================================

synchronized

java语言的关键字,当它用来修饰一个方法或者一个代码块的时候,能够保证在同一时刻最多只有一个线程执行该段代码。

一、当两个并发线程访问同一个对象object中的这个synchronized(this)同步代码块时,一个时间内只能有一个线程得到执行。另一个线程必须等待当前线程执行完这个代码块以后才能执行该代码块。

二、然而,当一个线程访问object的一个synchronized(this)同步代码块时,另一个线程仍然可以访问该object中的非synchronized(this)同步代码块。

三、尤其关键的是,当一个线程访问object的一个synchronized(this)同步代码块时,其他线程对object中所有其它synchronized(this)同步代码块的访问将被阻塞。

四、第三个例子同样适用其它同步代码块。也就是说,当一个线程访问object的一个synchronized(this)同步代码块时,它就获得了这个object的对象锁。结果,其它线程对该object对象所有同步代码部分的访问都被暂时阻塞。

五、synchronized 用在方法代码块上有什么区别呢?

synchronized 用在方法签名上(以test为例),当某个线程调用此方法时,会获取该实例的对象锁,方法未结束之前,其他线程只能去等待。当这个方法执行完时,才会释放对象锁。其他线程才有机会去抢占这把锁,去执行方法test,但是发生这一切的基础应当是所有线程使用的同一个对象实例,才能实现互斥的现象。否则synchronized关键字将失去意义。但是如果该方法为类方法,即其修饰符为static,那么synchronized 意味着某个调用此方法的线程当前会拥有该类的锁,只要该线程持续在当前方法内运行,其他线程依然无法获得方法的使用权!

六、当线程运行到该代码块内,就会拥有obj对象的对象锁,如果多个线程共享同一个Object对象,那么此时就会形成互斥!特别的,当obj == this时,表示当前调用该方法的实例对象。即

public void test() {

synchronized(this) {
// todo your code
}

}
此时,其效果等同于
public synchronized void test() {
// to do your code
}

使用synchronized代码块,可以只对需要同步的代码进行同步,这样可以大大的提高效率。
有关synchronized更详细解析,请参看以下博客:
http://www.cnblogs.com/GnagWang/archive/2011/02/27/1966606.html

===========================================

Lock

1、Lock 实现提供了比使用 synchronized 方法和语句可获得的更广泛的锁定操作。此实现允许更灵活的结构,可以具有差别很大的属性,可以支持多个相关的 Condition 对象。

2、锁是控制多个线程对共享资源进行访问的工具。通常,锁提供了对共享资源的独占访问。一次只能有一个线程获得锁,对共享资源的所有访问都需要首先获得锁。不过,某些锁可能允许对共享资源并发访问,如 ReadWriteLock 的读取锁。

3、synchronized 方法或语句的使用提供了对与每个对象相关的隐式监视器锁的访问,但却强制所有锁获取和释放均要出现在一个块结构中:当获取了多个锁时,它们必须以相反的顺序释放,且必须在与所有锁被获取时相同的词法范围内释放所有锁。

4、虽然 synchronized 方法和语句的范围机制使得使用监视器锁编程方便了很多,而且还帮助避免了很多涉及到锁的常见编程错误,但有时也需要以更为灵活的方式使用锁。例如,某些遍历并发访问的数据结果的算法要求使用 “hand-over-hand” 或 “chain locking”:获取节点 A 的锁,然后再获取节点 B 的锁,然后释放 A 并获取 C,然后释放 B 并获取 D,依此类推。Lock 接口的实现允许锁在不同的作用范围内获取和释放,并允许以任何顺序获取和释放多个锁,从而支持使用这种技术。

5、随着灵活性的增加,也带来了更多的责任。不使用块结构锁就失去了使用 synchronized 方法和语句时会出现的锁自动释放功能。在大多数情况下,应该使用以下语句:

 Lock l = ...; l.lock();try {// access the resource protected by this lock} finally {l.unlock();}

锁定和取消锁定出现在不同作用范围中时,必须谨慎地确保保持锁定时所执行的所有代码用 try-finally 或 try-catch 加以保护,以确保在必要时释放锁。

6、Lock 实现提供了使用 synchronized 方法和语句所没有的其他功能,包括提供了一个非块结构的获取锁尝试 (tryLock())、一个获取可中断锁的尝试 (lockInterruptibly()) 和一个获取超时失效锁的尝试 (tryLock(long, TimeUnit))。

7、Lock 类还可以提供与隐式监视器锁完全不同的行为和语义,如保证排序、非重入用法或死锁检测。如果某个实现提供了这样特殊的语义,则该实现必须对这些语义加以记录。

注意:

1、Lock 实例只是普通的对象,其本身可以在 synchronized 语句中作为目标使用。获取 Lock 实例的监视器锁与调用该实例的任何 lock() 方法没有特别的关系。为了避免混淆,建议除了在其自身的实现中之外,决不要以这种方式使用 Lock 实例。

2、除非另有说明,否则为任何参数传递 null 值都将导致抛出 NullPointerException。

3、ReentrantLock 与synchronized有相同的并发性和内存语义,还包含了中断锁等候和定时锁等候,意味着线程A如果先获得了对象obj的锁,那么线程B可以在等待指定时间内依然无法获取锁,那么就会自动放弃该锁。但是由于synchronized是在JVM层面实现的,因此系统可以监控锁的释放与否,而ReentrantLock使用代码实现的,系统无法自动释放锁,需要在代码中finally子句中显式释放锁lock.unlock();

相关实例请参看本人“线程协作”博客,链接如下:
http://blog.csdn.net/lmb55/article/details/46274165

总结:

各有千秋,在并发量比较小的情况下,使用synchronized是个不错的选择,但是在并发量比较高的情况下,其性能下降很严重,此时ReentrantLock是个不错的方案。

【Java线程】线程同步—synchronized Lock相关推荐

  1. Java线程的同步 - synchronized

    为什么要在线程里面使用同步 - synchronized 首先看个列子: 假设系统里面有5张票,有个卖票的系统,执行完,打印的结果是这样的: public class RunDemo05 implem ...

  2. 多线程和线程安全 同步代码 lock锁

     多线程:Thread Runnable 并发与并行 •并发:指两个或多个事件在同一个时间段内发生. •并行:指两个或多个事件在同一时刻发生(同时发生). 线程 是程序中的执行线程.Java 虚拟机允 ...

  3. python线程同步锁_[python] 线程间同步之Lock RLock

    为什么需要同步 同样举之前的例子,两个线程分别对同一个全局变量进行加减,得不到预期结果,代码如下: total = 0 def add(): global total for i in range(1 ...

  4. Java线程(二):线程同步synchronized和volatile

    上篇通 过一个简单的例子说明了线程安全与不安全,在例子中不安全的情况下输出的结果恰好是逐个递增的(其实是巧合,多运行几次,会产生不同的输出结果),为什么 会产生这样的结果呢,因为建立的Count对象是 ...

  5. java runnable线程锁_多线程 java 同步 、锁 、 synchronized 、 Thread 、 Runnable

    线程 1 线程概述 1.1 什么是线程 v  线程是程序执行的一条路径, 一个进程中可以包含多条线程 v  一个应用程序可以理解成就是一个进程 v  多线程并发执行可以提高程序的效率, 可以同时完成多 ...

  6. Java并发知识梳理(上):并发优缺点,线程状态转换,Java内存模型,Synchronized,Volatile,final,并发三特性,Lock与AQS,ReetrandLock

    努力的意义,就是,在以后的日子里,放眼望去全是自己喜欢的人和事! 整个系列文章为Java并发专题,一是自己的兴趣,二是,这部分在实际理解上很有难度,另外在面试过程中也是经常被问到.所以在学习过程中,记 ...

  7. Java高级-线程同步机制实现

    2019独角兽企业重金招聘Python工程师标准>>> 前言 我们可以在计算机上运行各种计算机软件程序.每一个运行的程序可能包括多个独立运行的线程(Thread). 线程(Threa ...

  8. JAVA中线程同步的方法(7种)汇总

    JAVA中线程同步的方法(7种)汇总 同步的方法: 一.同步方法 即有synchronized关键字修饰的方法. 由于java的每个对象都有一个内置锁,当用此关键字修饰方法时, 内置锁会保护整个方法. ...

  9. Java多线程:线程间通信之Lock

    Java 5 之后,Java在内置关键字sychronized的基础上又增加了一个新的处理锁的方式,Lock类. 由于在Java线程间通信:volatile与sychronized中,我们已经详细的了 ...

最新文章

  1. Python3 条件控制
  2. (JAVA)Integer类之基本数据类型之间的转换
  3. null最后如何排序的_LeetCode 148——排序链表
  4. Go实现Raft第一篇:介绍
  5. 浅谈DOMContentLoaded事件及其封装方法
  6. Leetcode 刷题笔记(一) —— 数组类型解题方法一:二分法
  7. ddm模型公式_绝对估值法DDM、DCF模型和RNAV简介
  8. window下mysql免安装版教程大全
  9. 创建user01-user20 随机六位数密码 a-z A-Z 0-9
  10. RNN denoise
  11. matlab整流仿真,基于MATLAB的整流电路的建模与仿真
  12. EasyBoot中文启动光盘制作教程
  13. mac mail 删除邮件服务器,这是在Mac上的Mail中自动删除垃圾电子邮件的方法
  14. 科技云报道:乘风破浪的联通沃云,是一朵安全可控的国产云
  15. signature=54cb1c123491dc1a268a21f3502cccfc,汉隶《曹全碑》精讲精练
  16. 中国医师节丨华为IdeaHub用远程诊疗护佑人民健康,为医生减负
  17. IT资质认证证书如何查询?这篇文章教你查询方式
  18. Chapter3:根轨迹法(上)
  19. sql三表查子项目和
  20. Echarts 地图隐藏右下角 “南海诸岛” 的方法

热门文章

  1. MySQL 黑洞引擎的使用场景解释
  2. android Formatter 的使用
  3. kali linux fuzz工具集简述
  4. 什么是单页面应用程序
  5. 数据结构与算法 --- js描述集合
  6. ant 安装及基础教程 !
  7. MyBatis源码分析-IDEA新建MyBatis源码工程
  8. linux消息队列的使用
  9. 【转】SSL/TLS/WTLS协议原理
  10. Python爬虫框架Scrapy安装使用步骤