Mit der kräftigen Entwicklung des Internets stehen immer mehr Internetunternehmen mit gleichzeitigen Sicherheitsproblemen durch die Ausweitung des Benutzervolumens. Dieser Artikel konzentriert sich auf mehrere gemeinsame Verriegelungsmechanismen in der Parallelität von Java.
1. Positives Schloss
Vorgespannter Schloss ist ein von JDK1.6 vorgeschlagener Sperroptimierungsmechanismus. Die Kernidee ist, dass, wenn das Programm nicht konkurriert, der zuvor erhaltene Thread -Synchronisationsvorgang, der zuvor erhalten wurde, die Sperre abgesagt wird. Das heißt, wenn ein Schloss von einem Thread erfasst wird, tritt er in den Vorspannungsmodus ein. Wenn der Thread die Sperre erneut anfordert, müssen relevante Synchronisationsvorgänge nicht durchgeführt werden, wodurch die Betriebszeit gespeichert wird. Wenn andere Threads Sperranforderungen dazwischen stellen, verlässt der Sperre den Vorspannungsmodus. Verwenden Sie -xx:+UseBiaSedLocking in JVM
Paket JVMProject; import Java.util.List; import Java.util.Vector; öffentlicher Klasse voreingenommen {öffentliche statische Liste <Grapier> numberlist = new vector <Grapier> (); public static void main (String [] args) {long begin = system.currentTimemillis (); int count = 0; int startnum = 0; while (count <10000000) {numberList.add (startNum); startnum+= 2; zählen ++; } Long End = System.currentTimemillis (); System.out.println (End-BEIGHT); }}Initialisieren Sie einen Vektor, fügen Sie ihm 100.000.000 Ganzzahlobjekte hinzu und geben Sie dann den Zeitunterschied aus. Dies wird verwendet, um die Leistung von voreingenommenen Schlössern zu testen. Warum sollten Sie Vektor anstelle von ArrayList verwenden?
Da ArrayList Thread-Insecure ist, ist Vektor Thread-Safe. Dies ist möglicherweise nicht spezifisch genug. Sie können sich den Quellcode ansehen.
Fast alle Operationen in Vektor sind sychronisiert, während ArrayList nicht der Fall ist, so dass Vektor thread-safe ist.
Lassen Sie uns als nächstes testen, wie viel Einfluss auf die Eröffnung von voreingenommenen Schlössern und nicht die Eröffnung von voreingenommenen Schlössern auf die Programmleistung haben.
Konfigurieren Sie die Parameter von JVM -Starts (Einschalten der Vorspannungssperrung) in:
Konfigurieren Sie die Parameter von JVM -Start -up -Parametern (Close Bias Lock) auf:
Perfekt! Die Laufzeit des Programms, das eine voreingenommene Schloss ermöglicht, ist erheblich kürzer. Es hat bestimmte Vorteile, um voreingenommene Schlösser zu ermöglichen, als nicht voreingenommene Schlösser zu aktivieren. Die Synchronisationsmethode zum Betrieb eines Objekts in einem einzelnen Thread. Tatsächlich kann es auch auf diese Weise verstanden werden. Wenn nur ein Thread ein Vektorobjekt mit einer Synchronisationsmethode betreibt, wird der Vorgang auf dem Vektor in eine Operation auf der ArrayList konvertiert.
Das vorgespannte Schloss hat keinen starken Optimierungseffekt, wenn das Schloss wettbewerbsfähig ist, da eine große Menge an Konkurrenz dazu führt, dass der Faden, der das Schloss hält, kontinuierlich wechselt, und es ist schwierig, dass das Schloss im voreingenommenen Modus bleibt. Zu diesem Zeitpunkt erreicht die Verwendung des voreingenommenen Schlosses nicht nur die Leistungsoptimierung nicht, sondern kann die Leistung des Systems verringern. Daher können Sie im Falle eines heftigen Wettbewerbs versuchen, es zu verwenden.
-Xx: -UsBiastedLocking-Parameter deaktiviert die Verzerrung der Verriegelung.
2. Leichtes Schloss
Wenn das vorgespannte Schloss fehlschlägt, bittet die Java Virtual Machine den Faden, ein leichtes Schloss anzuwenden. Das leichte Schloss wird in der virtuellen Maschine implementiert und unter Verwendung eines Objekts implementiert, das zu einem BasicObjectlock wird, das aus einem Basiclock -Objekt und einem Java -Objektzeiger besteht, das das Schloss hält. Das BasicObjectLock -Objekt wird im Java -Stack -Rahmen platziert. Das Feld angezeigt_header wird auch im Basiclock -Objekt gepflegt, mit dem das Markwort des Objekt -Headers sichtbar ist.
Wenn ein Thread die Sperre eines Objekts enthält, lautet die Header -Mark -Informationen des Objekts wie folgt wie folgt
[PTR | 00] gesperrt
Die beiden Bits am Ende sind 00 und das gesamte Markwort ist ein Zeiger auf das Basiclock -Objekt. Da sich das BasicObjectLock -Objekt im Fadenstapel befindet, muss der Zeiger auf den Fadenstapelraum verweisen, der das Schloss enthält. Wenn festgestellt werden muss, ob ein Thread das Objekt enthält, muss nur festgestellt werden, ob sich der Zeiger des Objektkopfs im Stapeladressbereich des aktuellen Threads befindet. Gleichzeitig stützt der angezeigte_header des BasicLock -Objekts den Mark -Word -Inhalt des ursprünglichen Objekts, und das OBJ -Feld des BasicObjectLock -Objekts zeigt auf den Kopf des Objekts, das die Sperre hält.
3. Schwergewichtsschloss
Wenn das leichte Schloss ausfällt, verwendet die virtuelle Maschine das Schwergewichtsschloss. Bei Verwendung von Schwergewichtsschlössern lautet das Mark -Wort des Objekts wie folgt:
[PTR | 10] Monitor
Während des Betriebs kann der Faden auf Betriebssystemebene ausgesetzt werden. In diesem Fall werden die Kosten für das Umschalten und Anruf zwischen Threads erheblich erhöht.
4. Spin -Lock
Ein Spinschloss kann den Faden nicht suspendiert lassen, wenn er das Schloss nicht erhalten hat, sondern um eine leere Schleife auszuführen (dh den sogenannten Dreh, was bedeutet, die leere Schleife selbst auszuführen). Wenn der Thread das Schloss nach mehreren leeren Schleifen erhalten kann, wird es weiter ausgeführt. Wenn der Faden das Schloss immer noch nicht erhalten kann, wird er suspendiert.
Nach der Verwendung von Spin -Lock ist die Wahrscheinlichkeit, dass der Faden suspendiert wird, relativ reduziert und die Konsistenz der Threadausführung relativ verbessert. Daher hat es eine gewisse positive Bedeutung für gleichzeitige Threads, die mit Schlössern nicht sehr wettbewerbsfähig sind und eine sehr kurze Zeit haben. Bei gleichzeitigen Programmen, die mit Schlössern und Single-Threaden-Sperren sehr lange wettbewerbsfähig sind, kann das Spin-Lock das entsprechende Schloss nach dem Spin-Warten häufig nicht entschlossen nicht erhalten. Dies verschwendet nicht nur die CPU -Zeit, sondern hat auch zwangsläufig den suspendierten Betrieb am Ende, sondern verschwendet auch die Systemressourcen.
In JDK1.6 liefert die java -virtuelle Maschine den Parameter -xx:+usespinning, um das Spin -Sperre zu aktivieren, und verwendet den Parameter -xx: preBlockspin, um die Anzahl der Warten des Spin -Sperzers einzustellen.
Ab JDK 1.7 werden die Parameter des Spin -Locks abgebrochen. Die virtuelle Maschine unterstützt das von Benutzer konfigurierte Spin-Lock nicht mehr. Die Spinsperrung wird immer ausgeführt und die Anzahl der Spin -Schlösser wird automatisch von der virtuellen Maschine eingestellt.