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

Was ist der Unterschied zwischen synchronisiert und gesperrt?

Nov 19, 2020 am 11:38 AM
java lock synchronized

区别: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){

        }
    }
}

利用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();

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!

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

Heiße KI -Werkzeuge

Undress AI Tool

Undress AI Tool

Ausziehbilder kostenlos

Undresser.AI Undress

Undresser.AI Undress

KI-gestützte App zum Erstellen realistischer Aktfotos

AI Clothes Remover

AI Clothes Remover

Online-KI-Tool zum Entfernen von Kleidung aus Fotos.

Clothoff.io

Clothoff.io

KI-Kleiderentferner

Video Face Swap

Video Face Swap

Tauschen Sie Gesichter in jedem Video mühelos mit unserem völlig kostenlosen KI-Gesichtstausch-Tool aus!

Heiße Werkzeuge

Notepad++7.3.1

Notepad++7.3.1

Einfach zu bedienender und kostenloser Code-Editor

SublimeText3 chinesische Version

SublimeText3 chinesische Version

Chinesische Version, sehr einfach zu bedienen

Senden Sie Studio 13.0.1

Senden Sie Studio 13.0.1

Leistungsstarke integrierte PHP-Entwicklungsumgebung

Dreamweaver CS6

Dreamweaver CS6

Visuelle Webentwicklungstools

SublimeText3 Mac-Version

SublimeText3 Mac-Version

Codebearbeitungssoftware auf Gottesniveau (SublimeText3)

Heiße Themen

PHP-Tutorial
1506
276
Edge PDF -Viewer funktioniert nicht Edge PDF -Viewer funktioniert nicht Aug 07, 2025 pm 04:36 PM

TestthepdfinanotherapptodetermineeiftheisueiswithTheFileoredge.2.Enablethebuilt-InpdfviewerByTurningOff "immerOpenpdffileSexTternal" und "DownloadPdffffiles" Inedgesetings

Gehen Sie mit gutem Beispielionieren einer Subprozesse aus Gehen Sie mit gutem Beispielionieren einer Subprozesse aus Aug 06, 2025 am 09:05 AM

Führen Sie den untergeordneten Prozess mit dem Betriebssystem/EXEC -Paket aus, erstellen Sie den Befehl über exec.Command, führen Sie ihn jedoch nicht sofort aus. 2. Führen Sie den Befehl mit .output () aus und fangen Sie Stdout an. Wenn der Exit-Code ungleich Null ist, return exec.exiterror; 3. Verwenden Sie .Start (), um den Prozess ohne Blockierung zu starten, mit .stdoutpipe () in Echtzeit aus der Ausgabe von Ausgang zu streamen; V. 5. Exec.EexitEerror muss verarbeitet werden, um den Ausgangscode und den Stderr des fehlgeschlagenen Befehls zu erhalten, um Zombie -Prozesse zu vermeiden.

Optimierung verschachtelter Forach -Schleifen für komplexe Datenstrukturen Optimierung verschachtelter Forach -Schleifen für komplexe Datenstrukturen Aug 06, 2025 pm 12:53 PM

Um verschachtelte für Schleifen zu optimieren, sollten zuerst redundante Iterationen vermieden werden, und die zeitliche Komplexität kann von O (N × m) auf O (n m) reduziert werden. Zweitens, wenn die Struktur nicht wirklich hierarchisch ist, sollten die Daten mithilfe von Methoden wie SelectMany abgeflacht werden. Drittens herausspringen oder unnötige Verarbeitung durch bedingte Beurteilung überspringen; Viertens wählen Sie geeignete Datenstrukturen wie Wörterbuch- oder Hash -Mengen aus, um die Suchffizienz zu verbessern. Fünftens kann eine Parallelisierung mit Vorsicht verwendet werden, wenn die Operationen unabhängig und zeitaufwändig sind. Sechstens, um eine komplexe Logik in unabhängige Methoden oder Abfragen zu extrahieren, um die Lesbarkeit und Wartbarkeit zu verbessern. Der Kern der Optimierung besteht darin, die Komplexität zu verringern, Daten vernünftig zu organisieren und immer die Notwendigkeit des Verschachtelns zu bewerten und letztendlich einen effizienten, klaren und erweiterbaren Code zu erreichen.

Bereitstellung einer Java -Anwendung in Kubernetes mit Docker Bereitstellung einer Java -Anwendung in Kubernetes mit Docker Aug 08, 2025 pm 02:45 PM

Containerisierte Java-Anwendung: Erstellen Sie eine Dockerfile, verwenden Sie ein grundlegendes Bild wie Eclipse-Temurin: 17-Jre-Alpine, kopieren Sie die JAR-Datei und definieren Sie den Startbefehl, erstellen Sie das Bild über Dockerbuild und führen Sie lokal mit Dockerun aus. 2. Drücken Sie das Bild in die Containerregistrierung: Verwenden Sie Dockertag, um das Bild zu markieren und zu Dockerhub und anderen Registern zu drücken. Sie müssen sich zuerst bei DockerLogin anmelden. 3.. Bereitstellen in Kubernetes: Schreiben Sie die Bereitstellung. Yaml, um die Bereitstellung zu definieren, die Anzahl der Replikate, Containerbilder und Ressourcenbeschränkungen festlegen und den Dienst schreiben.yaml zum Erstellen zu erstellen

Wie implementieren Sie einen einfachen TCP -Client in Java? Wie implementieren Sie einen einfachen TCP -Client in Java? Aug 08, 2025 pm 03:56 PM

Importjava.ioandjava.net.socketfori/oandsocketcommunication.2.CreateSocketObjectToConnectTotheserverusednameAnDport.3.useprintSertosendDataviaoutputStreamandBufferedReadereadServerresponSfrend

VS -Code -Verknüpfung, um sich auf das Explorer -Panel zu konzentrieren VS -Code -Verknüpfung, um sich auf das Explorer -Panel zu konzentrieren Aug 08, 2025 am 04:00 AM

In VSCODE können Sie das Panel- und Bearbeitungsbereich durch Abkürzungsschlüssel schnell wechseln. Um zum linken Explorer -Feld zu springen, verwenden Sie die Strg -Verschiebung E (Windows/Linux) oder CMD Shift E (MAC). Kehren Sie in den Bearbeitungsbereich zurück, um Strg `oder ESC oder Strg 1 ~ 9 zu verwenden. Im Vergleich zum Mausbetrieb sind Tastaturverknüpfungen effizienter und unterbrechen den Codierungsrhythmus nicht. Weitere Tipps sind: Strg KCtrl E Fokus -Suchkästchen, F2 -Datei umbenennen, Datei löschen, die Öffnungsdatei eingeben, Pfeilschlüssel erweitern/kollapten.

Wie kann ich eine vorbereitete Erklärung in Java ausführen? Wie kann ich eine vorbereitete Erklärung in Java ausführen? Aug 06, 2025 pm 04:04 PM

Laden Sie den JDBC -Treiber und stellen Sie eine Datenbankverbindung her. 2. Verwenden Sie Connection.preparestatement (), um eine SQL -Anweisung mit einem Platzhalter zu erstellen. 3. Call setString (), setInt () und andere Methoden zum Festlegen der Parameterwerte aus 1; V. 5. Verwenden Sie Try-with-Ressourcen, um die Ressourcen mit der Verbindung, vorbereitet und vorhandenen und Ergebnissen automatisch zu schließen, um Speicherlecks zu verhindern und eine sichere und effiziente Verarbeitung von Datenbankvorgängen sicherzustellen.

Lösen gemeinsamer Speicherlecks in Java -Anwendungen Lösen gemeinsamer Speicherlecks in Java -Anwendungen Aug 06, 2025 am 09:47 AM

StaticfieldsholdingobjectreferencesCanpreventGarbagebackecollection; UseWeakhashMaporCleanupMechanisishs.2.

See all articles