无法在 RejectionHandler 中获取 CallableThread
Unable to get CallableThread in RejectionHandler
我有线程池,它将使用 Callable
个工作线程和 RejectionHandler
。我需要在 RejectionHandler
中获取此 Callable 任务,但无法获取它。
在下面的示例中,我需要为其执行 RejectionHandler 的 Callable 任务的 uniqueId。在 RejecitonHandler
中,Runnable
被强制转换为 FutureTask
,我希望它应该被强制转换为 Callable
工作线程。
请帮助我在 RejectionHandler
中获取 Callable
工作线程实例。
import java.util.Random;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.Callable;
import java.util.concurrent.RejectedExecutionHandler;
import java.util.concurrent.FutureTask;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
public class RejectionDemo {
RejectionDemo(){
Random random = new Random();
ThreadPoolExecutor executor = new ThreadPoolExecutor(1, 1, 1, TimeUnit.SECONDS, new ArrayBlockingQueue<Runnable>(2), new RejectionHandlerImpl());
CallableWorkerThread workers[] =
new CallableWorkerThread[10];
for (int i=0; i< workers.length; i++){
workers[i] = new CallableWorkerThread(random.nextInt(100));
FutureTask<Integer> task = new FutureTask<Integer>(workers[i]);
executor.submit(task);
}
}
public static void main(String args[]){
RejectionDemo demo = new RejectionDemo();
}
public class CallableWorkerThread implements
Callable<Integer> {
private int uniqueId;
CallableWorkerThread(int uniqueId) {
this.uniqueId = uniqueId;
}
public Integer call() {
System.out.println("Unique id="+uniqueId);
return uniqueId;
}
public String toString(){
return ""+uniqueId;
}
}
class RejectionHandlerImpl implements RejectedExecutionHandler{
public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
try{
System.out.println(r);
}catch(Throwable t){
t.printStackTrace();
}
}
}
}
输出
java.util.concurrent.FutureTask@70036428
Unique id=68
java.util.concurrent.FutureTask@6ea4b78b
java.util.concurrent.FutureTask@e3f6d
java.util.concurrent.FutureTask@1ce84763
java.util.concurrent.FutureTask@55a6c368
java.util.concurrent.FutureTask@4e77b794
java.util.concurrent.FutureTask@15b57dcb
Unique id=55
Unique id=83
我期待 CallableWorkerThread 而不是 FutureTask。帮助我获取 WorkerThread 实例。
在你的代码中
workers[i] = new CallableWorkerThread(random.nextInt(100));
FutureTask<Integer> task = new FutureTask<Integer>(workers[i]);
executor.submit(task);
你创建了一个 FutureTask
来包装 CallableWorkerThread
实例但是你正在使用 submit
它接受任意 Runnable
和 returns 一个 FutureTask
包装 Runnable
.
换句话说,您将 FutureTask
包裹在另一个 FutureTask
中。有两种方法可以解决这个问题
使用
workers[i] = new CallableWorkerThread(random.nextInt(100));
executor.submit(workers[i]);
让 ExecutorService
将您的 Callable
包裹在 FutureTask
中。
使用
workers[i] = new CallableWorkerThread(random.nextInt(100));
executor.execute(new FutureTask<Integer>(workers[i]));
手动包装 Callable
并将其作为 Runnable
入队而不进一步包装(注意使用 execute
而不是 submit
)
由于您想启用对原始 Callable
的检索,第二个选项适合您,因为它使您可以完全控制 FutureTask
实例:
static class MyFutureTask<T> extends FutureTask<T> {
final Callable<T> theCallable;
public MyFutureTask(Callable<T> callable) {
super(callable);
theCallable=callable;
}
}
提交代码:
for (int i=0; i< workers.length; i++){
workers[i] = new CallableWorkerThread(random.nextInt(100));
executor.execute(new MyFutureTask<Integer>(workers[i]));
}
拒绝执行处理程序:
class RejectionHandlerImpl implements RejectedExecutionHandler{
public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
if(r instanceof MyFutureTask) {
MyFutureTask<?> myFutureTask = (MyFutureTask)r;
Callable<?> c=myFutureTask.theCallable;
System.out.println(c);
}
else System.out.println(r);
}
}
我有线程池,它将使用 Callable
个工作线程和 RejectionHandler
。我需要在 RejectionHandler
中获取此 Callable 任务,但无法获取它。
在下面的示例中,我需要为其执行 RejectionHandler 的 Callable 任务的 uniqueId。在 RejecitonHandler
中,Runnable
被强制转换为 FutureTask
,我希望它应该被强制转换为 Callable
工作线程。
请帮助我在 RejectionHandler
中获取 Callable
工作线程实例。
import java.util.Random;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.Callable;
import java.util.concurrent.RejectedExecutionHandler;
import java.util.concurrent.FutureTask;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
public class RejectionDemo {
RejectionDemo(){
Random random = new Random();
ThreadPoolExecutor executor = new ThreadPoolExecutor(1, 1, 1, TimeUnit.SECONDS, new ArrayBlockingQueue<Runnable>(2), new RejectionHandlerImpl());
CallableWorkerThread workers[] =
new CallableWorkerThread[10];
for (int i=0; i< workers.length; i++){
workers[i] = new CallableWorkerThread(random.nextInt(100));
FutureTask<Integer> task = new FutureTask<Integer>(workers[i]);
executor.submit(task);
}
}
public static void main(String args[]){
RejectionDemo demo = new RejectionDemo();
}
public class CallableWorkerThread implements
Callable<Integer> {
private int uniqueId;
CallableWorkerThread(int uniqueId) {
this.uniqueId = uniqueId;
}
public Integer call() {
System.out.println("Unique id="+uniqueId);
return uniqueId;
}
public String toString(){
return ""+uniqueId;
}
}
class RejectionHandlerImpl implements RejectedExecutionHandler{
public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
try{
System.out.println(r);
}catch(Throwable t){
t.printStackTrace();
}
}
}
}
输出
java.util.concurrent.FutureTask@70036428
Unique id=68
java.util.concurrent.FutureTask@6ea4b78b
java.util.concurrent.FutureTask@e3f6d
java.util.concurrent.FutureTask@1ce84763
java.util.concurrent.FutureTask@55a6c368
java.util.concurrent.FutureTask@4e77b794
java.util.concurrent.FutureTask@15b57dcb
Unique id=55
Unique id=83
我期待 CallableWorkerThread 而不是 FutureTask。帮助我获取 WorkerThread 实例。
在你的代码中
workers[i] = new CallableWorkerThread(random.nextInt(100));
FutureTask<Integer> task = new FutureTask<Integer>(workers[i]);
executor.submit(task);
你创建了一个 FutureTask
来包装 CallableWorkerThread
实例但是你正在使用 submit
它接受任意 Runnable
和 returns 一个 FutureTask
包装 Runnable
.
换句话说,您将 FutureTask
包裹在另一个 FutureTask
中。有两种方法可以解决这个问题
使用
workers[i] = new CallableWorkerThread(random.nextInt(100)); executor.submit(workers[i]);
让
ExecutorService
将您的Callable
包裹在FutureTask
中。使用
workers[i] = new CallableWorkerThread(random.nextInt(100)); executor.execute(new FutureTask<Integer>(workers[i]));
手动包装
Callable
并将其作为Runnable
入队而不进一步包装(注意使用execute
而不是submit
)
由于您想启用对原始 Callable
的检索,第二个选项适合您,因为它使您可以完全控制 FutureTask
实例:
static class MyFutureTask<T> extends FutureTask<T> {
final Callable<T> theCallable;
public MyFutureTask(Callable<T> callable) {
super(callable);
theCallable=callable;
}
}
提交代码:
for (int i=0; i< workers.length; i++){
workers[i] = new CallableWorkerThread(random.nextInt(100));
executor.execute(new MyFutureTask<Integer>(workers[i]));
}
拒绝执行处理程序:
class RejectionHandlerImpl implements RejectedExecutionHandler{
public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
if(r instanceof MyFutureTask) {
MyFutureTask<?> myFutureTask = (MyFutureTask)r;
Callable<?> c=myFutureTask.theCallable;
System.out.println(c);
}
else System.out.println(r);
}
}