Data Structures, Algorithms, & Applications in Java
Chapter 11, Exercise 5
The code for the new class is given below. The test program and output are
in the files
SortedArrayList.*.
The codes for the get,
remove,
and
put methods may be speeded by using binary search
in place of the sequential left to right search used
in our code. Doing so will reduce the asymptotic complexity
of the get method from its current
O(size) to O(log size).
The complexity of the remove
and put methods, however, remains
O(size).
public class SortedArrayList implements Dictionary
{
// top-level nested class
protected static class SortedListNode
{
// data members
protected Comparable key;
protected Object element;
// constructors
protected SortedListNode() {}
protected SortedListNode(Object theKey, Object theElement)
{
key = (Comparable) theKey;
element = theElement;
}
}
// data members of SortedList
protected SortedListNode [] element; // array of elements
protected int size; // number of elements in array
// constructors
/** create a list with initial capacity initialCapacity
* throws IllegalArgumentException
* when initialCapacity < 1 */
public SortedArrayList(int initialCapacity)
{
if (initialCapacity < 1)
throw new IllegalArgumentException
("initialCapacity must be >= 1");
// size has the default initial value of 0
element = new SortedListNode [initialCapacity];
}
/** create a list with initial capacity 10 */
public SortedArrayList()
{// use default capacity of 10
this(10);
}
// methods
/** return true iff list is empty */
public boolean isEmpty()
{return size == 0;}
/** return current number of elements in list */
public int size()
{return size;}
/** return element with specified key
* return null if there is no matching element */
public Object get(Object theKey)
{
// search from left to right for matching element
// would be faster to use binary search
int i = 0;
while (i < size && element[i].key.compareTo(theKey) < 0)
i++;
// verify match
if (i >= size || !element[i].key.equals(theKey))
// no matching element
return null;
else
// there is a match
return element[i].element;
}
/** insert an element with the specified key
* overwrite old element if there is already an
* element with the given key
* return old element (if any) with key theKey */
public Object put(Object theKey, Object theElement)
{
// examine elements from left to right
// would be faster to use binary search
int i = 0;
while (i < size && element[i].key.compareTo(theKey) < 0)
i++;
// verify match
if (i < size && element[i].key.equals(theKey))
{// replace old element
Object elementToReturn = element[i].element;
element[i].element = theElement;
return elementToReturn;
}
if (size == element.length)
// no space for new element, double capacity
element = (SortedListNode []) ChangeArrayLength.changeLength1D
(element, 2 * element.length);
// create space for new element by moving
// [i:size - 1] one spot right
System.arraycopy(element, i, element, i + 1, size - i);
// insert at element[i]
element[i] = new SortedListNode(theKey, theElement);
size++;
return null;
}
/** return matching element and remove it
* return null if no matching element */
public Object remove(Object theKey)
{
// search for match with theKey
// would be faster to use binary search
int i = 0;
while (i < size && element[i].key.compareTo(theKey) < 0)
i++;
// verify match
if (i >= size || !element[i].key.equals(theKey))
// no matching element
return null;
// save matching element in e and remove from list
Object removedElement = element[i].element;
System.arraycopy(element, i + 1, element, i, size - i - 1);
size--; // new list size
return removedElement;
}
/** convert to a string */
public String toString()
{
StringBuffer s = new StringBuffer("[");
if (size != 0)
{// nonempty list
// do first element
s.append(element[0].element.toString());
// do remaining elements
for (int i = 1; i < size; i++)
s.append(", " + element[i].element.toString());
}
s.append("]");
// create equivalent String
return new String(s);
}
/** create and return an iterator */
public Iterator iterator()
{return new SortedArrayArrayListIterator();}
private class SortedArrayArrayListIterator implements Iterator
{
// data member
private int nextIndex; // index of next element
// constructor
public SortedArrayArrayListIterator()
{
// nextIndex has the default initial value 0
}
// methods
/** return true iff list has a next element */
public boolean hasNext()
{return nextIndex < size;}
/** return next element in list
* throws NoSuchElementException
* when there is no next element */
public Object next()
{
if (nextIndex < size)
return element[nextIndex++].element;
else
throw new NoSuchElementException("No next element");
}
/** unsupported method */
public void remove()
{
throw new UnsupportedOperationException
("remove not supported");
}
}
}