CSC 161 Grinnell College Spring, 2009
Imperative Problem Solving and Data Structures

Queues with Arrays


This laboratory exercise introduces the concept of the queue abstract data type and provides experience with an array implementation of this ADT.


Most of this reading is an edited version of Henry M. Walker, Introduction to Computing and Computer Science with Pascal, Little, Brown, and Company, 1986, Sections 17.1, 17.5-17.6, with programming examples translated from Pascal to C. This material is used with permission from the copyright holder.

The Queue Abstract Data Type

The stack abstract data type, described in the lab on Stacks with Arrays, introduced the concept of an abstract data type and discussed the stack as an example that stored and retrieved data in a first-in, last-out (FILO) manner. This lab describes a queue abstract data type that stores and retrieves data in a first-in, first-out (FIFO) manner.

This queue ADT models the checkout counter of a store. A clerk works with one customer at a time, until the customer's bill has been computed and paid. Then the clerk goes on to the next customer. In this situation, while the customer is being served by the clerk, other customers may get into the checkout line to wait for their turn. Normally, customers do not get into line until they have selected all items they wish to buy, and once a customer gets into line, the customer waits until the clerk finishes with those ahead. When we consider this processing at the cash register, we can identify these characteristicss.

  1. Customers wait in a line to be served.
  2. Customers leave the line at one end (the front), when they have been served by the clerk.
  3. Customers enter the line at the other end (the rear).
  4. Occasionally, a line may be empty.

In addition, if a line becomes to long, customers may decide to purchase their items at another time rather than wait in line. In this situation, we might want to specify a maximum size for the queue, and we might want to test if the queue is full.

Unlike stacks where the operational names Push and Pop are standard, the operations for queues are commonly called by several names. For example, the addition of a customer to a queue may be called Enter, Insert, or Enqueue; the leaving of a customer after being served may be called Delete, Remove, or Dequeue. For parallelism in terminology, we use Enqueue and Dequeue here.

More formally, a queue is defined as the abstract data type that has data of a specified type, and operations described as follows:

Normally, queue operations do not allow access to the first or last items on the queue or to any items in the middle. Thus, queues have no equivalent to the Top operation for stacks.

With these operations, queues provide a rather different pattern of data storage and retrieval than we find with stacks. In particular, once an item is placed on a queue, the item is not retrieved until all items ahead of it have already been removed. Here, the first item placed into a queue is the first one processed, and subsequent items must wait for their turn. We say queues provide First-in, First-out (FIFO) storage or Last-in, Last-out (LILO) storage, in contrast to the FILO storage of stacks.

Implementation of Queues by Arrays

As with stacks, one common implementation of a queue involves the use of an array. Although this implementation is reasonably straightforward, a few details require some care.

Our basic approach is fairly simple. We think of an array as extending to the right indefinitely, and we store our data items in order in this array. We use variables first and last to mark where our first element was added and where the last or most recent element was added. The following figure shows this setup, where we have placed four items on the queue. In the figure, item 0 was inserted first, followed by item 1, item 2, and item 3 in that order. The first item is marked by the variable first and the final item added is marked by last.

Conceptual Implementation of a Queue

From this figure, we can trace what happens in our enqueue and dequeue operations. For the enqueue operation, we must add 1 to last to mark a new end for the queue, and insert the specified item at this new location. Similarly, to dequeue, we must return the first item specified, and add 1 to first to to mark the new head of the queue. With this basic picture, we can tell if a queue is empty by checking if first > last. Further, in this figure, the queue has enough space, so it is never full.

In practice, this basic algorithm is complication by the limitation that an array has a finite size; the array does not extend indefinitely to the right. With this limitation, we have two choices.

Adding an element to a Queue a the end
of the Array

Of these two alternatives, the first approach involves much shifting of data and thus is rather inefficient. The second approach allows our code to run much more quickly; however, we do need to be sure that we do not store new items on top of old ones, before the old ones are deleted from the queue. This check can be handled in several ways. One of the easiest is to keep a count of the number of items waiting in the queue. When this number reaches the maximum size of the array, the array is full, and further insertions are impossible. This count also allows us to check if the queue is empty.

Queues in C

As with the implementation of stacks, our implementation of queues in C uses a struct to package together the various variables needed:

#define MaxQueue 50  /* size of all queue arrays */

typedef struct {
   int first;
   int last;
   int count;
   char * queueArray [MaxQueue];
} stringQueue;

Also, in this code, we need to be able to increment first and last by 1 easily, with the first element of the array following the last array element. Using MaxQueue as the size of the array, then this incrementing can be done using modular arithmetic. For example, if myQueue has type stringQueue, then incrementing first would use the statement:

   myQueue.first = (myQueue.first + 1) % MaxQueue;

This document is available on the World Wide Web as

created 28 April 1997
last revised 18 January 2009
Valid HTML 4.01! Valid CSS!
For more information, please contact Henry M. Walker at