java - 如何在java中请求锁定数据结构的数据
问题描述
最近,在研究现代数据库中的事务时,我发现现在的事务不会对整个集合或表使用锁或监视器,而是通常对集合或表的数据进行操作,这些数据将被不同的人使用事务执行的操作。
所以我在想,假设我们有一个数据结构,它可以是 LinkedList、Hashtable 等,并且多个不同的事务想要同时访问该结构以更新数据。我如何请求锁定事务将要使用的数据,而不是锁定整个对象数据结构?这显然会提高性能,因为使用相同数据结构的不同数据的不同更新事务将同时发生。
我将尝试澄清更多我想要实现的目标,这是一个示例:
public class Table {
// suppose this is the data of the table and it has a lot of values
private LinkedList<String> data = new LinkedList();
public void doTransactionJob() {
// here we get the data from the list
// and we ask for monitor on this data so that no other
// transaction can operate on it
synchronized(data.get(randomIndex)) {
// here the transaction works on the data but doesnt
// block any other transaction from working on the same table
// but with different data
}
}
}
是否存在与我上面的示例类似的东西?
解决方案
您可以使用一个SynchronizedList
对象,它将阻止和同步列表上的任何操作,甚至读取操作,因此在添加或更新列表时更好地使用它,或者CopyOnWriteList
将使用新对象创建一个新列表,并且不会导致正在运行的读取操作的问题。但是如果你的问题是对象本身在列表中的某个位置,我建议ReentrantReadWriteLock
对你想要阻止的方法使用策略,这样你可以在锁定时更好地管理,只有当人们更新对象或其他东西时,甚至使用StampedLock
.
在这里你可以看到如何使用 Java 锁。您所说的“锁定事务正在使用的数据”非常含糊,您不能阻止整个对象 AFAIK,您可以阻止该对象的各个部分,一次只能通过一个线程。无论如何,如果您不想在类方法上使用锁,您可以创建第二个列表,一个已使用的对象 ID 列表,并且无法通过其他事务获取,您可以将其与lamport bakery结合使用algorithm,或将需要该对象的事务添加到队列的简单代码;
List<Object> objects = new ArrayList<>();
List<Integer> objectIds = new ArrayList<>();
Queue<Integer> transactionIds = new PriorityQueue<>();
// code ...
// suppose this is a transaction that run on a thread, and can access our lists
public void doUpdateOnObject() {
Object object = objects.get(1);
if (objectsIds.indexOf(object) > 0) {
transactionIds.add(this.id) // this transactionId
while(transactionIds.peek() != this.id) { // if you aren't the next, wait
Thread.sleep(400);
}
}
objectIds.add(object.getId());
// here change object fields or whatever;
objectIds.remove(object.getId());
}
实际上,您的示例工作正常,因为它使用您要锁定的对象作为监视器,因此当一个线程位于同步块内时,没有其他线程可以访问它。
推荐阅读
- reactjs - 我可以包括
材质 UI 中的菜单项 - html - 验证最大最小模式输入
- c++ - CGAL - Surface_mesh_shortest_path - 测地线步行
- javascript - 尝试使用 Vue.js 播放 mp3
- python - 接收 AttributeError: 'NoneType' 对象在使用纸浆时没有属性 'actualSolve'
- pycharm - PyCharm - 找不到设置-工具-Python Scientific
- android - 如何将图像从 url 保存到 Android 应用程序的设备私人文件夹中
- fail2ban - fail2ban 正则表达式中的奇怪之处
- c# - Azure Function to Read & Write to Blob using HTTP Trigger
- python - how to get the multiple csv files on a line graph using Plotly python library to get the results on browser?