У меня есть класс, представляющий world
, в котором живут субъекты
public class WorldLifecycle {
private ExecutorService executorService;
public void startWorld() {
executorService = Executors.newFixedThreadPool(Runtime.getRuntime().availableProcessors(),
r -> {
String id = ((IdentifiableRunnable) r).getId();
return new Thread(r, id);
});
}
public void bringLife(LivingPerson ... people) {
Arrays.stream(people).forEach(executorService::submit);
}
public void endWorld() {
executorService.shutdownNow();
try {
executorService.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
} catch (InterruptedException e) {
System.err.println("Failed to finish thread executor!");
}
}
}
Каждый LivingPerson
выглядит следующим образом
public class LivingPerson implements IdentifiableRunnable {
// investigate global world variable
private boolean isRunning = true;
private final StatefulPerson person;
public LivingPerson(StatefulPerson person) {
this.person = person;
}
@Override
public void run() {
System.out.println("Initial state: person=" + person.getRawPerson());
while (isRunning) { // for now forever
try {
Thread.sleep(1000); // do transition every 1 seconds
LifeState state = person.nextState();
System.out.println(getPerson().getName() + " " + state.getActionLabel());
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
}
System.out.println("End state: person=" + person.getRawPerson());
}
@Override
public String getId() {
Person person = getPerson();
return person.getId() + " - " + person.getName();
}
@Override
public void terminate() {
isRunning = false;
}
// returns clone instead of existing
private Person getPerson() {
return person.getRawPerson();
}
}
Я хочу назвать каждую нить с помощьюимя человека и уникальный идентификатор.
IdentifiableRunnable
- это простой интерфейс
public interface IdentifiableRunnable extends Runnable {
String getId();
void terminate();
}
Я инициализирую все так:
WorldLifecycle world = new WorldLifecycle();
LivingPerson male = createPerson("John", 40, Gender.MALE);
LivingPerson female = createPerson("Helen", 25, Gender.FEMALE);
System.out.println("Starting world...");
world.startWorld();
world.bringLife(male, female);
// just wait
try {
Thread.sleep(10000);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
System.out.println("Destroying world...");
world.endWorld();
Но когда я пытаюсь запустить его,Я получаю ошибку
Exception in thread "main" java.lang.ClassCastException: java.util.concurrent.ThreadPoolExecutor$Worker cannot be cast to com.lapots.breed.lifecycle.api.Ide
ntifiableRunnable
at com.lapots.breed.lifecycle.WorldLifecycle.lambda$startWorld$0(WorldLifecycle.java:14)
at java.util.concurrent.ThreadPoolExecutor$Worker.<init>(ThreadPoolExecutor.java:612)
at java.util.concurrent.ThreadPoolExecutor.addWorker(ThreadPoolExecutor.java:925)
at java.util.concurrent.ThreadPoolExecutor.execute(ThreadPoolExecutor.java:1357)
at java.util.concurrent.AbstractExecutorService.submit(AbstractExecutorService.java:112)
at java.util.Spliterators$ArraySpliterator.forEachRemaining(Spliterators.java:948)
at java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:580)
at com.lapots.breed.lifecycle.WorldLifecycle.bringLife(WorldLifecycle.java:20)
at com.lapots.breed.Sandbox.main(Sandbox.java:23)
Как кажется, он не получает мой identifiableRunnable
в ThreadFactory
.Как это решить?