C Programs | IT Developer
IT Developer

C Programs



Share with a Friend

Data Structures in C

Circular Queue Implementation

Here’s a real-world application example built on top of the Circular Queue using Linked List — demonstrating how such a structure is used in Printer Job Scheduling (a common and relatable OS-level application).

C Program: Circular Queue Implementation

Real-World Application: Printer Job Scheduling using Circular Queue (Linked List)

Concept

Modern printers handle multiple print requests in a queue.
Each print job (e.g., a document or file) is stored in a queue, and the printer processes them in order (FIFO).

When one job finishes printing, the next one automatically moves to the front — making a Circular Queue a perfect fit, as the system can continuously cycle through jobs if needed (e.g., in a multi-printer setup).

 

C

#include <stdio.h>

#include <stdlib.h>

#include <string.h>

 

// Structure for a printer job node

struct Job {

    int jobId;

    char fileName[50];

    struct Job *next;

};

 

struct Job *front = NULL;

struct Job *rear = NULL;

int jobCounter = 0;

 

// Function to add a print job to the queue

void addJob(char fileName[]) {

    struct Job *newJob = (struct Job*) malloc(sizeof(struct Job));

    if (newJob == NULL) {

        printf("Memory allocation failed!\n");

        return;

    }

 

    newJob->jobId = ++jobCounter;

    strcpy(newJob->fileName, fileName);

    newJob->next = NULL;

 

    if (front == NULL) {

        front = rear = newJob;

        rear->next = front;

    } else {

        rear->next = newJob;

        rear = newJob;

        rear->next = front;

    }

 

    printf("Print Job Added: [Job ID: %d, File: %s]\n", newJob->jobId, newJob->fileName);

}

 

// Function to process (dequeue) a print job

void processJob() {

    if (front == NULL) {

        printf("No print jobs in the queue.\n");

        return;

    }

 

    struct Job *temp = front;

    printf("Processing Print Job: [Job ID: %d, File: %s]\n", temp->jobId, temp->fileName);

 

    if (front == rear) {

        front = rear = NULL;

    } else {

        front = front->next;

        rear->next = front;

    }

 

    free(temp);

}

 

// Function to view the next job in the queue

void viewNextJob() {

    if (front == NULL) {

        printf("No pending print jobs.\n");

    } else {

        printf("Next Job -> [Job ID: %d, File: %s]\n", front->jobId, front->fileName);

    }

}

 

// Function to display all jobs in the queue

void displayJobs() {

    if (front == NULL) {

        printf("No print jobs in the queue.\n");

        return;

    }

 

    struct Job *temp = front;

    printf("\n--- Print Job Queue ---\n");

    do {

        printf("Job ID: %d | File: %s\n", temp->jobId, temp->fileName);

        temp = temp->next;

    } while (temp != front);

    printf("-----------------------\n");

}

 

int main() {

    int choice;

    char fileName[50];

 

    while (1) {

        printf("\n=== Printer Job Scheduler ===\n");

        printf("1. Add Print Job\n");

        printf("2. Process Next Job\n");

        printf("3. View Next Job\n");

        printf("4. Display All Jobs\n");

        printf("5. Exit\n");

        printf("Enter your choice: ");

        scanf("%d", &choice);

        getchar();  // consume newline

 

        switch (choice) {

            case 1:

                printf("Enter file name to print: ");

                fgets(fileName, sizeof(fileName), stdin);

                fileName[strcspn(fileName, "\n")] = 0;  // remove newline

                addJob(fileName);

                break;

 

            case 2:

                processJob();

                break;

 

            case 3:

                viewNextJob();

                break;

 

            case 4:

                displayJobs();

                break;

 

            case 5:

                printf("Exiting Printer Job Scheduler...\n");

                exit(0);

 

            default:

                printf("Invalid choice. Please try again.\n");

        }

    }

 

    return 0;

}

Output

 
OUTPUT :

=== Printer Job Scheduler ===
1. Add Print Job
2. Process Next Job
3. View Next Job
4. Display All Jobs
5. Exit
Enter your choice: 1
Enter file name to print: Report1.pdf
Print Job Added: [Job ID: 1, File: Report1.pdf]

Enter your choice: 1
Enter file name to print: Invoice.docx
Print Job Added: [Job ID: 2, File: Invoice.docx]

Enter your choice: 4
--- Print Job Queue ---
Job ID: 1 | File: Report1.pdf
Job ID: 2 | File: Invoice.docx
-----------------------

Enter your choice: 3
Next Job -> [Job ID: 1, File: Report1.pdf]

Enter your choice: 2
Processing Print Job: [Job ID: 1, File: Report1.pdf]

Enter your choice: 4
--- Print Job Queue ---
Job ID: 2 | File: Invoice.docx
-----------------------

Key Concepts Demonstrated

Concept

Description

Dynamic Queue

Uses Linked List for flexible job management.

Circular Connection

Rear node connects to front, allowing continuous job cycles.

Real-World Relevance

Models how print spooling and CPU scheduling queues operate.