StampedLock 类
定义
重要
一些信息与预发行产品相关,相应产品在发行之前可能会进行重大修改。 对于此处提供的信息,Microsoft 不作任何明示或暗示的担保。
一种基于功能的锁,具有三种控制读/写访问的模式。
[Android.Runtime.Register("java/util/concurrent/locks/StampedLock", ApiSince=24, DoNotGenerateAcw=true)]
public class StampedLock : Java.Lang.Object, IDisposable, Java.Interop.IJavaPeerable, Java.IO.ISerializable
[<Android.Runtime.Register("java/util/concurrent/locks/StampedLock", ApiSince=24, DoNotGenerateAcw=true)>]
type StampedLock = class
inherit Object
interface ISerializable
interface IJavaObject
interface IDisposable
interface IJavaPeerable
- 继承
- 属性
- 实现
注解
一种基于功能的锁,具有三种控制读/写访问的模式。 StampedLock 的状态由版本和模式组成。 锁获取方法返回一个标记,表示和控制锁状态的访问;这些方法的“try”版本可能会返回特殊值零,表示无法获取访问权限。 锁释放和转换方法需要标记作为参数,如果它们与锁的状态不匹配,则失败。 这三种模式是:
<ul>
<李><b>写作。</b> 方法 #writeLock
可能会阻止等待独占访问,返回可用于释放锁的方法 #unlockWrite
中的标记。 还提供了非计时版本和计时版本的 tryWriteLock
版本。 当锁定处于写入模式时,无法获取读取锁,并且所有乐观读取验证都将失败。
<李><b>阅读。</b> 方法 #readLock
可能会阻止等待非独占访问,并返回可用于释放锁的方法 #unlockRead
中的标记。 还提供了非计时版本和计时版本的 tryReadLock
版本。
<李><b>乐观阅读。</b> 方法 #tryOptimisticRead
仅当锁当前未处于写入模式时返回非零标记。 如果在写入模式下未获取锁,则方法 #validate
返回 true,因为获取给定的标记,在这种情况下,在调用 tryOptimisticRead
后,最近写入锁释放之前发生的所有操作。 此模式可视为读取锁的极弱版本,随时可由编写器破坏。 对短只读代码段使用乐观读取模式通常会减少争用并提高吞吐量。 然而,它的使用本质上是脆弱的。 乐观读取部分应只读取字段,并将它们保存在本地变量中,供稍后在验证后使用。 在乐观读取模式下读取时读取的字段可能非常不一致,因此,仅当熟悉数据表示形式以检查一致性和/或重复调用方法 validate()
时才适用。 例如,在首次读取对象或数组引用,然后访问其中一个字段、元素或方法时,通常需要执行此类步骤。
</ul>
此类还支持在三种模式下有条件地提供转换的方法。 例如,方法 #tryConvertToWriteLock
尝试“升级”模式,如果(1)已在阅读模式下(2)处于写入模式(2),并且没有其他读取器或(3)处于乐观读取模式且锁可用,则返回有效的写入标记。 这些方法的形式旨在帮助减少在基于重试的设计中出现的某些代码膨胀。
StampedLocks 旨在用作线程安全组件开发中的内部实用工具。 它们的使用依赖于了解它们所保护的数据、对象和方法的内部属性。 它们不是重新进入的,因此锁定的正文不应调用可能尝试重新获取锁的其他未知方法(尽管你可以将戳记传递给其他可以使用或转换锁的方法)。 读取锁模式的使用依赖于具有副作用的关联代码部分。 未经评估的乐观读取部分无法调用已知无法容忍潜在不一致的方法。 邮票使用有限表示形式,并且不是加密安全的(即,有效的邮票可能是可以猜测的)。 在连续操作的一年后,标记值可能会回收(不超过)一年。 一个未使用或验证的模具超过此时间段可能无法正确验证。 StampedLocks 可序列化,但始终反序列化为初始解锁状态,因此它们不适用于远程锁定。
与大多数实现一样 java.util.concurrent.Semaphore Semaphore
,但与大多数 Lock
实现不同,StampedLocks 没有所有权的概念。 可以在另一个线程中释放或转换获取的锁。
StampedLock 的计划策略不一直更喜欢读者而不是编写器,反之亦然。 所有“尝试”方法都是尽最大努力的,不一定符合任何计划或公平策略。 从任何用于获取或转换锁的“try”方法返回的零返回不携带有关锁状态的任何信息;后续调用可能会成功。
由于它支持跨多个锁模式的协调使用,因此此类不直接实现 Lock
或 ReadWriteLock
接口。 但是,可以在需要关联功能集的应用程序中查看 #asReadLock()
#asWriteLock()
StampedLock。#asReadWriteLock()
<b>内存同步。</b> 在任何模式下成功锁定的效果的方法与 em>Lock</em> 操作具有相同的内存同步效果<,如引用>Java 语言规范</引用>的第 17 <章中所述。 在写入模式下成功解锁的方法具有与 em Unlock/em> 操作相同的内存同步效果<。>< 在乐观读取用法中,只有在以后验证返回 true 时,才保证在 tryOptimisticRead 之后的操作发生之前,才保证执行最新的写入模式解锁操作;否则,不能保证 tryOptimisticRead 之间的读取并验证获取一致的快照。
<b>示例用法。</b> 下面说明了维护简单二维点的类中的一些用法习惯。 示例代码演示了一些 try/catch 约定,尽管此处不严格需要这些约定,因为它们的正文中不会发生异常。
{@code
class Point {
private double x, y;
private final StampedLock sl = new StampedLock();
// an exclusively locked method
void move(double deltaX, double deltaY) {
long stamp = sl.writeLock();
try {
x += deltaX;
y += deltaY;
} finally {
sl.unlockWrite(stamp);
}
}
// a read-only method
// upgrade from optimistic read to read lock
double distanceFromOrigin() {
long stamp = sl.tryOptimisticRead();
try {
retryHoldingLock: for (;; stamp = sl.readLock()) {
if (stamp == 0L)
continue retryHoldingLock;
// possibly racy reads
double currentX = x;
double currentY = y;
if (!sl.validate(stamp))
continue retryHoldingLock;
return Math.hypot(currentX, currentY);
}
} finally {
if (StampedLock.isReadLockStamp(stamp))
sl.unlockRead(stamp);
}
}
// upgrade from optimistic read to write lock
void moveIfAtOrigin(double newX, double newY) {
long stamp = sl.tryOptimisticRead();
try {
retryHoldingLock: for (;; stamp = sl.writeLock()) {
if (stamp == 0L)
continue retryHoldingLock;
// possibly racy reads
double currentX = x;
double currentY = y;
if (!sl.validate(stamp))
continue retryHoldingLock;
if (currentX != 0.0 || currentY != 0.0)
break;
stamp = sl.tryConvertToWriteLock(stamp);
if (stamp == 0L)
continue retryHoldingLock;
// exclusive access
x = newX;
y = newY;
return;
}
} finally {
if (StampedLock.isWriteLockStamp(stamp))
sl.unlockWrite(stamp);
}
}
// upgrade read lock to write lock
void moveIfAtOrigin2(double newX, double newY) {
long stamp = sl.readLock();
try {
while (x == 0.0 && y == 0.0) {
long ws = sl.tryConvertToWriteLock(stamp);
if (ws != 0L) {
stamp = ws;
x = newX;
y = newY;
break;
}
else {
sl.unlockRead(stamp);
stamp = sl.writeLock();
}
}
} finally {
sl.unlock(stamp);
}
}
}}
已在 1.8 中添加。
适用于 . 的 java.util.concurrent.locks.StampedLock
Java 文档
本页的某些部分是根据 Android 开放源代码项目创建和共享的工作进行的修改,并根据 Creative Commons 2.5 属性许可证中所述的术语使用。
构造函数
StampedLock() |
创建一个新锁,最初处于解锁状态。 |
StampedLock(IntPtr, JniHandleOwnership) |
一种基于功能的锁,具有三种控制读/写访问的模式。 |
属性
Class |
返回此 |
Handle |
基础 Android 实例的句柄。 (继承自 Object) |
IsReadLocked |
如果锁当前非独占保留,则返回 |
IsWriteLocked |
如果锁当前以独占方式保存,则返回 |
JniIdentityHashCode |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
JniPeerMembers |
一种基于功能的锁,具有三种控制读/写访问的模式。 |
PeerReference |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
ReadLockCount |
查询此锁保留的读取锁数。 |
ThresholdClass |
一种基于功能的锁,具有三种控制读/写访问的模式。 |
ThresholdType |
一种基于功能的锁,具有三种控制读/写访问的模式。 |
方法
AsReadLock() |
返回此 StampedLock 的纯 |
AsReadWriteLock() |
返回 |
AsWriteLock() |
返回此 StampedLock 的纯 |
Clone() |
创建并返回此对象的副本。 (继承自 Object) |
Dispose() |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
Dispose(Boolean) |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
Equals(Object) |
指示其他对象是否“等于”此对象。 (继承自 Object) |
GetHashCode() |
返回对象的哈希代码值。 (继承自 Object) |
IsLockStamp(Int64) |
指示戳记是否表示持有锁。 |
IsOptimisticReadStamp(Int64) |
指示图章是否表示成功的乐观读取。 |
IsReadLockStamp(Int64) |
指示印章是否代表非独占持有锁。 |
IsWriteLockStamp(Int64) |
指示邮票是否代表以独占方式持有锁。 |
JavaFinalize() |
当垃圾回收确定不再引用该对象时,由对象上的垃圾回收器调用。 (继承自 Object) |
Notify() |
唤醒正在等待此对象的监视器的单个线程。 (继承自 Object) |
NotifyAll() |
唤醒正在等待此对象的监视器的所有线程。 (继承自 Object) |
ReadLock() |
非独占获取锁,必要时会阻止,直到可用为止。 |
ReadLockInterruptibly() |
非独占方式获取锁,必要时会阻塞,直到可用或当前线程中断。 |
SetHandle(IntPtr, JniHandleOwnership) |
设置 Handle 属性。 (继承自 Object) |
ToArray<T>() |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
ToString() |
返回对象的字符串表示形式。 (继承自 Object) |
TryConvertToOptimisticRead(Int64) |
如果锁状态与给定的标记匹配,则原子上,如果图章表示持有锁,则释放它并返回观察标记。 |
TryConvertToReadLock(Int64) |
如果锁状态与给定的标记匹配,则以原子方式执行下列操作之一。 |
TryConvertToWriteLock(Int64) |
如果锁状态与给定的标记匹配,则以原子方式执行下列操作之一。 |
TryOptimisticRead() |
返回以后可以验证的戳记,如果以独占方式锁定,则返回零。 |
TryReadLock() |
如果锁立即可用,则非独占获取锁。 |
TryReadLock(Int64, TimeUnit) |
如果锁在给定时间内可用且当前线程未中断,则非独占方式获取该锁。 |
TryUnlockRead() |
释放读取锁的一个保留(如果保留),而无需标记值。 |
TryUnlockWrite() |
释放写入锁(如果保留),而无需标记值。 |
TryWriteLock() |
如果锁立即可用,则独占获取该锁。 |
TryWriteLock(Int64, TimeUnit) |
如果锁在给定时间内可用,并且当前线程尚未中断,则独占获取该锁。 |
Unlock(Int64) |
如果锁状态与给定的标记匹配,则释放锁的相应模式。 |
UnlockRead(Int64) |
如果锁状态与给定的标记匹配,则释放非独占锁。 |
UnlockWrite(Int64) |
如果锁状态与给定的标记匹配,则释放独占锁。 |
UnregisterFromRuntime() |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
Validate(Int64) |
如果自颁发给定邮票以来未独占获取锁,则返回 true。 |
Wait() |
使当前线程等待,直到唤醒它,通常是通过 em 通知/em> 或 <em>interrupted</em>。<>< (继承自 Object) |
Wait(Int64, Int32) |
使当前线程等待直到唤醒,通常是通过 <em>通知</em> 或 <em interrupted</em>>,或直到经过一定数量的实时。 (继承自 Object) |
Wait(Int64) |
使当前线程等待直到唤醒,通常是通过 <em>通知</em> 或 <em interrupted</em>>,或直到经过一定数量的实时。 (继承自 Object) |
WriteLock() |
独占获取锁,必要时会阻止,直到可用为止。 |
WriteLockInterruptibly() |
独占获取锁,如有必要,阻止,直到可用或当前线程中断。 |
显式接口实现
IJavaPeerable.Disposed() |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
IJavaPeerable.DisposeUnlessReferenced() |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
IJavaPeerable.Finalized() |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
IJavaPeerable.JniManagedPeerState |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
IJavaPeerable.SetJniIdentityHashCode(Int32) |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
IJavaPeerable.SetJniManagedPeerState(JniManagedPeerStates) |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
IJavaPeerable.SetPeerReference(JniObjectReference) |
一种基于功能的锁,具有三种控制读/写访问的模式。 (继承自 Object) |
扩展方法
JavaCast<TResult>(IJavaObject) |
执行 Android 运行时检查的类型转换。 |
JavaCast<TResult>(IJavaObject) |
一种基于功能的锁,具有三种控制读/写访问的模式。 |
GetJniTypeName(IJavaPeerable) |
一种基于功能的锁,具有三种控制读/写访问的模式。 |