java 代码同步_Java同步代码块 转

Java 同步块(synchronized block)用来标记方法或者代码块是同步的。Java同步块用来避免竞争。本文介绍以下内容:

Java同步关键字(synchronzied)

实例方法同步

静态方法同步

实例方法中同步块

静态方法中同步块

Java同步示例

Java同步关键字(synchronized)

Java中的同步块用synchronized标记。同步块在Java中是同步在某个对象上。所有同步在一个对象上的同步块在同时只能被一个线程进入并执行操作。所有其他等待进入该同步块的线程将被阻塞,直到执行该同步块中的线程退出。

有四种不同的同步块:

实例方法

静态方法

实例方法中的同步块

静态方法中的同步块

上述同步块都同步在不同对象上。实际需要那种同步块视具体情况而定。

实例方法同步

下面是一个同步的实例方法:

1 public synchronized void add(intvalue){2   this.count +=value;3 }

注意在方法声明中同步(synchronized )关键字。这告诉Java该方法是同步的。

Java实例方法同步是同步在拥有该方法的对象上。这样,每个实例其方法同步都同步在不同的对象上,即该方法所属的实例。只有一个线程能够在实例方法同步块中运行。如果有多个实例存在,那么一个线程一次可以在一个实例同步块中执行操作。一个实例一个线程。

静态方法同步

静态方法同步和实例方法同步方法一样,也使用synchronized 关键字。Java静态方法同步如下示例:

1 public static synchronized void add(intvalue){2 count +=value;3 }

同样,这里synchronized 关键字告诉Java这个方法是同步的。

静态方法的同步是指同步在该方法所在的类对象上。因为在Java虚拟机中一个类只能对应一个类对象,所以同时只允许一个线程执行同一个类中的静态同步方法。

对于不同类中的静态同步方法,一个线程可以执行每个类中的静态同步方法而无需等待。不管类中的那个静态同步方法被调用,一个类只能由一个线程同时执行。

实例方法中的同步块

有时你不需要同步整个方法,而是同步方法中的一部分。Java可以对方法的一部分进行同步。

在非同步的Java方法中的同步块的例子如下所示:

1 public void add(intvalue){2

3 synchronized(this){4 this.count +=value;5 }6 }

示例使用Java同步块构造器来标记一块代码是同步的。该代码在执行时和同步方法一样。

注意Java同步块构造器用括号将对象括起来。在上例中,使用了“this”,即为调用add方法的实例本身。在同步构造器中用括号括起来的对象叫做监视器对象。上述代码使用监视器对象同步,同步实例方法使用调用方法本身的实例作为监视器对象。

一次只有一个线程能够在同步于同一个监视器对象的Java方法内执行。

下面两个例子都同步他们所调用的实例对象上,因此他们在同步的执行效果上是等效的。

1 public classMyClass {2

3 public synchronized voidlog1(String msg1, String msg2){4 log.writeln(msg1);5 log.writeln(msg2);6 }7

8 public voidlog2(String msg1, String msg2){9 synchronized(this){10 log.writeln(msg1);11 log.writeln(msg2);12 }13 }14 }

在上例中,每次只有一个线程能够在两个同步块中任意一个方法内执行。

如果第二个同步块不是同步在this实例对象上,那么两个方法可以被线程同时执行。

静态方法中的同步块

和上面类似,下面是两个静态方法同步的例子。这些方法同步在该方法所属的类对象上。

1 public classMyClass {2 public static synchronized voidlog1(String msg1, String msg2){3 log.writeln(msg1);4 log.writeln(msg2);5 }6

7 public static voidlog2(String msg1, String msg2){8 synchronized(MyClass.class){9 log.writeln(msg1);10 log.writeln(msg2);11 }12 }13 }

这两个方法不允许同时被线程访问。

如果第二个同步块不是同步在MyClass.class这个对象上。那么这两个方法可以同时被线程访问。

Java同步实例

在下面例子中,启动了两个线程,都调用Counter类同一个实例的add方法。因为同步在该方法所属的实例上,所以同时只能有一个线程访问该方法。

1 public classCounter{2 long count = 0;3 public synchronized void add(longvalue){4 this.count +=value;5 }6 }7

8 public class CounterThread extendsThread{9 protected Counter counter = null;10

11 publicCounterThread(Counter counter){12 this.counter =counter;13 }14

15 public voidrun() {16 for(int i=0; i<10; i++){17 counter.add(i);18 }19 }20 }21

22 public classExample {23

24 public static voidmain(String[] args){25 Counter counter = newCounter();26 Thread threadA = newCounterThread(counter);27 Thread threadB = newCounterThread(counter);28

29 threadA.start();30 threadB.start();31 }32 }

创建了两个线程。他们的构造器引用同一个Counter实例。Counter.add方法是同步在实例上,是因为add方法是实例方法并且被标记上synchronized关键字。因此每次只允许一个线程调用该方法。另外一个线程必须要等到第一个线程退出add()方法时,才能继续执行方法。

如果两个线程引用了两个不同的Counter实例,那么他们可以同时调用add()方法。这些方法调用了不同的对象,因此这些方法也就同步在不同的对象上。这些方法调用将不会被阻塞。如下面这个例子所示:

1 public classExample {2

3 public static voidmain(String[] args){4 Counter counterA = newCounter();5 Counter counterB = newCounter();6 Thread threadA = newCounterThread(counterA);7 Thread threadB = newCounterThread(counterB);8

9 threadA.start();10 threadB.start();11 }12 }

注意这两个线程,threadA和threadB,不再引用同一个counter实例。CounterA和counterB的add方法同步在他们所属的对象上。调用counterA的add方法将不会阻塞调用counterB的add方法。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/298229.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Office 2010 64位版本

最新的Office 2010有了x86和x64两种不同的版本&#xff0c;众所周知的使用x64版本具有可以支持更大的内存等特点&#xff0c;但是也会出现一定的兼容性问题。其中感觉影响比较大的是Access的32位版本和64位版本创建的数据库无法通用&#xff0c;这样以前创建的Access文件就无法…

JUnit 测试

Junit 使用 1、忽略测试方法。在使用Test的方法上使用Ignore&#xff0c;将不会对此方法进行测试 2、测试套件 解决的问题&#xff1a; 1、对测试类进行统一测试&#xff0c;而不必在单独测试类上一个一个进行测试。 使用JUnit的RunWith以及SuiteClassses注解&#xff0c;Suite…

【另类见解】秒杀并非高不可攀

“一提到秒杀很简单这个话题&#xff0c;我知道要被别人鄙视了&#xff1a;你不懂高并发... 这年头开头不画个思维导图都觉得掉价image谈到秒杀&#xff0c;网络上不少于几千片文章&#xff0c;但是大多大同小异。如果你的微信当中关注了几个编程技术类的公众号&#xff0c;我敢…

我又相信爱情了!

1 圣诞限定款的肥宅快乐水更好喝了吗&#xff1f;不&#xff01;更贵了2 周边鬼才&#xff01;这手机壳我爱了3 你以为是个王者&#xff0c;其实是个大脸......4 高温超导材料达到临界温度后能使物体悬浮在不同位置5 火山爆发你见过吗&#xff1f;6 我又相信爱情了&#xff01;…

opencv计算两数组的乘积_#剑指Offer#12. 构建乘积数组

题目描述&#xff1a;给定一个数组A[0,1,...,n-1],请构建一个数组B[0,1,...,n-1]。其中B中的元素B[i]A[0] * A[1]... * A[i-1] * A[i1]... * A[n-1]。不能使用除法。解题思路&#xff1a;首先&#xff0c;仔细理解题意&#xff0c;B[i]是A数组所有元素的乘积&#xff0c;但是没…

python引用numpy出错_使用numpy时出错

我尝试使用pandas python进行excel操作。在每当我尝试使用pandas库时&#xff0c;它都会给我错误的提示&#xff1a;numpy没有安装。在现在&#xff0c;当我尝试安装pip install numpy和pip安装pandas时&#xff0c;它说需求已经满足了。在但是当我尝试做一个简单的numpy教程时…

中国移动:面向全业务运营的安全管理平台

在2008年的一个电信运营支撑系统论坛上&#xff0c;来自中国移动的集团网络部的安全副处长周智先生做了一个题为《面向全业务运营的安全运行管理系统定位及建设思路》的报告。 在这个报告中&#xff0c;周处首先分析了全业务运营环境下的安全挑战&#xff0c;然后提出了在全业务…

记一次 .NET 某桌面奇侠游戏 非托管内存泄漏分析

一&#xff1a;背景 1. 讲故事说实话&#xff0c;这篇dump我本来是不准备上一篇文章来解读的&#xff0c;但它有两点深深的感动了我。无数次的听说用 Unity 可做游戏开发&#xff0c;但百闻不如一见。游戏中有很多金庸武侠小说才有的名字&#xff0c;太赏心悦目了。000000df315…

成年人的数学公式

1 成年人的数学公式2 唯一对我说过“别走好吗”的人3 主人发起疯来有多可怕4 别人家的狗看到主人有危险▼你家的……▼5 蜘蛛捕食瞬间6 蜡烛重燃&#xff08;冒的白烟是固态小颗粒的石蜡蒸汽&#xff0c;可燃&#xff09;你点的每个赞&#xff0c;我都认真当成了喜欢

ubuntu运行python ide_在Ubuntu-16.04中安装Python可视化IDE——Spyder

Spyder是Python(x,y)的作者为它开发的一个简单的集成开发环境。和其他的Python开发环境相比&#xff0c;它最大的优点就是模仿MATLAB的“工作空间”的功能&#xff0c;可以很方便地观察和修改数组的值。Spyder的界面由许多窗格构成&#xff0c;用户可以根据自己的喜好调整它们的…

Linux查看系统信息的一些命令及查看已安装软件包的命令(转)

系统 # uname -a # 查看内核/操作系统/CPU信息 # head -n 1 /etc/issue # 查看操作系统版本 # cat /proc/cpuinfo # 查看CPU信息 # hostname # 查看计算机名 # lspci -tv # 列出所有PCI设备 # lsusb -tv # 列出所…

日历签到 java_我的Android案例―签到日历

public class MainActivity extends Activity {//Log标签private static final String TAG "SIGN";//声明对象private Button sign;private TextView show;private GridView myDate;//获得本地时间Time nowTime new Time();//1个月内的天数private int dayMaxNum;p…

phpMailer 配置 企业邮局 163

phpMailer的两种配置&#xff0c;记录一下&#xff0c;差别在一个要写完整邮件地址&#xff0c;一个只要填前面的部分。一、自己的企业邮局发信$mail new PHPMailer();//$body file_get_contents("mail/".$date.".html"); //$bo…

Linux运维实战之DNS的高级配置(转发器、视图等)

上次博文我们具体配置了一台DNS服务器并实现了主辅之间的区域传送&#xff0c;本次博文我们来看看DNS的一些高级配置。 在进行DNS的高级配置之前&#xff0c;必须要理解DNS的原理&#xff08;参见http://sweetpotato.blog.51cto.com/533893/1596973&#xff09; 并且对DNS的基础…

POJ1269 Intersecting Lines 计算几何 C语言

题目&#xff1a;http://poj.org/problem?id1269 题目大意&#xff1a;给出四个点确定两条直线。如果是一条线输出“LINE”&#xff0c;如果平行输出“NONE”&#xff0c; 如果有交点输出交点坐标。 思路&#xff1a;注意是直线&#xff0c;不是线段啊。 用两点式推出两条直线…

史上最烧脑的学习方法,看完瞬间涨姿势!

▲ 点击查看 在美国&#xff0c;有一个天才儿童计划&#xff0c;选拔一批“天才”儿童进入天才班。这个计划是为了保证每个人接受平等教育机会的同时&#xff0c;也为精英成长提供合适的土壤。美国所谓的天才和精英是怎样的标准呢&#xff1f;进入天才班的儿童首先要通过一个叫…

WPF轮播图实现方式(二)

WPF开发者QQ群&#xff1a; 340500857 | 微信群 -> 进入公众号主页 加入组织欢迎转发、分享、点赞、在看&#xff0c;谢谢~。 01—效果预览02—代码如下一、EmphasizerCarousel.cs 代码如下using System; using System.Collections.Generic; using System.Collections.Obj…

java开闭原则_什么是开闭原则?如何实现开闭原则

2015-04-13 06:30:01阅读( 137 )开闭原则的解释就是&#xff1a;软件实体应当对扩展开放&#xff0c;对修改关闭&#xff0c;也就是&#xff1a;软件系统中包含的各种组件&#xff0c;例如模块(Modules)、类(Classes)以及功能(Functions)等等&#xff0c;应该在不修改现有代码的…

实现链栈的各种基本运算的算法_LeetCode基础算法题第78篇:如何不用加减号实现两数的加法运算?...

一直很纠结算法的文章应该怎么写。最后觉得还是从最简单的level开始写吧&#xff0c;一开始就弄些重量级的&#xff0c;什么人工智能&#xff0c;机器学习的算法&#xff0c;还要有大量的数学以及优化的知识&#xff0c;小白们估计会很郁闷&#xff0c;当然我也不一定能做出来对…

QQREADERB9B632B5D3670680

QQREADERB9B632B5D3670680