Я новичок в многопоточности Java. Я хотел выполнить программу-исполнитель процесса. Каждый процесс содержит от нуля до многих предварительных требований (список строк процесса)

Моя цель - запускать процесс один за другим. И в случае, если предварительные требования к текущему потоку еще не завершены, он будет ждать и возобновить выполнение, как только все его предварительные процессы будут выполнены.

Я не уверен, возможно ли это. Надеюсь, ты сможешь мне помочь. Пожалуйста, помогите мне сделать его более простым и понятным.

Мой текущий вывод программы: поток запускается. Резервное копирование. Запускается. Отчет о передаче. Запуск потока. Отчет об архивировании. Поток работает. Резервное копирование. Ожидает передачи. Отчет. Поток. Ожидание.

Мой ожидаемый результат: поток запускается. Резервное копирование. Начало потока. Отчет о передаче. Поток запускается. Отчет об архивировании. Поток работает. Резервное копирование. Ожидает поток. Отчет. Поток. Ожидание. Тема работает Отчет о передаче Тема завершена Отчет о передаче Добавление отчета о передаче в завершенный процесс. Тема работает Отчет об архиве Тема завершена Отчет об архиве Добавление отчета об архиве в завершенный процесс. == Конец ==

Ниже приведены мои текущие коды:

Основное приложение

public class ThreadApp {

    public static void main(String[] args) {
        List<EODProcess> eodProcesses = new ArrayList<>();
        eodProcesses.add(new EODProcess("Back Up", new ArrayList<String>()));
        eodProcesses.add(new EODProcess("Archive Report", Arrays.asList("Transfer Report")));
        eodProcesses.add(new EODProcess("Transfer Report", Arrays.asList("Back Up")));
        
        int count = eodProcesses.size();
        CountDownLatch latch = new CountDownLatch(count);
        CyclicBarrier barrier = new CyclicBarrier(count);
        ExecutorService pool = Executors.newFixedThreadPool(count);

        List<String> finishedProcess = new ArrayList<>();
        
        for (EODProcess eodProcess : eodProcesses) {
            pool.execute(() -> {
                try {
                    System.out.println("Thread starts " + eodProcess.getProcess());
                    Thread.sleep(1000);
                    
                    // Wait IF
                    // Process Prerequisite is not empty
                    // Process Prerequisite is not yet finished
                    while(!eodProcess.getPrerequisites().isEmpty() ||
                            !finishedProcess.containsAll(eodProcess.getPrerequisites())) {
                        System.out.println("Thread waits " + eodProcess.getProcess());
                        barrier.await();
                    }
                    
                    System.out.println("Thread works " + eodProcess.getProcess());
                    Thread.sleep(1000);
                    System.out.println("Thread finished " + eodProcess.getProcess());
                
                    System.out.println("Adding " + eodProcess.getProcess() + " to finished process.");
                    finishedProcess.add(eodProcess.getProcess());
                    
                } catch (Exception e) {
                    System.err.println("Worker thread inrerrupted " + eodProcess.getProcess());
                } finally {
                    latch.countDown();
                }
            });
        }

        try {
            // wait for the threads to be done
            latch.await();
            System.out.println("== End == ");
        } catch (InterruptedException e) {
            System.err.println("Starting interrupted");
        }
        pool.shutdown();
    }

}

Объект EODProcess

public class EODProcess {

    private String process;
    
    private List<String> prerequisites = new ArrayList<>();
    
    public EODProcess(String process, List<String> prerequisites) {
        this.process = process;
        this.prerequisites.addAll(prerequisites);
    }

    public String getProcess() {
        return process;
    }

    public void setProcess(String process) {
        this.process = process;
    }

    public List<String> getPrerequisites() {
        return prerequisites;
    }

    public void setPrerequisites(List<String> prerequisites) {
        this.prerequisites = prerequisites;
    }

}
0
Jeipz 11 Фев 2021 в 09:51

1 ответ

Лучший ответ

Я упростил свою реализацию. В моем вызываемом объекте я делаю это.

@Override
public String call() throws Exception {
    while (!ThreadApp.finishedProcess.containsAll(eodProcess.getPrerequisites())) {
        System.out.println(eodProcess.getProcess() + " still waiting for prerequisites...");
        Thread.sleep(3000);
    }
    System.out.println(eodProcess.getProcess() + " working...");
    System.out.println(eodProcess.getProcess() + " done!");
    ThreadApp.finishedProcess.add(eodProcess.getProcess());
    return eodProcess.getProcess();
}

Спасибо за вашу помощь!

0
Jeipz 16 Фев 2021 в 05:35