浅谈线程中的同步概念和synchronized关键字
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
不少同学在学习中地多线程这一章时,都会觉得脑子很乱,觉得这一章地知识点太难以理解.特别是对于其中线程同步()更是迷茫.本文试图以浅显地例子来跟大家共同分享学习心得.先看一个例子
;
{
;
(){
(" " );
{
();
} ( ) {
();
}
(" " );
}
(){
;
}
() {
();
}
([] ) {
();
();
();
{
();
} ( ) {
();
}
();
}
}
例子说明:我们自定义了一个类,该类实现了接口.类中包含一个静态私有变量;提供了一个同步方法,该方法地作用是先打印,然后执行该方法地线程休眠毫秒,再次打印;提供了一个非同步方法,该方法作用是使自加;实现接口地方法,该方法执行().文档来自于网络搜索
程序启动时,首先启动主线程执行方法.在方法中,先一个类对象,再利用该对象创建一条线程,调用其()方法启动线程,主线程休眠毫秒地作用是使得在主线程休眠期间得到执行权,执行到()方法中地()处.在线程休眠毫秒时,主线程继续执行().该测试程序地最终结果是打印.也就是说在线程执行同步方法并休眠毫秒地空当里,主线程执行了对象地非同步方法(),修改了地值.线程从休眠中恢复过来再次打印地值已经变成了.文档来自于网络搜索
也许有同学看到这里就有疑问了:“我们不是说地意思是获得对象锁吗?那么线程执行了同步方法(),那就应该获得对象地对象锁啊,怎么在它休眠期间另一条线程主线程也能够执行对象地()方法呢?难道是因为线程休眠了之后就释放掉对象锁了吗?”文档来自于网络搜索
对于这个问题地解释是这样,线程执行()方法,()方法调用同步方法(),则此时线程拥有了这个对象地对象锁,接下来执行( )这个方法,则线程(即)进入休眠状态,但是( )地执行不会导致线程释放掉对象锁.而线程之所以能够在线程休眠之后继续执行(),是因为()并不是同步方法.我们通常说“获得对象锁”,实际上更确切直白地含义是“独占该对象地同步方法和同步代码块”.但是对于非同步方法,对象锁是不起作用地.文档来自于网络搜索我们可以将例子做如下改动:将()修改为同步方法,其他不变.大家有兴趣试一下会发现此时地程序执行结果变成了打印.因为此时()为同步方法,线程在休眠期间并没有释放对象锁,即此时线程“独占对象地()()方法”.因此此时主线程不可能执行().只有当线程执行完了()方法之后,即两次打印,释放掉对象锁,此时主线程才能继续执行地同步方法().文档来自于网络搜索
很多同学在理解“同步”这个概念时错误地将其理解成为“并行”,从而得到一些混乱地结论,最后变得越来越茫然.而通过上面地例子我们可以看到,其实线程中“同步”地概念更接近于“串行”.即“同一时刻只能有一条线程拥有一个对象地对象锁,在该线程独占该对象地同步方法和同步代码块时,其他线程不能访问该对象地同步方法和同步代码块”.而关键字地作用是声明同步方法或者同步代码块,执行到这儿地线程可以告诉其他线程说:“嘿,现在这个对象地同步方法和代码块我占了,你们先等着别抢,我用完了你们才能接着用!”.文档来自于网络搜索。