队列在操作系统中的任务调度
在操作系统中,任务调度是一个关键功能,队列常用于管理和调度任务,确保任务按照一定顺序执行。常见的调度算法包括先来先服务(FCFS)、短作业优先(SJF)、轮转调度(RR)等。队列在这些调度算法中的应用主要体现在任务的组织和调度上。
任务调度示例题目
题目1:假设有以下任务到达时间和执行时间,使用FCFS调度算法计算各任务的等待时间和周转时间。
- 任务A:到达时间0,执行时间4
- 任务B:到达时间1,执行时间3
- 任务C:到达时间2,执行时间2
- 任务D:到达时间3,执行时间1
解答:
- 按照到达时间顺序排队:A -> B -> C -> D
- 计算等待时间和周转时间:
- 任务A:等待时间0,周转时间4
- 任务B:等待时间3,周转时间6
- 任务C:等待时间5,周转时间7
- 任务D:等待时间6,周转时间7
题目2:使用RR调度算法(时间片为2)计算各任务的等待时间和周转时间。
- 任务A:到达时间0,执行时间4
- 任务B:到达时间1,执行时间3
- 任务C:到达时间2,执行时间2
- 任务D:到达时间3,执行时间1
解答:
- 按到达时间顺序排队并按照时间片调度:
- 时间0-2:任务A执行,剩余2
- 时间2-4:任务B执行,剩余1
- 时间4-6:任务C执行,完成
- 时间6-7:任务D执行,完成
- 时间7-8:任务A执行,完成
- 时间8-9:任务B执行,完成
- 计算等待时间和周转时间:
- 任务A:等待时间5,周转时间9
- 任务B:等待时间5,周转时间8
- 任务C:等待时间2,周转时间4
- 任务D:等待时间3,周转时间4
树的层次遍历
树的层次遍历(广度优先遍历)是一种按层次顺序遍历树中节点的算法,通常使用队列实现。遍历过程中,从根节点开始,依次访问每层的所有节点。
层次遍历示例题目
题目1:给定一棵二叉树,按层次遍历输出各节点的值。
1
/ \
2 3
/ \ / \
4 5 6 7
解答:
- 初始化队列并将根节点入队。
- 重复以下步骤直到队列为空:
- 从队列中取出一个节点,访问其值并将其子节点入队。
- 遍历顺序:1 -> 2 -> 3 -> 4 -> 5 -> 6 -> 7
代码示例:
c
#include <stdio.h>
#include <stdlib.h>
typedef struct TreeNode {
int val;
struct TreeNode *left, *right;
} TreeNode;
typedef struct QueueNode {
TreeNode *treeNode;
struct QueueNode *next;
} QueueNode;
typedef struct {
QueueNode *front, *rear;
} Queue;
void initQueue(Queue *q) {
q->front = q->rear = NULL;
}
int isEmpty(Queue *q) {
return q->front == NULL;
}
void enqueue(Queue *q, TreeNode *node) {
QueueNode *newNode = (QueueNode *)malloc(sizeof(QueueNode));
newNode->treeNode = node;
newNode->next = NULL;
if (isEmpty(q)) {
q->front = q->rear = newNode;
} else {
q->rear->next = newNode;
q->rear = newNode;
}
}
TreeNode *dequeue(Queue *q) {
if (isEmpty(q)) return NULL;
QueueNode *temp = q->front;
q->front = q->front->next;
if (q->front == NULL) {
q->rear = NULL;
}
TreeNode *treeNode = temp->treeNode;
free(temp);
return treeNode;
}
void levelOrderTraversal(TreeNode *root) {
if (root == NULL) return;
Queue q;
initQueue(&q);
enqueue(&q, root);
while (!isEmpty(&q)) {
TreeNode *current = dequeue(&q);
printf("%d ", current->val);
if (current->left != NULL) enqueue(&q, current->left);
if (current->right != NULL) enqueue(&q, current->right);
}
}
int main() {
TreeNode n1 = {1, NULL, NULL};
TreeNode n2 = {2, NULL, NULL};
TreeNode n3 = {3, NULL, NULL};
TreeNode n4 = {4, NULL, NULL};
TreeNode n5 = {5, NULL, NULL};
TreeNode n6 = {6, NULL, NULL};
TreeNode n7 = {7, NULL, NULL};
n1.left = &n2;
n1.right = &n3;
n2.left = &n4;
n2.right = &n5;
n3.left = &n6;
n3.right = &n7;
levelOrderTraversal(&n1);
return 0;
}
题目2:给定一棵二叉树,按层次遍历输出每层的节点值。
1
/ \
2 3
/ \ \
4 5 6
解答:
- 初始化队列并将根节点入队。
- 重复以下步骤直到队列为空:
- 获取当前队列的长度(表示当前层的节点数)。
- 遍历当前层的所有节点,依次出队并访问其值,同时将其子节点入队。
- 遍历顺序:
- 第一层:1
- 第二层:2 3
- 第三层:4 5 6
队列在操作系统中的任务调度和树的层次遍历中都有重要应用。通过示例题目和解答,我们可以更好地理解队列在这些场景中的具体应用和实现方法。希望这些内容对你理解和应用队列有所帮助。