gcc/libjava/java/util/Vector.java

462 lines
10 KiB
Java
Raw Normal View History

/* Copyright (C) 1998, 1999, 2000 Free Software Foundation
1999-04-07 22:42:40 +08:00
This file is part of libgcj.
This software is copyrighted work licensed under the terms of the
Libgcj License. Please consult the file "LIBGCJ_LICENSE" for
details. */
package java.util;
import java.io.Serializable;
/**
* @author Warren Levy <warrenl@cygnus.com>
* @date August 17, 1998.
*/
/* Written using "Java Class Libraries", 2nd edition, ISBN 0-201-31002-3
* "The Java Language Specification", ISBN 0-201-63451-1
* plus online API docs for JDK 1.2 beta from http://www.javasoft.com.
* Status: Believed complete and correct
*/
final class VectorEnumeration implements Enumeration
1999-04-07 22:42:40 +08:00
{
private int enumIndex;
private Vector enumVec;
public VectorEnumeration(Vector vec)
{
enumVec = vec;
enumIndex = 0;
}
public boolean hasMoreElements()
{
return enumIndex < enumVec.size();
}
public Object nextElement()
{
if (! (enumIndex < enumVec.size()))
1999-04-07 22:42:40 +08:00
throw new NoSuchElementException();
return enumVec.elementData[enumIndex++];
}
}
// TODO12:
// public class Vector extends AbstractList
// implements List, Cloneable, Serializable
public class Vector implements Cloneable, Serializable
{
/* The size of the increment to use when growing this vector.
The default of 0 means to double the capacity when growing. */
protected int capacityIncrement;
/* The number of elements currently in elementData */
protected int elementCount;
/* The buffer in which elements of this vector are stored */
protected Object[] elementData;
public Vector()
{
this(10, 0);
}
public Vector(int initCap)
{
this(initCap, 0);
}
public Vector(int initCap, int capIncrement)
{
if (initCap < 0)
throw new IllegalArgumentException ();
elementData = new Object[initCap];
capacityIncrement = capIncrement;
elementCount = 0;
}
public final synchronized void addElement(Object obj)
{
// Make sure there's room for a new element
if (elementCount == elementData.length)
ensureCapacity(elementCount+1);
elementData[elementCount++] = obj;
}
public final int capacity()
{
return elementData.length;
}
public synchronized Object clone()
{
// New vector needs to have same size, capacity and capacityIncrement
Vector newVec = new Vector(elementData.length, capacityIncrement);
System.arraycopy(elementData, 0, newVec.elementData, 0, elementCount);
newVec.elementCount = elementCount;
return newVec;
}
public final boolean contains(Object obj)
{
for (int i = 0; i < elementCount; i++)
{
if (obj == null
? elementData[i] == null
: obj.equals(elementData[i]))
return true;
}
return false;
}
public final synchronized void copyInto(Object[] objArray)
{
System.arraycopy(elementData, 0, objArray, 0, elementCount);
}
public final synchronized Object elementAt(int idx)
{
if (idx < 0 || idx >= size())
throw new ArrayIndexOutOfBoundsException();
return elementData[idx];
}
public final synchronized Enumeration elements()
{
return new VectorEnumeration(this);
}
public final synchronized void ensureCapacity(int minCap)
{
// Increasing the vector could make it much larger than minCap;
// e.g. if minCap is just larger than the vector, size may double.
// If someone cares about this possibility they should set capacityIncrement
if (minCap > elementData.length)
{
// Increase the vector; double it if capacityIncrement is zero
int newSize = elementData.length;
newSize +=
(capacityIncrement > 0) ? capacityIncrement : elementData.length;
// Make sure newSize is at least minCap
if (newSize < minCap)
newSize = minCap;
Object[] newArray = new Object[newSize];
System.arraycopy(elementData, 0, newArray, 0, elementCount);
elementData = newArray;
}
}
public final synchronized Object firstElement()
{
if (elementCount == 0)
throw new NoSuchElementException();
return elementData[0];
}
public final int indexOf(Object obj)
{
return indexOf(obj, 0);
}
public final synchronized int indexOf(Object obj, int idx)
{
if (idx < 0)
throw new IllegalArgumentException ();
for (int i = idx; i < elementCount; i++)
{
if (obj == null
? elementData[i] == null
: obj.equals(elementData[i]))
return i;
}
return -1;
}
public final synchronized void insertElementAt(Object obj, int idx)
{
if (idx < 0 || idx > size())
throw new ArrayIndexOutOfBoundsException();
else if (idx == size()) // Spec says just use addElement()
addElement(obj);
else
{
// Make sure there's room for a new element
if (elementCount == elementData.length)
ensureCapacity(elementCount+1);
// Shift the existing elements up and increment elementCount
for (int i = elementCount++; i > idx; --i)
elementData[i] = elementData[i-1];
elementData[idx] = obj;
}
}
public final boolean isEmpty()
{
return elementCount == 0;
}
public final synchronized Object lastElement()
{
if (elementCount == 0)
throw new NoSuchElementException();
return elementData[elementCount - 1];
}
public final int lastIndexOf(Object obj)
{
return lastIndexOf(obj, size()-1);
}
public final synchronized int lastIndexOf(Object obj, int idx)
{
if (idx < 0)
throw new IllegalArgumentException ();
for (int i = idx; i >= 0; --i)
{
if (obj == null
? elementData[i] == null
: obj.equals(elementData[i]))
return i;
}
return -1;
}
public final synchronized void removeAllElements()
{
// Remove elements now to assist the gc in early cleanup
for (int i = elementCount-1; i >= 0; --i)
elementData[i] = null;
elementCount = 0;
}
public final synchronized boolean removeElement(Object obj)
{
for (int i = 0; i < elementCount; i++)
{
if (obj == null
? elementData[i] == null
: obj.equals(elementData[i]))
{
int j;
// Decrement count first to ensure we don't walk off end of array
--elementCount;
for (j = i; j < elementCount; j++)
elementData[j] = elementData[j+1];
// At this point, j was incrememented and points to old last element
// Remove element now to assist the gc in early cleanup
elementData[j] = null;
return true;
}
}
return false;
}
public final synchronized void removeElementAt(int idx)
{
int i;
if (idx < 0 || idx >= size())
throw new ArrayIndexOutOfBoundsException();
// Decrement count first to ensure we don't walk off the end of the array
--elementCount;
for (i = idx; i < elementCount; i++)
elementData[i] = elementData[i+1];
// At this point, i was incrememented and now points to the old last element
// Remove element now to assist the gc in early cleanup
elementData[i] = null;
}
public final synchronized void setElementAt(Object obj, int idx)
{
if (idx < 0 || idx >= size())
throw new ArrayIndexOutOfBoundsException();
elementData[idx] = obj;
}
public final synchronized void setSize(int newSize)
{
if (newSize < 0)
throw new ArrayIndexOutOfBoundsException();
// Java Lang Spec p. 658 says to remove the excess elements and discard
// when new size is smaller than old size.
// When truncating, we could alternatively just reset elementCount instead
// of freeing up the memory if the spec hadn't specified. The spec makes
// sense though; if someone cares enough to call a setSize() function
// they probably are doing so to free memory.
if (newSize < elementCount)
{
elementCount = newSize;
trimToSize();
}
else if (newSize > elementCount) // Skip == case
{
// TBD: ensureCapacity() may create a vector much larger than newSize;
// do we want to make the vector exactly newSize? Spec is unclear.
ensureCapacity(newSize);
// Make sure to null out new elements of grown vector
for (int i = elementCount; i < newSize; i++)
elementData[i] = null;
elementCount = newSize;
}
}
public final int size()
{
return elementCount;
}
public final synchronized String toString()
{
// Following the Java Lang Spec p. 656
// Prepend first element with open bracket
StringBuffer result = new StringBuffer("[");
if (elementCount > 0) // add first element if one exists
result.append(elementData[0].toString());
// Prepend subsequent elements with ", "
for (int i = 1; i < elementCount; i++)
result.append(", ").append(elementData[i].toString());
// Append last element with closing bracket
result.append("]");
return result.toString();
}
public final synchronized void trimToSize()
{
// Give up excess storage capacity to save memory
//
// Don't bother checking for the case where size() == the capacity of the
// vector since that is a much less likely case; it's more efficient to
// not do the check and lose a bit of performance in that infrequent case
Object[] newArray = new Object[elementCount];
System.arraycopy(elementData, 0, newArray, 0, elementCount);
elementData = newArray;
}
// TODO12:
// public Vector(Collection c)
// {
// }
// TODO12:
// public public boolean add(Object o)
// {
// }
// TODO12:
// public void add(int index, Object element)
// {
// }
// TODO12:
// public boolean addAll(Collection c)
// {
// }
// TODO12:
// public boolean addAll(int index, Collection c)
// {
// }
// TODO12:
// public void clear()
// {
// }
// TODO12:
// public boolean containsAll(Collection c)
// {
// }
// TODO12:
// public boolean equals(Object o)
// {
// }
// TODO12:
// public int hashCode()
// {
// }
// TODO12:
// public Object get(int index)
// {
// }
public synchronized boolean remove(Object o)
{
for (int i = 0; i < elementCount; ++i)
{
if (o == null
? elementData[i] == null
: o.equals (elementData[i]))
{
System.arraycopy (elementData, i, elementData, i + 1,
elementCount - i - 1);
return true;
}
}
return false;
}
1999-04-07 22:42:40 +08:00
// TODO12:
// public Object remove(int index)
// {
// }
// TODO12:
// public boolean removeAll(Collection c)
// {
// }
// TODO12:
// public boolean retainAll(Collection c)
// {
// }
// TODO12:
// public Object set(int index, Object element)
// {
// }
// TODO12:
// public Object[] toArray()
// {
// }
// TODO12:
// public Object[] toArray(Object[] a)
// {
// }
}