我有一个类'ResourceConsumerThread',它扩展了Thread并定义了一些行为。此类的多个实例(即多个线程(将具有不同的行为。我正在尝试通过函数接口(Runnable(传递这些行为,同时创建ResourceConsumerThread类的实例。ResourceConsumerThread 的 run(( 方法只需调用 lambda 的方法 - run((。但是,我的要求是我传递的lambda需要引用它被传递到的ResourceConsumerThread对象。
public class ResourceConsumingThread extends Thread {
//threads which have acquired resources that this thread is asking for.
private List<ResourceConsumingThread> dependencyList;
private List<Resource> acquiredResources;
private List<Resource> requestedResources;
private volatile boolean isDeadlockDetected;
private final String id;
private static int threadIdGenerator;
private final Runnable runnableBody;
private ResourceConsumingThread( Runnable runnableBody) {
this.dependencyList = new ArrayList<>();
this.acquiredResources = new ArrayList<>();
this.requestedResources = new ArrayList<>();
this.id = "T" + threadIdGenerator++;
this.runnableBody = runnableBody;
}
@Override
public void run() {
System.out.println("Running body for thread : " + id);
if(runnableBody != null){
runnableBody.run();
}else{
System.out.println("ERROR...threadBody can't be null.");
}
}
}
此类的用户将像下面这样使用它:
public void callerMethod(){
ResourceConsumingThread t1 = lockManager.createNewThread(new Runnable() {
@Override
public void run() {
lockManager.acquireLockOnResourceForThread(new Resource(), t1);
}
});
}
但是,由于 t1 尚未构建,因此我无法在 run(( 方法中使用它 - 我收到编译器错误。
知道我如何实现这一点,即使它涉及一些设计返工?主要要求是:
- LockManager.acquireLockOnResourceForThread(( 需要知道哪个 ResourceConsumingThread 实例正在请求哪个资源。
- ResourceConsumingThread 的 run(( 方法应该能够在单独的线程中执行不同的逻辑。
更新了我正在尝试的答案(不确定它是否正确(。仍在等待通过社区解决潜在解决方案的其他天使。
final Map<String, Resource> resourceMap = new HashMap<>();
resourceMap.put("R1", new Resource());
final ResourceConsumingThread t1 = new ResourceConsumingThread();
Runnable t1Runnable = new Runnable() {
@Override
public void run() {
lockManager.acquireLockOnResourceForThread(resourceMap.get("R1"), t1);
}
};
t1.setRunnableBody(t1Runnable);
t1.start();
t1.join();
更新(在@Cliff的评论之后(:
ResourceConsumingThread t = lockManager.createNewThread(() -> {
lockManager.acquireLockOnResourceForThread(new Resource(), (ResourceConsumingThread) Thread.currentThread());
});
您可以简单地在匿名内部类中使用this
:
public void callerMethod(){
ResourceConsumingThread t1 = lockManager.createNewThread(new Runnable() {
@Override
public void run() {
lockManager.acquireLockOnResourceForThread(new Resource(), this);
}
});
}
这将传递对callerMethod
中称为t1
的Runnable
的引用。
我建议创建一个函数接口,在其运行方法中接受ResourceConsumingThread。
interface ResourceRunnable {
void run(ResourceConsumingThread resourceThread);
}
这意味着更改 ResourceConsumingThread 的构造函数以接受 ResourceRunnable。然后你可以做:
public void callerMethod(){
ResourceConsumingThread t1 = lockManager.createNewThread(new Runnable() {
@Override
public void run(ResourceConsumingThread resourceThread) {
lockManager.acquireLockOnResourceForThread(new Resource(), resourceThread);
}
});
}
其中 ResourceConsumingThread 会在内部调用 ResourceRunnable.run(this(。
更新:正如我通过评论建议的那样,另一种方法是:
ResourceConsumingThread t = lockManager.createNewThread(() -> {
lockManager.acquireLockOnResourceForThread(new Resource(), (ResourceConsumingThread) Thread.currentThread());
});