Heim > Java > JavaBase > Was ist der Unterschied zwischen synchronisiert und gesperrt?

Was ist der Unterschied zwischen synchronisiert und gesperrt?

青灯夜游
Freigeben: 2020-11-19 11:38:29
Original
68726 Leute haben es durchsucht

区别:1、lock是一个接口,而synchronized是java的一个关键字。2、synchronized在发生异常时会自动释放占有的锁,因此不会出现死锁;而lock发生异常时,不会主动释放占有的锁,必须手动来释放锁,可能引起死锁的发生。

Was ist der Unterschied zwischen synchronisiert und gesperrt?

在分布式开发中,锁是线程控制的重要途径。Java为此也提供了2种锁机制,synchronized和lock。

0、synchronized实现原理

Java中每一个对象都可以作为锁,这是synchronized实现同步的基础:

  • 普通同步方法,锁是当前实例对象

  • 静态同步方法,锁是当前类的class对象

  • 同步方法块,锁是括号里面的对象
    当一个线程访问同步代码块时,它首先是需要得到锁,当退出或者抛出异常时必须要释放锁,那么它是如何来实现这个机制的呢?我们先看一段简单的代码:

package cn.alibab.javap;public class SynchronizedTest {

    public synchronized void test1(){

    }    public void test2(){        synchronized (this){

        }
    }
}
Nach dem Login kopieren

利用javap工具(javap是java编译之后的class文件的分解器)查看生成的class文件信息来分析Synchronized的实现

Was ist der Unterschied zwischen synchronisiert und gesperrt?

Was ist der Unterschied zwischen synchronisiert und gesperrt?
从上面可以看出,同步代码块是使用monitorenter和monitorexit指令实现的,同步方法(在这看不出来需要看JVM底层实现)依靠的是方法修饰符上的ACC_SYNCHRONIZED实现。

同步代码块:monitorenter指令是在编译后插入到同步代码块的开始位置,monitorexit指令插入到同步代码块的结束位置,JVM需要保证每一个monitorenter都有一个monitorexit与之相对应。任何对象都有一个monitor与之相关联,当且一个monitor被持有之后,他将处于锁定状态。线程执行到monitorenter指令时,将会尝试获取对象所对应的monitor所有权,即尝试获取对象的锁;【摘自并发编程艺术】

同步方法:synchronized方法则会被翻译成普通的方法调用和返回指令如:invokevirtual、areturn指令,在VM字节码层面并没有任何特别的指令来实现被synchronized修饰的方法,而是在Class文件的方法表中将该方法的access_flags字段中的synchronized标志位置1,表示该方法是同步方法并使用调用该方法的对象或该方法所属的Class在JVM的内部对象表示Klass做为锁对象。(摘自:http://www.cnblogs.com/javaminer/p/3889023.html)

synchronized和lock的区别

Was ist der Unterschied zwischen synchronisiert und gesperrt?
区别如下:

  • 来源:
    lock是一个接口,而synchronized是java的一个关键字,synchronized是内置的语言实现;

  • 异常是否释放锁:
    synchronized在发生异常时候会自动释放占有的锁,因此不会出现死锁;而lock发生异常时候,不会主动释放占有的锁,必须手动unlock来释放锁,可能引起死锁的发生。(所以最好将同步代码块用try catch包起来,finally中写入unlock,避免死锁的发生。)

  • 是否响应中断
    lock等待锁过程中可以用interrupt来中断等待,而synchronized只能等待锁的释放,不能响应中断;

  • 是否知道获取锁
    Lock可以通过trylock来知道有没有获取锁,而synchronized不能;

  • Lock可以提高多个线程进行读操作的效率。(可以通过readwritelock实现读写分离)

  • 在性能上来说,如果竞争资源不激烈,两者的性能是差不多的,而当竞争资源非常激烈时(即有大量线程同时竞争),此时Lock的性能要远远优于synchronized。所以说,在具体使用时要根据适当情况选择。

  • synchronized使用Object对象本身的wait 、notify、notifyAll调度机制,而Lock可以使用Condition进行线程之间的调度,

//Condition定义了等待/通知两种类型的方法
Lock lock=new ReentrantLock();
Condition condition=lock.newCondition();...condition.await();...condition.signal();
condition.signalAll();
Nach dem Login kopieren

1、synchronized和lock的用法区别

synchronized:在需要同步的对象中加入此控制,synchronized可以加在方法上,也可以加在特定代码块中,括号中表示需要锁的对象。

lock:一般使用ReentrantLock类做为锁。在加锁和解锁处需要通过lock()和unlock()显示指出。所以一般会在finally块中写unlock()以防死锁。

2、synchronized和lock性能区别

synchronized是托管给JVM执行的,
而lock是java写的控制锁的代码。

In Java 1.5 ist die Synchronisierung leistungsineffizient. Da es sich hierbei um eine schwere Operation handelt, die den Aufruf der Operationsschnittstelle erfordert, kann das Sperren mehr Systemzeit beanspruchen als andere Vorgänge als das Sperren. Im Gegensatz dazu bietet die Verwendung des von Java bereitgestellten Lock-Objekts eine höhere Leistung.

Aber mit Java 1.6 haben sich die Dinge geändert. Synchronize ist semantisch sehr klar und kann viele Optimierungen durchführen, einschließlich adaptivem Spin, Sperrenbeseitigung, Sperrvergröberung, leichtgewichtiger Sperre, voreingenommener Sperre usw. Infolgedessen ist die Leistung von Synchronize unter Java1.6 nicht schlechter als die von Lock. Beamte gaben außerdem an, dass sie auch die Synchronisierung stärker unterstützen und es in zukünftigen Versionen Raum für Optimierungen gebe.

Die spezifischen Unterschiede zwischen den beiden Mechanismen:
Synchronized verwendete ursprünglich den pessimistischen CPU-Sperrmechanismus, dh der Thread erhält eine exklusive Sperre. Exklusive Sperre bedeutet, dass andere Threads nur auf die Blockierung warten können, bis der Thread die Sperre aufhebt. Wenn der CPU-Konvertierungsthread blockiert ist, führt dies zu einem Thread-Kontextwechsel. Wenn viele Threads um die Sperre konkurrieren, führt dies zu einem häufigen Kontextwechsel der CPU, was zu einer sehr geringen Effizienz führt.

Und Lock verwendet eine optimistische Sperrmethode. Die sogenannte optimistische Sperre besteht darin, einen Vorgang jedes Mal ohne Sperre abzuschließen, jedoch unter der Annahme, dass kein Konflikt vorliegt. Wenn er aufgrund eines Konflikts fehlschlägt, wird er wiederholt, bis er erfolgreich ist. Der durch optimistische Sperren implementierte Mechanismus ist die CAS-Operation (Compare and Swap). Wenn wir den Quellcode von ReentrantLock weiter untersuchen, werden wir feststellen, dass eine der wichtigeren Methoden zum Erhalten der Sperre CompareAndSetState ist. Dies ist eigentlich die spezielle Anweisung, die von der aufgerufenen CPU bereitgestellt wird.

Moderne CPUs stellen Anweisungen bereit, die gemeinsam genutzte Daten automatisch aktualisieren und Störungen durch andere Threads erkennen können. CompareAndSet() verwendet diese anstelle von Sperren. Dieser Algorithmus wird als nicht blockierender Algorithmus bezeichnet. Dies bedeutet, dass der Ausfall oder die Unterbrechung eines Threads keinen Einfluss auf den Ausfall oder die Unterbrechung anderer Threads haben sollte.

3. Der Unterschied zwischen synchronisierten und Sperrzwecken

Unter normalen Umständen gibt es keinen Unterschied zwischen synchronisierten Grundelementen und ReentrantLock. Bei sehr komplexen Synchronisierungsanwendungen sollten Sie jedoch die Verwendung von ReentrantLock in Betracht ziehen, insbesondere wenn Sie auf die folgenden beiden Anforderungen stoßen.

1. Ein bestimmter Thread muss unterbrochen werden, während er auf die Kontrolle einer Sperre wartet. 2. Einige Wartebenachrichtigungen müssen separat verarbeitet werden. Die Bedingungsanwendung in ReentrantLock kann steuern, welcher Thread benachrichtigt werden soll. 3. Es gibt eine faire Sperre Funktion. Jeder eingehende Thread wird in der Schlange stehen

Lass uns im Detail darüber reden...

Lass uns zuerst über den ersten Fall sprechen. Es gibt zwei Sperrmechanismen von ReentrantLock, die Interrupt-Sperren ignorieren und auf Interrupt-Sperren reagieren viele Probleme. Große Flexibilität. Beispiel: Wenn zwei Threads A und B um eine Sperre konkurrieren, erhält Thread A die Sperre und Thread B wartet. Allerdings hat Thread A zu diesem Zeitpunkt wirklich zu viele Dinge zu erledigen und kann Thread B möglicherweise nicht zurückgeben Ich möchte noch länger warten, aufhören, auf diese Sperre zu warten, und mich anderen Dingen zuwenden. Zu diesem Zeitpunkt bietet

ReentrantLock zwei Mechanismen: unterbrechbar/nicht unterbrechbar

Erstens unterbricht Thread B sich selbst (oder andere Threads unterbrechen ihn), aber ReentrantLock antwortet nicht und lässt Thread B weiterhin warten, I taub geworden (dies ist beim synchronisierten Grundelement der Fall); Zweitens unterbricht sich der B-Thread selbst (oder andere Threads unterbrechen ihn), ReentrantLock verarbeitet den Interrupt und wartet nicht mehr auf das Eintreffen der Sperre, sondern gibt vollständig auf .

Weitere Kenntnisse zum Thema Programmierung finden Sie unter:

Programmiervideos

! !

Das obige ist der detaillierte Inhalt vonWas ist der Unterschied zwischen synchronisiert und gesperrt?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Verwandte Etiketten:
Quelle:php.cn
Erklärung dieser Website
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn
Beliebte Tutorials
Mehr>
Neueste Downloads
Mehr>
Web-Effekte
Quellcode der Website
Website-Materialien
Frontend-Vorlage