Pseudocode | Description |
---|---|
enqueue | Adds a new entry to the back of the queue |
dequeue | Removes and returns the entry at the front of the queue |
getFront | Retrieves the queue’s front entry without changing the queue |
isEmpty | Detects whether the queue is empty |
clear | Removes all entries from the queue |
Note: Improving performance in implementation
- If you keep references to the first and last nodes, you can make additions and removals take O(1).
Remember: Client can only see and remove the entry at the front of the queue!
Example: Queue Interface
public interface QueueInterface<T> { void enqueue(T: newEntry); dequeue(); T getFront(); T boolean isEmpty(); void clear(); }
Responsibilities:
Collaboration:
Remember: Random Number Generation
- We can generate a floating-point between 0—1.
- So, to pick something 80% of the time, we simply check if the random number is \le 0.8
Queue
Methods:
add()
offer()
remove()
poll()
element()
peek()
isEmpty()
size()
boolean add(T newEntry);
boolean offer(T newEntry);
remove();
T poll();
T element();
T peek();
T void isEmpty();
int clearSize();
Deque: Double-ended queue.
Example:
- Deque is used in the real-world to provide undo functionality.
Example: Private Node inner-class with next and previous pointers
private class Node<T> { private T data; private Node next; private Node prev; private Node (T data) { this(data, null, null) } private Node (T data, Node next, Node prev) { this.data = data; this.next = next; this.prev = prev; } }
Example: Interface
public interface DequeInterface<T> { boolean addToFront(T newEntry); boolean addToBack(T newEntry); boolean removeFront(); boolean removeBack(); getFront(); T getBack(); T boolean isEmpty(); void clear(); }
Queue
Methods:
addFirst
, offerFirst
addLast
, offerLast
removeFirst
, pollFirst
removeLast
, pollLast
getFirst
, peekFirst
getLast
, peekLast
isEmpty
, clear
, size
push
, pop
ArrayDeque
ArrayDeque()
ArrayDeque(int initialCapacity)
Note: A better data structure to implement the deque would be a doubly-linked list.
Priority Queue: Organizes objects according to their priorities.
Note: The definition of “priority” depends on the nature of the items in the queue.
Note: Well be using priority queue (and other ADTs) for the final project (implementing Dijkstra’s algorithm)
Example: Priority Queue Interface
public interface PriorityQueueInterface<T> extends Comparable<? super T> { void add(T newEntry); remove(); T peek(); T boolean isEmpty(); int getSize(); void clear(); }
- Note:
Comparable<? super T>
- Means that we want the generic object (or its super class) to implement the
Comparable
method.
Example: Priority queue based on lexical graphical order
<String> myQueue = newLinkedPriorityQueue<>(); PriorityQueueInterface.add("Jane"); myQueue.add("Jess"); myQueue.add("Jill"); myQueue.add("Jim"); myQueue.remove(); myQueue// Remaining Entries: // Jess // Jill // Jim
Methods:
add
offer
remove
poll
element
peek
isEmpty
clear
size
Note: Uses a heap.
(Singly) Linked Implementation:
null
.Circular Array Implementation:
frontIndex
: Where we enqueuebackIndex
: Where we dequeuecount
: Keeps track of how many entries we have.isEmpty
much easier.count
is equal to the array’s length, the queue is full.%
) to find indices.Remember: A queue is not a bag, it’s not supposed to be used for storage, we use it because we want to take things out.
- tl;dr We use a queue when we have a producer* and consumer of data (e.g., keyboard input).*
Circular Linked Implementation:
Doubly-Linked Implementation:
next
node and previous
node.One way to implement a priority queue is to use an array of queue.