Step 2 of 5
40% CompleteEnqueue Operation
Learn how to add elements to a queue
The Enqueue Operation
The enqueue operation adds an element to the rear (end) of the queue. It's like a person joining the back of a line.
When implementing a queue, the enqueue operation is responsible for:
- Adding a new element to the end of the queue
- Updating the rear pointer (if applicable)
- Increasing the size of the queue
Array-based Implementation
In an array-based implementation, the enqueue operation is straightforward. We simply add the new element to the end of the array.
enqueue(element) {// Add element to the end of the arraythis.items.push(element);return this; // For method chaining}
Key Points:
- Time Complexity: O(1) - constant time
- Always adds to the rear of the queue
- Simple to implement using JavaScript's built-in array methods
- May require resizing the array if it has a fixed capacity
Linked List-based Implementation
In a linked list-based implementation, we add a new node to the tail of the linked list.
class Node {constructor(value) {this.value = value;this.next = null;}}class LinkedListQueue {constructor() {this.head = null; // Front of the queuethis.tail = null; // Rear of the queuethis.size = 0;}enqueue(value) {const newNode = new Node(value);// If queue is empty, set both head and tail to the new nodeif (this.isEmpty()) {this.head = newNode;this.tail = newNode;} else {// Otherwise, add to the end and update tailthis.tail.next = newNode;this.tail = newNode;}this.size++;return this;}isEmpty() {return this.size === 0;}}
Key Points:
- Time Complexity: O(1) - constant time
- Requires maintaining both head and tail pointers for efficiency
- Special handling for the first element (when the queue is empty)
- No capacity limitations (can grow as needed)
Circular Queue Implementation
In a circular queue, we use an array with front and rear pointers that wrap around to the beginning when they reach the end. This allows for more efficient use of space.
class CircularQueue {constructor(capacity = 5) {this.items = new Array(capacity);this.capacity = capacity;this.front = 0;this.rear = 0;this.size = 0;}enqueue(element) {// Check if queue is fullif (this.isFull()) {throw new Error("Queue overflow");// Alternatively, resize the queue// this.resize();}// Add element at the rear positionthis.items[this.rear] = element;// Update rear (wrap around if necessary)this.rear = (this.rear + 1) % this.capacity;// Increment sizethis.size++;return this;}isFull() {return this.size === this.capacity;}isEmpty() {return this.size === 0;}}
Key Points:
- Time Complexity: O(1) - constant time
- Uses modulo arithmetic to wrap around the array
- Requires tracking size separately from front and rear pointers
- More efficient space utilization compared to simple array implementation
- Needs to handle the queue being full
Edge Cases and Considerations
Queue Overflow
In fixed-size implementations, you need to handle the case when the queue is full. Options include:
- Throw an error
- Return a failure indicator
- Resize the queue (dynamic array)
- Implement a circular buffer
Performance Considerations
While the enqueue operation is typically O(1), there are some considerations:
- Array resizing can occasionally cause O(n) operations
- Memory allocation for new nodes in linked list implementations
- Cache locality is better in array-based implementations
Practical Example
Let's see a complete example of a queue with the enqueue operation:
class Queue {constructor() {this.items = [];}// Add an element to the queueenqueue(element) {this.items.push(element);return this;}// Check if the queue is emptyisEmpty() {return this.items.length === 0;}// Get the size of the queuesize() {return this.items.length;}}// Usage exampleconst queue = new Queue();console.log("Queue created. Is empty?", queue.isEmpty()); // truequeue.enqueue(10);console.log("After enqueuing 10:", queue.items); // [10]queue.enqueue(20).enqueue(30); // Method chainingconsole.log("After enqueuing 20 and 30:", queue.items); // [10, 20, 30]console.log("Queue size:", queue.size()); // 3
Check Your Understanding
Next Steps
Now that you understand how to add elements to a queue with the enqueue operation, let's move on to learning how to remove elements from a queue with the dequeue operation.