A queue is like a waiting list.
Imagine you’re waiting in line to buy the latest Apple product, getting a movie ticket, or to pay for your groceries.
These are queues!
You can use queues in your Ruby projects.
How?
Queues allow you to process things in order of arrival, so they can be helpful for anything that requires things to be given priority the longer they have been waiting for.
You can apply this to:
- Model a real-world queue
- Implement algorithms like Breadth-First Search (BFS)
- Control access to a shared resource, like CPU, disks, printers, etc.
Now…
Let’s see some code!
How To Implement A Queue in Ruby
An array can behave like a Queue
if you use the right methods.
These methods are:
unshift
(orprepend
with Ruby 2.5+)pop
When you unshift
, you are adding one item to the queue.
Example:
queue = [] queue.unshift "apple" queue.unshift "orange" queue.unshift "banana" # ["banana", "orange", "apple"]
When you pop
, you remove the last item from the queue.
This is the next item that should be processed.
Example:
queue.pop # "apple" queue.pop # "orange"
You can look at the last item, to see “who’s next” without removing this item.
Example:
queue[-1] # "banana"
This operation is called peek
.
Ruby Concurrent Queue
Ruby has a proper thread-safe, blocking, Queue
class.
You can use this queue for coordinating work in a multi-threaded program.
Example:
que = Queue.new que << 1 que << 2 que << 3
You can get an item off this queue with pop
:
que.pop # 1 que.pop # 2
If the queue is empty, calling pop
will put your current thread to sleep & wait until something is added to the queue.
That’s what it means to “block”.
You can avoid blocking by passing true
to pop
:
que.pop(true)
This will raise a ThreadError: queue empty
exception when the queue is empty.
How to Use A Sized Queue
A sized queue is the same as a regular queue but with a size limit.
Example:
que = SizedQueue.new(5)
When the queue is full, the push
(same as <<
) operation will suspend the current thread until an item is taken off the queue.
Example:
que.push(:bacon)
You can choose to raise an exception instead, passing true
as an argument:
que.push(:bacon, true)
This raises ThreadError: queue full
.
Video Tutorial
Summary
You’ve learned about Ruby queues!
You can use a queue when you need to process work in FIFO (first-in-first-out) order. There are two ways to implement a queue, using an array, or using the Queue
class.
Thanks for reading. 🙂
I didn’t know sized queue. Very helpful article.
Thanks!
Great! Good to know you found it helpful 🙂
Your posts are very elegant to read! Thanks!
Thanks for your comment! That’s exactly what I want to do, to write the easiest to understand & most enjoyable articles of any tech site 🙂
You always provide great content, simple enough to digest. With so much to learn, you present the knowledge in digestible chunks. Thanks man, good work.
Thanks for reading 🙂
Hey Jesus, can you please tell me why bacon has : in front of it when you push it to the queue?
The code is
que.push(:bacon)
Yes! This
:bacon
is called a symbol, it’s a kind of Ruby object like a string.