AbstractList.java (SubList): Make it a top-level private class.
2000-11-03 Bryce McKinlay <bryce@albatross.co.nz> * java/util/AbstractList.java (SubList): Make it a top-level private class. * java/util/LinkedList.java (remove): Do update modCount and knownMod. (add): Ditto. * Makefile.am (ordinary_java_source_files): Add LinkedList.java. * Makefile.in: Rebuilt. From-SVN: r37218
This commit is contained in:
parent
19944601d6
commit
8d218b6742
5 changed files with 284 additions and 275 deletions
|
@ -309,232 +309,230 @@ public abstract class AbstractList extends AbstractCollection implements List
|
|||
knownMod++;
|
||||
}
|
||||
} // AbstractList.Iterator
|
||||
|
||||
static class SubList extends AbstractList
|
||||
{
|
||||
private AbstractList backingList;
|
||||
private int offset;
|
||||
private int size;
|
||||
|
||||
public SubList(AbstractList backing, int fromIndex, int toIndex)
|
||||
{
|
||||
backingList = backing;
|
||||
// FIXME: The `this' prefixes in this class are a workaround for a
|
||||
// gcj bug. They should be removed later.
|
||||
this.modCount = backingList.modCount;
|
||||
offset = fromIndex;
|
||||
size = toIndex - fromIndex;
|
||||
}
|
||||
|
||||
/**
|
||||
* This method checks the two modCount fields to ensure that there has
|
||||
* not been a concurrent modification. It throws an exception if there
|
||||
* has been, and otherwise returns normally.
|
||||
* Note that since this method is private, it will be inlined.
|
||||
*
|
||||
* @exception ConcurrentModificationException if there has been a
|
||||
* concurrent modification.
|
||||
*/
|
||||
private void checkMod()
|
||||
{
|
||||
if (this.modCount != backingList.modCount)
|
||||
throw new ConcurrentModificationException();
|
||||
}
|
||||
|
||||
/**
|
||||
* This method checks that a value is between 0 and size (inclusive). If
|
||||
* it is not, an exception is thrown.
|
||||
* Note that since this method is private, it will be inlined.
|
||||
*
|
||||
* @exception IndexOutOfBoundsException if the value is out of range.
|
||||
*/
|
||||
private void checkBoundsInclusive(int index)
|
||||
{
|
||||
if (index < 0 || index > size)
|
||||
throw new IndexOutOfBoundsException("Index: " + index + ", Size:" +
|
||||
size);
|
||||
}
|
||||
|
||||
/**
|
||||
* This method checks that a value is between 0 (inclusive) and size
|
||||
* (exclusive). If it is not, an exception is thrown.
|
||||
* Note that since this method is private, it will be inlined.
|
||||
*
|
||||
* @exception IndexOutOfBoundsException if the value is out of range.
|
||||
*/
|
||||
private void checkBoundsExclusive(int index)
|
||||
{
|
||||
if (index < 0 || index >= size)
|
||||
throw new IndexOutOfBoundsException("Index: " + index + ", Size:" +
|
||||
size);
|
||||
}
|
||||
|
||||
public int size()
|
||||
{
|
||||
checkMod();
|
||||
return size;
|
||||
}
|
||||
|
||||
public Object set(int index, Object o)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsExclusive(index);
|
||||
o = backingList.set(index + offset, o);
|
||||
return o;
|
||||
}
|
||||
|
||||
public Object get(int index)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsExclusive(index);
|
||||
return backingList.get(index + offset);
|
||||
}
|
||||
|
||||
public void add(int index, Object o)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsInclusive(index);
|
||||
backingList.add(index + offset, o);
|
||||
this.modCount++;
|
||||
size++;
|
||||
}
|
||||
|
||||
public Object remove(int index)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsExclusive(index);
|
||||
Object o = backingList.remove(index + offset);
|
||||
this.modCount++;
|
||||
size--;
|
||||
return o;
|
||||
}
|
||||
|
||||
public void removeRange(int fromIndex, int toIndex)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsExclusive(fromIndex);
|
||||
checkBoundsInclusive(toIndex);
|
||||
|
||||
// this call will catch the toIndex < fromIndex condition
|
||||
backingList.removeRange(offset + fromIndex, offset + toIndex);
|
||||
this.modCount = backingList.modCount;
|
||||
size -= toIndex - fromIndex;
|
||||
}
|
||||
|
||||
public boolean addAll(int index, Collection c)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsInclusive(index);
|
||||
int csize = c.size();
|
||||
boolean result = backingList.addAll(offset + index, c);
|
||||
this.modCount = backingList.modCount;
|
||||
size += csize;
|
||||
return result;
|
||||
}
|
||||
|
||||
public Iterator iterator()
|
||||
{
|
||||
return listIterator(0);
|
||||
}
|
||||
|
||||
public ListIterator listIterator(final int index)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsInclusive(index);
|
||||
|
||||
return new ListIterator()
|
||||
{
|
||||
ListIterator i = backingList.listIterator(index + offset);
|
||||
int position = index;
|
||||
|
||||
public boolean hasNext()
|
||||
{
|
||||
checkMod();
|
||||
return position < size;
|
||||
}
|
||||
|
||||
public boolean hasPrevious()
|
||||
{
|
||||
checkMod();
|
||||
return position > 0;
|
||||
}
|
||||
|
||||
public Object next()
|
||||
{
|
||||
if (position < size)
|
||||
{
|
||||
Object o = i.next();
|
||||
position++;
|
||||
return o;
|
||||
}
|
||||
else
|
||||
throw new NoSuchElementException();
|
||||
}
|
||||
|
||||
public Object previous()
|
||||
{
|
||||
if (position > 0)
|
||||
{
|
||||
Object o = i.previous();
|
||||
position--;
|
||||
return o;
|
||||
}
|
||||
else
|
||||
throw new NoSuchElementException();
|
||||
}
|
||||
|
||||
public int nextIndex()
|
||||
{
|
||||
return offset + i.nextIndex();
|
||||
}
|
||||
|
||||
public int previousIndex()
|
||||
{
|
||||
return offset + i.previousIndex();
|
||||
}
|
||||
|
||||
public void remove()
|
||||
{
|
||||
i.remove();
|
||||
// FIXME: Uncomment the following line once the compiler is fixed.
|
||||
//SubList.this.modCount++;
|
||||
size--;
|
||||
position = nextIndex();
|
||||
}
|
||||
|
||||
public void set(Object o)
|
||||
{
|
||||
i.set(o);
|
||||
}
|
||||
|
||||
public void add(Object o)
|
||||
{
|
||||
i.add(o);
|
||||
// FIXME: Uncomment the following line once the compiler is fixed.
|
||||
//SubList.this.modCount++;
|
||||
size++;
|
||||
position++;
|
||||
}
|
||||
|
||||
// Here is the reason why the various modCount fields are mostly
|
||||
// ignored in this wrapper listIterator.
|
||||
// IF the backing listIterator is failfast, then the following holds:
|
||||
// Using any other method on this list will call a corresponding
|
||||
// method on the backing list *after* the backing listIterator
|
||||
// is created, which will in turn cause a ConcurrentModException
|
||||
// when this listIterator comes to use the backing one. So it is
|
||||
// implicitly failfast.
|
||||
// If the backing listIterator is NOT failfast, then the whole of
|
||||
// this list isn't failfast, because the modCount field of the
|
||||
// backing list is not valid. It would still be *possible* to
|
||||
// make the iterator failfast wrt modifications of the sublist
|
||||
// only, but somewhat pointless when the list can be changed under
|
||||
// us.
|
||||
// Either way, no explicit handling of modCount is needed.
|
||||
// However modCount++ must be executed in add and remove, and size
|
||||
// must also be updated in these two methods, since they do not go
|
||||
// through the corresponding methods of the subList.
|
||||
};
|
||||
}
|
||||
} // AbstractList.SubList
|
||||
}
|
||||
|
||||
|
||||
|
||||
class SubList extends AbstractList
|
||||
{
|
||||
private AbstractList backingList;
|
||||
private int offset;
|
||||
private int size;
|
||||
|
||||
public SubList(AbstractList backing, int fromIndex, int toIndex)
|
||||
{
|
||||
backingList = backing;
|
||||
modCount = backingList.modCount;
|
||||
offset = fromIndex;
|
||||
size = toIndex - fromIndex;
|
||||
}
|
||||
|
||||
/**
|
||||
* This method checks the two modCount fields to ensure that there has
|
||||
* not been a concurrent modification. It throws an exception if there
|
||||
* has been, and otherwise returns normally.
|
||||
* Note that since this method is private, it will be inlined.
|
||||
*
|
||||
* @exception ConcurrentModificationException if there has been a
|
||||
* concurrent modification.
|
||||
*/
|
||||
private void checkMod()
|
||||
{
|
||||
if (modCount != backingList.modCount)
|
||||
throw new ConcurrentModificationException();
|
||||
}
|
||||
|
||||
/**
|
||||
* This method checks that a value is between 0 and size (inclusive). If
|
||||
* it is not, an exception is thrown.
|
||||
* Note that since this method is private, it will be inlined.
|
||||
*
|
||||
* @exception IndexOutOfBoundsException if the value is out of range.
|
||||
*/
|
||||
private void checkBoundsInclusive(int index)
|
||||
{
|
||||
if (index < 0 || index > size)
|
||||
throw new IndexOutOfBoundsException("Index: " + index + ", Size:" +
|
||||
size);
|
||||
}
|
||||
|
||||
/**
|
||||
* This method checks that a value is between 0 (inclusive) and size
|
||||
* (exclusive). If it is not, an exception is thrown.
|
||||
* Note that since this method is private, it will be inlined.
|
||||
*
|
||||
* @exception IndexOutOfBoundsException if the value is out of range.
|
||||
*/
|
||||
private void checkBoundsExclusive(int index)
|
||||
{
|
||||
if (index < 0 || index >= size)
|
||||
throw new IndexOutOfBoundsException("Index: " + index + ", Size:" +
|
||||
size);
|
||||
}
|
||||
|
||||
public int size()
|
||||
{
|
||||
checkMod();
|
||||
return size;
|
||||
}
|
||||
|
||||
public Object set(int index, Object o)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsExclusive(index);
|
||||
o = backingList.set(index + offset, o);
|
||||
return o;
|
||||
}
|
||||
|
||||
public Object get(int index)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsExclusive(index);
|
||||
return backingList.get(index + offset);
|
||||
}
|
||||
|
||||
public void add(int index, Object o)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsInclusive(index);
|
||||
backingList.add(index + offset, o);
|
||||
this.modCount++;
|
||||
size++;
|
||||
}
|
||||
|
||||
public Object remove(int index)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsExclusive(index);
|
||||
Object o = backingList.remove(index + offset);
|
||||
this.modCount++;
|
||||
size--;
|
||||
return o;
|
||||
}
|
||||
|
||||
public void removeRange(int fromIndex, int toIndex)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsExclusive(fromIndex);
|
||||
checkBoundsInclusive(toIndex);
|
||||
|
||||
// this call will catch the toIndex < fromIndex condition
|
||||
backingList.removeRange(offset + fromIndex, offset + toIndex);
|
||||
this.modCount = backingList.modCount;
|
||||
size -= toIndex - fromIndex;
|
||||
}
|
||||
|
||||
public boolean addAll(int index, Collection c)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsInclusive(index);
|
||||
int csize = c.size();
|
||||
boolean result = backingList.addAll(offset + index, c);
|
||||
this.modCount = backingList.modCount;
|
||||
size += csize;
|
||||
return result;
|
||||
}
|
||||
|
||||
public Iterator iterator()
|
||||
{
|
||||
return listIterator(0);
|
||||
}
|
||||
|
||||
public ListIterator listIterator(final int index)
|
||||
{
|
||||
checkMod();
|
||||
checkBoundsInclusive(index);
|
||||
|
||||
return new ListIterator()
|
||||
{
|
||||
ListIterator i = backingList.listIterator(index + offset);
|
||||
int position = index;
|
||||
|
||||
public boolean hasNext()
|
||||
{
|
||||
checkMod();
|
||||
return position < size;
|
||||
}
|
||||
|
||||
public boolean hasPrevious()
|
||||
{
|
||||
checkMod();
|
||||
return position > 0;
|
||||
}
|
||||
|
||||
public Object next()
|
||||
{
|
||||
if (position < size)
|
||||
{
|
||||
Object o = i.next();
|
||||
position++;
|
||||
return o;
|
||||
}
|
||||
else
|
||||
throw new NoSuchElementException();
|
||||
}
|
||||
|
||||
public Object previous()
|
||||
{
|
||||
if (position > 0)
|
||||
{
|
||||
Object o = i.previous();
|
||||
position--;
|
||||
return o;
|
||||
}
|
||||
else
|
||||
throw new NoSuchElementException();
|
||||
}
|
||||
|
||||
public int nextIndex()
|
||||
{
|
||||
return offset + i.nextIndex();
|
||||
}
|
||||
|
||||
public int previousIndex()
|
||||
{
|
||||
return offset + i.previousIndex();
|
||||
}
|
||||
|
||||
public void remove()
|
||||
{
|
||||
i.remove();
|
||||
modCount++;
|
||||
size--;
|
||||
position = nextIndex();
|
||||
}
|
||||
|
||||
public void set(Object o)
|
||||
{
|
||||
i.set(o);
|
||||
}
|
||||
|
||||
public void add(Object o)
|
||||
{
|
||||
i.add(o);
|
||||
modCount++;
|
||||
size++;
|
||||
position++;
|
||||
}
|
||||
|
||||
// Here is the reason why the various modCount fields are mostly
|
||||
// ignored in this wrapper listIterator.
|
||||
// IF the backing listIterator is failfast, then the following holds:
|
||||
// Using any other method on this list will call a corresponding
|
||||
// method on the backing list *after* the backing listIterator
|
||||
// is created, which will in turn cause a ConcurrentModException
|
||||
// when this listIterator comes to use the backing one. So it is
|
||||
// implicitly failfast.
|
||||
// If the backing listIterator is NOT failfast, then the whole of
|
||||
// this list isn't failfast, because the modCount field of the
|
||||
// backing list is not valid. It would still be *possible* to
|
||||
// make the iterator failfast wrt modifications of the sublist
|
||||
// only, but somewhat pointless when the list can be changed under
|
||||
// us.
|
||||
// Either way, no explicit handling of modCount is needed.
|
||||
// However modCount++ must be executed in add and remove, and size
|
||||
// must also be updated in these two methods, since they do not go
|
||||
// through the corresponding methods of the subList.
|
||||
};
|
||||
}
|
||||
} // SubList
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue