我有一个具有某些属性的类(下例中的分区)
class Car {
public String partition;
....
}
我有一个功能
private void doSomething(Car car){
//
Object obj = getLock(car); // should write this function
synchronized (obj){
// do work here
}
}
如果我有 Car 对象的 2 个实例
从 2 个不同的线程调用函数 doSomething。同步块应该只同步具有相同“分区”值的对象。当 2 个汽车对象具有不同的分区键时,它们可以同时进入代码块
我想知道如何编写“getLock”函数。我应该使用一些地图吗
Map<String,Object> ?
是否有更好的方法来防止具有相同属性的 2 个对象进入临界区?
是的,使用 Map
示例实现:
import java.util.HashMap;
import java.util.Map;
class Car {
public String partition;
// ...
}
public class CarManager {
private Map<String, Object> lockMap = new HashMap<>();
private Object getLock(Car car) {
String partition = car.partition;
synchronized (lockMap) {
// Check if a lock object exists for the partition
if (!lockMap.containsKey(partition)) {
// If not, create a new lock object and store it in the map
lockMap.put(partition, new Object());
}
// Return the lock object for the partition
return lockMap.get(partition);
}
}
private void doSomething(Car car) {
Object obj = getLock(car);
synchronized (obj) {
// do work here
}
}
}
如果你确实想使用锁定,我会看一下条纹锁。一些伪代码:
class CarManager{
final Object[] lockStripe = new Object[Runtime.availableProcessors()*4];
public CarManager(){
for(int k=0;k<lockStripe.length;k++){
lockStripe[k]=new Object();
}
}
Object getLock(Car car){
int hash = car.partition.hashCode();
int lockIndex;
if (hash == Integer.MIN_VALUE) {
lockIndex = 0;
} else {
lockIndex = abs(hash) % lockStripe.length;
}
return lockStripe[lockIndex];
}
public void doSomething(Car car){
synchronized(getLock(car)){
...
}
}
这种方法将确保: