• 作者:老汪软件技巧
  • 发表时间:2024-10-04 07:00
  • 浏览量:

为了构建一个更加复杂的多级反馈队列(Multi-Level Feedback Queue, MLFQ)调度器,我们可以引入一些更高级的调度机制。例如:

不同的时间片策略:每个队列有不同的时间片长度,且不一定是简单的倍数关系。老化机制:防止某个进程在低优先级队列中长期得不到执行(避免饥饿问题)。I/O阻塞与恢复:模拟进程因I/O操作阻塞,并在I/O完成后恢复到适当的优先级队列中。

import java.util.LinkedList;
import java.util.Queue;
import java.util.Random;
class Process {
    String name;
    int burstTime; // 该进程需要的总 CPU 时间
    int remainingTime; // 剩余执行时间
    int currentQueue; // 当前所在的优先级队列
    int waitTime; // 等待时间,用于老化机制
    boolean ioBlocked; // 是否进入 I/O 阻塞状态
    public Process(String name, int burstTime) {
        this.name = name;
        this.burstTime = burstTime;
        this.remainingTime = burstTime;
        this.currentQueue = 0; // 初始在最高优先级队列
        this.waitTime = 0; // 等待时间初始为 0
        this.ioBlocked = false; // 初始时未阻塞
    }
    public boolean isFinished() {
        return remainingTime <= 0;
    }
    public void blockForIO() {
        ioBlocked = true;
        System.out.println("Process " + name + " is blocked for I/O.");
    }
    public void unblockFromIO() {
        ioBlocked = false;
        System.out.println("Process " + name + " has returned from I/O.");
    }
}
public class AdvancedMLFQScheduler {
    private int numQueues; // 队列数量
    private int[] timeQuanta; // 每个队列的时间片
    private Queue[] queues; // 队列数组
    private int maxWaitTime; // 老化机制中的最大等待时间
    @SuppressWarnings("unchecked")
    public AdvancedMLFQScheduler(int numQueues, int[] timeQuanta, int maxWaitTime) {
        this.numQueues = numQueues;
        this.timeQuanta = timeQuanta;
        this.maxWaitTime = maxWaitTime;
        queues = new LinkedList[numQueues];
        for (int i = 0; i < numQueues; i++) {
            queues[i] = new LinkedList<>();
        }
    }
    // 添加进程到最高优先级队列
    public void addProcess(Process process) {
        queues[0].add(process);
    }
    // 模拟调度
    public void schedule() {
        Random random = new Random();
        while (!allQueuesEmpty()) {
            for (int i = 0; i < numQueues; i++) {
                Queue queue = queues[i];
                int quantum = timeQuanta[i];
                while (!queue.isEmpty()) {
                    Process process = queue.poll();
                    // 如果进程被I/O阻塞,跳过它
                    if (process.ioBlocked) {
                        continue;
                    }
                    System.out.println("Executing process: " + process.name + " from queue " + i);
                    // 模拟进程可能触发 I/O 阻塞
                    if (random.nextInt(10) < 2) { // 20% 几率进入 I/O
                        process.blockForIO();
                        continue;
                    }
                    // 该队列分配的时间片
                    int executionTime = Math.min(quantum, process.remainingTime);
                    process.remainingTime -= executionTime;
                    process.waitTime = 0; // 重置等待时间
                    System.out.println("Process " + process.name + " executed for " + executionTime + " units, remaining time: " + process.remainingTime);
                    if (process.isFinished()) {
                        System.out.println("Process " + process.name + " has finished.");
                    } else {
                        // 如果没完成,降级到下一个优先级队列
                        if (i < numQueues - 1) {
                            process.currentQueue = i + 1;
                            queues[i + 1].add(process);
                            System.out.println("Process " + process.name + " moved to queue " + (i + 1));
                        } else {
                            // 如果已经在最低优先级队列,继续留在该队列
                            queues[i].add(process);
                            System.out.println("Process " + process.name + " stays in queue " + i);
                        }
                    }
                    // 模拟 I/O 完成
                    if (!process.ioBlocked && random.nextInt(10) < 1) { // 10% 几率解除 I/O 阻塞
                        process.unblockFromIO();
                    }
                    // 老化机制:检查所有低优先级队列中的进程
                    applyAging(i);
                }
            }
        }
    }
    // 老化机制:如果进程等待时间过长,提升其优先级
    private void applyAging(int currentQueue) {
        for (int i = currentQueue + 1; i < numQueues; i++) {
            Queue queue = queues[i];
            for (Process process : queue) {
                process.waitTime++;
                if (process.waitTime > maxWaitTime) {
                    queue.remove(process);
                    process.currentQueue = i - 1;
                    queues[i - 1].add(process);
                    System.out.println("Process " + process.name + " has been aged and moved to queue " + (i - 1));
                }
            }
        }
    }
    // 检查所有队列是否为空
    private boolean allQueuesEmpty() {
        for (int i = 0; i < numQueues; i++) {
            if (!queues[i].isEmpty()) {
                return false;
            }
        }
        return true;
    }
    public static void main(String[] args) {
        // 定义四个优先级队列,时间片分别为 2、4、8、16,最大等待时间为 10
        int[] timeQuanta = {2, 4, 8, 16};
        AdvancedMLFQScheduler scheduler = new AdvancedMLFQScheduler(4, timeQuanta, 10);
        // 创建一些进程
        Process p1 = new Process("P1", 20);
        Process p2 = new Process("P2", 10);
        Process p3 = new Process("P3", 15);
        Process p4 = new Process("P4", 25);
        // 添加进程到调度器
        scheduler.addProcess(p1);
        scheduler.addProcess(p2);
        scheduler.addProcess(p3);
        scheduler.addProcess(p4);
        // 开始调度
        scheduler.schedule();
    }
}

输出示例

Executing process: P1 from queue 0
Process P1 executed for 2 units, remaining time: 18
Process P1 moved to queue 1
Executing process: P2 from queue 0
Process P2 executed for 2 units, remaining time: 8
Process P2 moved to queue 1
Executing process: P3 from queue 0
Process P3 executed for 2 units, remaining time: 13
Process P3 moved to queue 1
Executing process: P4 from queue 0
Process P4 executed for 2 units, remaining time: 23
Process P4 moved to queue 1
Executing process: P1 from queue 1
Process P1 executed for 4 units, remaining time: 14
Process P1 moved to queue 2
Executing process: P2 from queue 1
Process P2 executed for 4 units, remaining time: 4
Process P2 moved to queue 2
...

_多级反馈队列调度算法c_linux进程调度中的多级反馈队列

代码解释

I/O 阻塞与恢复:

老化机制(Aging):

不同的时间片策略:

调度循环: