751 |
return new SubList(this, fromIndex, toIndex); |
return new SubList(this, fromIndex, toIndex); |
752 |
} |
} |
753 |
|
|
|
} // class AbstractList |
|
|
|
|
|
|
|
|
/** |
|
|
* This class follows the implementation requirements set forth in |
|
|
* {@link AbstractList#subList(int, int)}. It matches Sun's implementation |
|
|
* by using a non-public top-level class in the same package. |
|
|
* |
|
|
* @author Original author unknown |
|
|
* @author Eric Blake <ebb9@email.byu.edu> |
|
|
*/ |
|
|
class SubList extends AbstractList |
|
|
{ |
|
|
// Package visible, for use by iterator. |
|
|
/** The original list. */ |
|
|
final AbstractList backingList; |
|
|
/** The index of the first element of the sublist. */ |
|
|
final int offset; |
|
|
/** The size of the sublist. */ |
|
|
int size; |
|
|
|
|
|
/** |
|
|
* Construct the sublist. |
|
|
* |
|
|
* @param backing the list this comes from |
|
|
* @param fromIndex the lower bound, inclusive |
|
|
* @param toIndex the upper bound, exclusive |
|
|
*/ |
|
|
SubList(AbstractList backing, int fromIndex, int toIndex) |
|
|
{ |
|
|
backingList = backing; |
|
|
modCount = backing.modCount; |
|
|
offset = fromIndex; |
|
|
size = toIndex - fromIndex; |
|
|
} |
|
|
|
|
|
/** |
|
|
* This method checks the two modCount fields to ensure that there has |
|
|
* not been a concurrent modification, returning if all is okay. |
|
|
* |
|
|
* @throws ConcurrentModificationException if the backing list has been |
|
|
* modified externally to this sublist |
|
|
*/ |
|
|
// This can be inlined. Package visible, for use by iterator. |
|
|
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. |
|
|
* |
|
|
* @param index the value to check |
|
|
* @throws IndexOutOfBoundsException if index < 0 || index > size() |
|
|
*/ |
|
|
// This will get inlined, since it is private. |
|
|
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. |
|
|
* |
|
|
* @param index the value to check |
|
|
* @throws IndexOutOfBoundsException if index < 0 || index >= size() |
|
|
*/ |
|
|
// This will get inlined, since it is private. |
|
|
private void checkBoundsExclusive(int index) |
|
|
{ |
|
|
if (index < 0 || index >= size) |
|
|
throw new IndexOutOfBoundsException("Index: " + index + ", Size:" |
|
|
+ size); |
|
|
} |
|
|
|
|
|
/** |
|
|
* Specified by AbstractList.subList to return the private field size. |
|
|
* |
|
|
* @return the sublist size |
|
|
* @throws ConcurrentModificationException if the backing list has been |
|
|
* modified externally to this sublist |
|
|
*/ |
|
|
public int size() |
|
|
{ |
|
|
checkMod(); |
|
|
return size; |
|
|
} |
|
|
|
|
|
/** |
|
|
* Specified by AbstractList.subList to delegate to the backing list. |
|
|
* |
|
|
* @param index the location to modify |
|
|
* @param o the new value |
|
|
* @return the old value |
|
|
* @throws ConcurrentModificationException if the backing list has been |
|
|
* modified externally to this sublist |
|
|
* @throws UnsupportedOperationException if the backing list does not |
|
|
* support the set operation |
|
|
* @throws IndexOutOfBoundsException if index < 0 || index >= size() |
|
|
* @throws ClassCastException if o cannot be added to the backing list due |
|
|
* to its type |
|
|
* @throws IllegalArgumentException if o cannot be added to the backing list |
|
|
* for some other reason |
|
|
*/ |
|
|
public Object set(int index, Object o) |
|
|
{ |
|
|
checkMod(); |
|
|
checkBoundsExclusive(index); |
|
|
return backingList.set(index + offset, o); |
|
|
} |
|
|
|
|
|
/** |
|
|
* Specified by AbstractList.subList to delegate to the backing list. |
|
|
* |
|
|
* @param index the location to get from |
|
|
* @return the object at that location |
|
|
* @throws ConcurrentModificationException if the backing list has been |
|
|
* modified externally to this sublist |
|
|
* @throws IndexOutOfBoundsException if index < 0 || index >= size() |
|
|
*/ |
|
|
public Object get(int index) |
|
|
{ |
|
|
checkMod(); |
|
|
checkBoundsExclusive(index); |
|
|
return backingList.get(index + offset); |
|
|
} |
|
|
|
|
|
/** |
|
|
* Specified by AbstractList.subList to delegate to the backing list. |
|
|
* |
|
|
* @param index the index to insert at |
|
|
* @param o the object to add |
|
|
* @throws ConcurrentModificationException if the backing list has been |
|
|
* modified externally to this sublist |
|
|
* @throws IndexOutOfBoundsException if index < 0 || index > size() |
|
|
* @throws UnsupportedOperationException if the backing list does not |
|
|
* support the add operation. |
|
|
* @throws ClassCastException if o cannot be added to the backing list due |
|
|
* to its type. |
|
|
* @throws IllegalArgumentException if o cannot be added to the backing |
|
|
* list for some other reason. |
|
|
*/ |
|
|
public void add(int index, Object o) |
|
|
{ |
|
|
checkMod(); |
|
|
checkBoundsInclusive(index); |
|
|
backingList.add(index + offset, o); |
|
|
size++; |
|
|
modCount = backingList.modCount; |
|
|
} |
|
|
|
|
|
/** |
|
|
* Specified by AbstractList.subList to delegate to the backing list. |
|
|
* |
|
|
* @param index the index to remove |
|
|
* @return the removed object |
|
|
* @throws ConcurrentModificationException if the backing list has been |
|
|
* modified externally to this sublist |
|
|
* @throws IndexOutOfBoundsException if index < 0 || index >= size() |
|
|
* @throws UnsupportedOperationException if the backing list does not |
|
|
* support the remove operation |
|
|
*/ |
|
|
public Object remove(int index) |
|
|
{ |
|
|
checkMod(); |
|
|
checkBoundsExclusive(index); |
|
|
Object o = backingList.remove(index + offset); |
|
|
size--; |
|
|
modCount = backingList.modCount; |
|
|
return o; |
|
|
} |
|
|
|
|
754 |
/** |
/** |
755 |
* Specified by AbstractList.subList to delegate to the backing list. |
* This class follows the implementation requirements set forth in |
756 |
* This does no bounds checking, as it assumes it will only be called |
* {@link AbstractList#subList(int, int)}. It matches Sun's implementation |
757 |
* by trusted code like clear() which has already checked the bounds. |
* by using a non-public top-level class in the same package. |
758 |
* |
* |
759 |
* @param fromIndex the lower bound, inclusive |
* @author Original author unknown |
760 |
* @param toIndex the upper bound, exclusive |
* @author Eric Blake <ebb9@email.byu.edu> |
761 |
* @throws ConcurrentModificationException if the backing list has been |
*/ |
762 |
* modified externally to this sublist |
private static class SubList extends AbstractList |
763 |
* @throws UnsupportedOperationException if the backing list does |
{ |
764 |
* not support removing elements. |
// Package visible, for use by iterator. |
765 |
*/ |
/** The original list. */ |
766 |
protected void removeRange(int fromIndex, int toIndex) |
final AbstractList backingList; |
767 |
{ |
/** The index of the first element of the sublist. */ |
768 |
checkMod(); |
final int offset; |
769 |
|
/** The size of the sublist. */ |
770 |
backingList.removeRange(offset + fromIndex, offset + toIndex); |
int size; |
771 |
size -= toIndex - fromIndex; |
|
772 |
modCount = backingList.modCount; |
/** |
773 |
} |
* Construct the sublist. |
774 |
|
* |
775 |
/** |
* @param backing the list this comes from |
776 |
* Specified by AbstractList.subList to delegate to the backing list. |
* @param fromIndex the lower bound, inclusive |
777 |
* |
* @param toIndex the upper bound, exclusive |
778 |
* @param index the location to insert at |
*/ |
779 |
* @param c the collection to insert |
SubList(AbstractList backing, int fromIndex, int toIndex) |
780 |
* @return true if this list was modified, in other words, c is non-empty |
{ |
781 |
* @throws ConcurrentModificationException if the backing list has been |
backingList = backing; |
782 |
* modified externally to this sublist |
modCount = backing.modCount; |
783 |
* @throws IndexOutOfBoundsException if index < 0 || index > size() |
offset = fromIndex; |
784 |
* @throws UnsupportedOperationException if this list does not support the |
size = toIndex - fromIndex; |
785 |
* addAll operation |
} |
786 |
* @throws ClassCastException if some element of c cannot be added to this |
|
787 |
* list due to its type |
/** |
788 |
* @throws IllegalArgumentException if some element of c cannot be added |
* This method checks the two modCount fields to ensure that there has |
789 |
* to this list for some other reason |
* not been a concurrent modification, returning if all is okay. |
790 |
* @throws NullPointerException if the specified collection is null |
* |
791 |
*/ |
* @throws ConcurrentModificationException if the backing list has been |
792 |
public boolean addAll(int index, Collection c) |
* modified externally to this sublist |
793 |
{ |
*/ |
794 |
checkMod(); |
// This can be inlined. Package visible, for use by iterator. |
795 |
checkBoundsInclusive(index); |
void checkMod() |
796 |
int csize = c.size(); |
{ |
797 |
boolean result = backingList.addAll(offset + index, c); |
if (modCount != backingList.modCount) |
798 |
size += csize; |
throw new ConcurrentModificationException(); |
799 |
modCount = backingList.modCount; |
} |
800 |
return result; |
|
801 |
} |
/** |
802 |
|
* This method checks that a value is between 0 and size (inclusive). If |
803 |
/** |
* it is not, an exception is thrown. |
804 |
* Specified by AbstractList.subList to return addAll(size, c). |
* |
805 |
* |
* @param index the value to check |
806 |
* @param c the collection to insert |
* @throws IndexOutOfBoundsException if index < 0 || index > size() |
807 |
* @return true if this list was modified, in other words, c is non-empty |
*/ |
808 |
* @throws ConcurrentModificationException if the backing list has been |
// This will get inlined, since it is private. |
809 |
* modified externally to this sublist |
private void checkBoundsInclusive(int index) |
810 |
* @throws UnsupportedOperationException if this list does not support the |
{ |
811 |
* addAll operation |
if (index < 0 || index > size) |
812 |
* @throws ClassCastException if some element of c cannot be added to this |
throw new IndexOutOfBoundsException("Index: " + index + ", Size:" |
813 |
* list due to its type |
+ size); |
814 |
* @throws IllegalArgumentException if some element of c cannot be added |
} |
815 |
* to this list for some other reason |
|
816 |
* @throws NullPointerException if the specified collection is null |
/** |
817 |
*/ |
* This method checks that a value is between 0 (inclusive) and size |
818 |
public boolean addAll(Collection c) |
* (exclusive). If it is not, an exception is thrown. |
819 |
{ |
* |
820 |
return addAll(size, c); |
* @param index the value to check |
821 |
} |
* @throws IndexOutOfBoundsException if index < 0 || index >= size() |
822 |
|
*/ |
823 |
/** |
// This will get inlined, since it is private. |
824 |
* Specified by AbstractList.subList to return listIterator(). |
private void checkBoundsExclusive(int index) |
825 |
* |
{ |
826 |
* @return an iterator over the sublist |
if (index < 0 || index >= size) |
827 |
*/ |
throw new IndexOutOfBoundsException("Index: " + index + ", Size:" |
828 |
public Iterator iterator() |
+ size); |
829 |
{ |
} |
830 |
return listIterator(); |
|
831 |
} |
/** |
832 |
|
* Specified by AbstractList.subList to return the private field size. |
833 |
/** |
* |
834 |
* Specified by AbstractList.subList to return a wrapper around the |
* @return the sublist size |
835 |
* backing list's iterator. |
* @throws ConcurrentModificationException if the backing list has been |
836 |
* |
* modified externally to this sublist |
837 |
* @param index the start location of the iterator |
*/ |
838 |
* @return a list iterator over the sublist |
public int size() |
839 |
* @throws ConcurrentModificationException if the backing list has been |
{ |
840 |
* modified externally to this sublist |
checkMod(); |
841 |
* @throws IndexOutOfBoundsException if the value is out of range |
return size; |
842 |
*/ |
} |
843 |
public ListIterator listIterator(final int index) |
|
844 |
{ |
/** |
845 |
checkMod(); |
* Specified by AbstractList.subList to delegate to the backing list. |
846 |
checkBoundsInclusive(index); |
* |
847 |
|
* @param index the location to modify |
848 |
|
* @param o the new value |
849 |
|
* @return the old value |
850 |
|
* @throws ConcurrentModificationException if the backing list has been |
851 |
|
* modified externally to this sublist |
852 |
|
* @throws UnsupportedOperationException if the backing list does not |
853 |
|
* support the set operation |
854 |
|
* @throws IndexOutOfBoundsException if index < 0 || index >= size() |
855 |
|
* @throws ClassCastException if o cannot be added to the backing list due |
856 |
|
* to its type |
857 |
|
* @throws IllegalArgumentException if o cannot be added to the backing list |
858 |
|
* for some other reason |
859 |
|
*/ |
860 |
|
public Object set(int index, Object o) |
861 |
|
{ |
862 |
|
checkMod(); |
863 |
|
checkBoundsExclusive(index); |
864 |
|
return backingList.set(index + offset, o); |
865 |
|
} |
866 |
|
|
867 |
|
/** |
868 |
|
* Specified by AbstractList.subList to delegate to the backing list. |
869 |
|
* |
870 |
|
* @param index the location to get from |
871 |
|
* @return the object at that location |
872 |
|
* @throws ConcurrentModificationException if the backing list has been |
873 |
|
* modified externally to this sublist |
874 |
|
* @throws IndexOutOfBoundsException if index < 0 || index >= size() |
875 |
|
*/ |
876 |
|
public Object get(int index) |
877 |
|
{ |
878 |
|
checkMod(); |
879 |
|
checkBoundsExclusive(index); |
880 |
|
return backingList.get(index + offset); |
881 |
|
} |
882 |
|
|
883 |
|
/** |
884 |
|
* Specified by AbstractList.subList to delegate to the backing list. |
885 |
|
* |
886 |
|
* @param index the index to insert at |
887 |
|
* @param o the object to add |
888 |
|
* @throws ConcurrentModificationException if the backing list has been |
889 |
|
* modified externally to this sublist |
890 |
|
* @throws IndexOutOfBoundsException if index < 0 || index > size() |
891 |
|
* @throws UnsupportedOperationException if the backing list does not |
892 |
|
* support the add operation. |
893 |
|
* @throws ClassCastException if o cannot be added to the backing list due |
894 |
|
* to its type. |
895 |
|
* @throws IllegalArgumentException if o cannot be added to the backing |
896 |
|
* list for some other reason. |
897 |
|
*/ |
898 |
|
public void add(int index, Object o) |
899 |
|
{ |
900 |
|
checkMod(); |
901 |
|
checkBoundsInclusive(index); |
902 |
|
backingList.add(index + offset, o); |
903 |
|
size++; |
904 |
|
modCount = backingList.modCount; |
905 |
|
} |
906 |
|
|
907 |
|
/** |
908 |
|
* Specified by AbstractList.subList to delegate to the backing list. |
909 |
|
* |
910 |
|
* @param index the index to remove |
911 |
|
* @return the removed object |
912 |
|
* @throws ConcurrentModificationException if the backing list has been |
913 |
|
* modified externally to this sublist |
914 |
|
* @throws IndexOutOfBoundsException if index < 0 || index >= size() |
915 |
|
* @throws UnsupportedOperationException if the backing list does not |
916 |
|
* support the remove operation |
917 |
|
*/ |
918 |
|
public Object remove(int index) |
919 |
|
{ |
920 |
|
checkMod(); |
921 |
|
checkBoundsExclusive(index); |
922 |
|
Object o = backingList.remove(index + offset); |
923 |
|
size--; |
924 |
|
modCount = backingList.modCount; |
925 |
|
return o; |
926 |
|
} |
927 |
|
|
928 |
|
/** |
929 |
|
* Specified by AbstractList.subList to delegate to the backing list. |
930 |
|
* This does no bounds checking, as it assumes it will only be called |
931 |
|
* by trusted code like clear() which has already checked the bounds. |
932 |
|
* |
933 |
|
* @param fromIndex the lower bound, inclusive |
934 |
|
* @param toIndex the upper bound, exclusive |
935 |
|
* @throws ConcurrentModificationException if the backing list has been |
936 |
|
* modified externally to this sublist |
937 |
|
* @throws UnsupportedOperationException if the backing list does |
938 |
|
* not support removing elements. |
939 |
|
*/ |
940 |
|
protected void removeRange(int fromIndex, int toIndex) |
941 |
|
{ |
942 |
|
checkMod(); |
943 |
|
|
944 |
return new ListIterator() |
backingList.removeRange(offset + fromIndex, offset + toIndex); |
945 |
|
size -= toIndex - fromIndex; |
946 |
|
modCount = backingList.modCount; |
947 |
|
} |
948 |
|
|
949 |
|
/** |
950 |
|
* Specified by AbstractList.subList to delegate to the backing list. |
951 |
|
* |
952 |
|
* @param index the location to insert at |
953 |
|
* @param c the collection to insert |
954 |
|
* @return true if this list was modified, in other words, c is non-empty |
955 |
|
* @throws ConcurrentModificationException if the backing list has been |
956 |
|
* modified externally to this sublist |
957 |
|
* @throws IndexOutOfBoundsException if index < 0 || index > size() |
958 |
|
* @throws UnsupportedOperationException if this list does not support the |
959 |
|
* addAll operation |
960 |
|
* @throws ClassCastException if some element of c cannot be added to this |
961 |
|
* list due to its type |
962 |
|
* @throws IllegalArgumentException if some element of c cannot be added |
963 |
|
* to this list for some other reason |
964 |
|
* @throws NullPointerException if the specified collection is null |
965 |
|
*/ |
966 |
|
public boolean addAll(int index, Collection c) |
967 |
{ |
{ |
968 |
private final ListIterator i = backingList.listIterator(index + offset); |
checkMod(); |
969 |
private int position = index; |
checkBoundsInclusive(index); |
970 |
|
int csize = c.size(); |
971 |
|
boolean result = backingList.addAll(offset + index, c); |
972 |
|
size += csize; |
973 |
|
modCount = backingList.modCount; |
974 |
|
return result; |
975 |
|
} |
976 |
|
|
977 |
|
/** |
978 |
|
* Specified by AbstractList.subList to return addAll(size, c). |
979 |
|
* |
980 |
|
* @param c the collection to insert |
981 |
|
* @return true if this list was modified, in other words, c is non-empty |
982 |
|
* @throws ConcurrentModificationException if the backing list has been |
983 |
|
* modified externally to this sublist |
984 |
|
* @throws UnsupportedOperationException if this list does not support the |
985 |
|
* addAll operation |
986 |
|
* @throws ClassCastException if some element of c cannot be added to this |
987 |
|
* list due to its type |
988 |
|
* @throws IllegalArgumentException if some element of c cannot be added |
989 |
|
* to this list for some other reason |
990 |
|
* @throws NullPointerException if the specified collection is null |
991 |
|
*/ |
992 |
|
public boolean addAll(Collection c) |
993 |
|
{ |
994 |
|
return addAll(size, c); |
995 |
|
} |
996 |
|
|
997 |
/** |
/** |
998 |
* Tests to see if there are any more objects to |
* Specified by AbstractList.subList to return listIterator(). |
999 |
* return. |
* |
1000 |
* |
* @return an iterator over the sublist |
1001 |
* @return True if the end of the list has not yet been |
*/ |
1002 |
* reached. |
public Iterator iterator() |
1003 |
* @throws ConcurrentModificationException if the |
{ |
1004 |
* list has been modified elsewhere. |
return listIterator(); |
1005 |
*/ |
} |
|
public boolean hasNext() |
|
|
{ |
|
|
checkMod(); |
|
|
return position < size; |
|
|
} |
|
|
|
|
|
/** |
|
|
* Tests to see if there are objects prior to the |
|
|
* current position in the list. |
|
|
* |
|
|
* @return True if objects exist prior to the current |
|
|
* position of the iterator. |
|
|
* @throws ConcurrentModificationException if the |
|
|
* list has been modified elsewhere. |
|
|
*/ |
|
|
public boolean hasPrevious() |
|
|
{ |
|
|
checkMod(); |
|
|
return position > 0; |
|
|
} |
|
|
|
|
|
/** |
|
|
* Retrieves the next object from the list. |
|
|
* |
|
|
* @return The next object. |
|
|
* @throws NoSuchElementException if there are no |
|
|
* more objects to retrieve. |
|
|
* @throws ConcurrentModificationException if the |
|
|
* list has been modified elsewhere. |
|
|
*/ |
|
|
public Object next() |
|
|
{ |
|
|
if (position == size) |
|
|
throw new NoSuchElementException(); |
|
|
position++; |
|
|
return i.next(); |
|
|
} |
|
|
|
|
|
/** |
|
|
* Retrieves the previous object from the list. |
|
|
* |
|
|
* @return The next object. |
|
|
* @throws NoSuchElementException if there are no |
|
|
* previous objects to retrieve. |
|
|
* @throws ConcurrentModificationException if the |
|
|
* list has been modified elsewhere. |
|
|
*/ |
|
|
public Object previous() |
|
|
{ |
|
|
if (position == 0) |
|
|
throw new NoSuchElementException(); |
|
|
position--; |
|
|
return i.previous(); |
|
|
} |
|
|
|
|
|
/** |
|
|
* Returns the index of the next element in the |
|
|
* list, which will be retrieved by <code>next()</code> |
|
|
* |
|
|
* @return The index of the next element. |
|
|
* @throws ConcurrentModificationException if the |
|
|
* list has been modified elsewhere. |
|
|
*/ |
|
|
public int nextIndex() |
|
|
{ |
|
|
return i.nextIndex() - offset; |
|
|
} |
|
1006 |
|
|
1007 |
/** |
/** |
1008 |
* Returns the index of the previous element in the |
* Specified by AbstractList.subList to return a wrapper around the |
1009 |
* list, which will be retrieved by <code>previous()</code> |
* backing list's iterator. |
1010 |
* |
* |
1011 |
* @return The index of the previous element. |
* @param index the start location of the iterator |
1012 |
* @throws ConcurrentModificationException if the |
* @return a list iterator over the sublist |
1013 |
* list has been modified elsewhere. |
* @throws ConcurrentModificationException if the backing list has been |
1014 |
*/ |
* modified externally to this sublist |
1015 |
public int previousIndex() |
* @throws IndexOutOfBoundsException if the value is out of range |
1016 |
{ |
*/ |
1017 |
return i.previousIndex() - offset; |
public ListIterator listIterator(final int index) |
1018 |
} |
{ |
1019 |
|
checkMod(); |
1020 |
|
checkBoundsInclusive(index); |
1021 |
|
|
1022 |
/** |
return new ListIterator() |
|
* Removes the last object retrieved by <code>next()</code> |
|
|
* from the list, if the list supports object removal. |
|
|
* |
|
|
* @throws IllegalStateException if the iterator is positioned |
|
|
* before the start of the list or the last object has already |
|
|
* been removed. |
|
|
* @throws UnsupportedOperationException if the list does |
|
|
* not support removing elements. |
|
|
*/ |
|
|
public void remove() |
|
1023 |
{ |
{ |
1024 |
i.remove(); |
private final ListIterator i = backingList.listIterator(index + offset); |
1025 |
size--; |
private int position = index; |
|
position = nextIndex(); |
|
|
modCount = backingList.modCount; |
|
|
} |
|
|
|
|
|
|
|
|
/** |
|
|
* Replaces the last object retrieved by <code>next()</code> |
|
|
* or <code>previous</code> with o, if the list supports object |
|
|
* replacement and an add or remove operation has not already |
|
|
* been performed. |
|
|
* |
|
|
* @throws IllegalStateException if the iterator is positioned |
|
|
* before the start of the list or the last object has already |
|
|
* been removed. |
|
|
* @throws UnsupportedOperationException if the list doesn't support |
|
|
* the addition or removal of elements. |
|
|
* @throws ClassCastException if the type of o is not a valid type |
|
|
* for this list. |
|
|
* @throws IllegalArgumentException if something else related to o |
|
|
* prevents its addition. |
|
|
* @throws ConcurrentModificationException if the list |
|
|
* has been modified elsewhere. |
|
|
*/ |
|
|
public void set(Object o) |
|
|
{ |
|
|
i.set(o); |
|
|
} |
|
1026 |
|
|
1027 |
/** |
/** |
1028 |
* Adds the supplied object before the element that would be returned |
* Tests to see if there are any more objects to |
1029 |
* by a call to <code>next()</code>, if the list supports addition. |
* return. |
1030 |
* |
* |
1031 |
* @param o The object to add to the list. |
* @return True if the end of the list has not yet been |
1032 |
* @throws UnsupportedOperationException if the list doesn't support |
* reached. |
1033 |
* the addition of new elements. |
* @throws ConcurrentModificationException if the |
1034 |
* @throws ClassCastException if the type of o is not a valid type |
* list has been modified elsewhere. |
1035 |
* for this list. |
*/ |
1036 |
* @throws IllegalArgumentException if something else related to o |
public boolean hasNext() |
1037 |
* prevents its addition. |
{ |
1038 |
* @throws ConcurrentModificationException if the list |
checkMod(); |
1039 |
* has been modified elsewhere. |
return position < size; |
1040 |
*/ |
} |
1041 |
public void add(Object o) |
|
1042 |
{ |
/** |
1043 |
i.add(o); |
* Tests to see if there are objects prior to the |
1044 |
size++; |
* current position in the list. |
1045 |
position++; |
* |
1046 |
modCount = backingList.modCount; |
* @return True if objects exist prior to the current |
1047 |
} |
* position of the iterator. |
1048 |
|
* @throws ConcurrentModificationException if the |
1049 |
// Here is the reason why the various modCount fields are mostly |
* list has been modified elsewhere. |
1050 |
// ignored in this wrapper listIterator. |
*/ |
1051 |
// If the backing listIterator is failfast, then the following holds: |
public boolean hasPrevious() |
1052 |
// Using any other method on this list will call a corresponding |
{ |
1053 |
// method on the backing list *after* the backing listIterator |
checkMod(); |
1054 |
// is created, which will in turn cause a ConcurrentModException |
return position > 0; |
1055 |
// when this listIterator comes to use the backing one. So it is |
} |
1056 |
// implicitly failfast. |
|
1057 |
// If the backing listIterator is NOT failfast, then the whole of |
/** |
1058 |
// this list isn't failfast, because the modCount field of the |
* Retrieves the next object from the list. |
1059 |
// backing list is not valid. It would still be *possible* to |
* |
1060 |
// make the iterator failfast wrt modifications of the sublist |
* @return The next object. |
1061 |
// only, but somewhat pointless when the list can be changed under |
* @throws NoSuchElementException if there are no |
1062 |
// us. |
* more objects to retrieve. |
1063 |
// Either way, no explicit handling of modCount is needed. |
* @throws ConcurrentModificationException if the |
1064 |
// However modCount = backingList.modCount must be executed in add |
* list has been modified elsewhere. |
1065 |
// and remove, and size must also be updated in these two methods, |
*/ |
1066 |
// since they do not go through the corresponding methods of the subList. |
public Object next() |
1067 |
}; |
{ |
1068 |
} |
if (position == size) |
1069 |
} // class SubList |
throw new NoSuchElementException(); |
1070 |
|
position++; |
1071 |
|
return i.next(); |
1072 |
|
} |
1073 |
|
|
1074 |
|
/** |
1075 |
|
* Retrieves the previous object from the list. |
1076 |
|
* |
1077 |
|
* @return The next object. |
1078 |
|
* @throws NoSuchElementException if there are no |
1079 |
|
* previous objects to retrieve. |
1080 |
|
* @throws ConcurrentModificationException if the |
1081 |
|
* list has been modified elsewhere. |
1082 |
|
*/ |
1083 |
|
public Object previous() |
1084 |
|
{ |
1085 |
|
if (position == 0) |
1086 |
|
throw new NoSuchElementException(); |
1087 |
|
position--; |
1088 |
|
return i.previous(); |
1089 |
|
} |
1090 |
|
|
1091 |
|
/** |
1092 |
|
* Returns the index of the next element in the |
1093 |
|
* list, which will be retrieved by <code>next()</code> |
1094 |
|
* |
1095 |
|
* @return The index of the next element. |
1096 |
|
* @throws ConcurrentModificationException if the |
1097 |
|
* list has been modified elsewhere. |
1098 |
|
*/ |
1099 |
|
public int nextIndex() |
1100 |
|
{ |
1101 |
|
return i.nextIndex() - offset; |
1102 |
|
} |
1103 |
|
|
1104 |
|
/** |
1105 |
|
* Returns the index of the previous element in the |
1106 |
|
* list, which will be retrieved by <code>previous()</code> |
1107 |
|
* |
1108 |
|
* @return The index of the previous element. |
1109 |
|
* @throws ConcurrentModificationException if the |
1110 |
|
* list has been modified elsewhere. |
1111 |
|
*/ |
1112 |
|
public int previousIndex() |
1113 |
|
{ |
1114 |
|
return i.previousIndex() - offset; |
1115 |
|
} |
1116 |
|
|
1117 |
|
/** |
1118 |
|
* Removes the last object retrieved by <code>next()</code> |
1119 |
|
* from the list, if the list supports object removal. |
1120 |
|
* |
1121 |
|
* @throws IllegalStateException if the iterator is positioned |
1122 |
|
* before the start of the list or the last object has already |
1123 |
|
* been removed. |
1124 |
|
* @throws UnsupportedOperationException if the list does |
1125 |
|
* not support removing elements. |
1126 |
|
*/ |
1127 |
|
public void remove() |
1128 |
|
{ |
1129 |
|
i.remove(); |
1130 |
|
size--; |
1131 |
|
position = nextIndex(); |
1132 |
|
modCount = backingList.modCount; |
1133 |
|
} |
1134 |
|
|
1135 |
|
|
1136 |
|
/** |
1137 |
|
* Replaces the last object retrieved by <code>next()</code> |
1138 |
|
* or <code>previous</code> with o, if the list supports object |
1139 |
|
* replacement and an add or remove operation has not already |
1140 |
|
* been performed. |
1141 |
|
* |
1142 |
|
* @throws IllegalStateException if the iterator is positioned |
1143 |
|
* before the start of the list or the last object has already |
1144 |
|
* been removed. |
1145 |
|
* @throws UnsupportedOperationException if the list doesn't support |
1146 |
|
* the addition or removal of elements. |
1147 |
|
* @throws ClassCastException if the type of o is not a valid type |
1148 |
|
* for this list. |
1149 |
|
* @throws IllegalArgumentException if something else related to o |
1150 |
|
* prevents its addition. |
1151 |
|
* @throws ConcurrentModificationException if the list |
1152 |
|
* has been modified elsewhere. |
1153 |
|
*/ |
1154 |
|
public void set(Object o) |
1155 |
|
{ |
1156 |
|
i.set(o); |
1157 |
|
} |
1158 |
|
|
1159 |
|
/** |
1160 |
|
* Adds the supplied object before the element that would be returned |
1161 |
|
* by a call to <code>next()</code>, if the list supports addition. |
1162 |
|
* |
1163 |
|
* @param o The object to add to the list. |
1164 |
|
* @throws UnsupportedOperationException if the list doesn't support |
1165 |
|
* the addition of new elements. |
1166 |
|
* @throws ClassCastException if the type of o is not a valid type |
1167 |
|
* for this list. |
1168 |
|
* @throws IllegalArgumentException if something else related to o |
1169 |
|
* prevents its addition. |
1170 |
|
* @throws ConcurrentModificationException if the list |
1171 |
|
* has been modified elsewhere. |
1172 |
|
*/ |
1173 |
|
public void add(Object o) |
1174 |
|
{ |
1175 |
|
i.add(o); |
1176 |
|
size++; |
1177 |
|
position++; |
1178 |
|
modCount = backingList.modCount; |
1179 |
|
} |
1180 |
|
|
1181 |
|
// Here is the reason why the various modCount fields are mostly |
1182 |
|
// ignored in this wrapper listIterator. |
1183 |
|
// If the backing listIterator is failfast, then the following holds: |
1184 |
|
// Using any other method on this list will call a corresponding |
1185 |
|
// method on the backing list *after* the backing listIterator |
1186 |
|
// is created, which will in turn cause a ConcurrentModException |
1187 |
|
// when this listIterator comes to use the backing one. So it is |
1188 |
|
// implicitly failfast. |
1189 |
|
// If the backing listIterator is NOT failfast, then the whole of |
1190 |
|
// this list isn't failfast, because the modCount field of the |
1191 |
|
// backing list is not valid. It would still be *possible* to |
1192 |
|
// make the iterator failfast wrt modifications of the sublist |
1193 |
|
// only, but somewhat pointless when the list can be changed under |
1194 |
|
// us. |
1195 |
|
// Either way, no explicit handling of modCount is needed. |
1196 |
|
// However modCount = backingList.modCount must be executed in add |
1197 |
|
// and remove, and size must also be updated in these two methods, |
1198 |
|
// since they do not go through the corresponding methods of the subList. |
1199 |
|
}; |
1200 |
|
} |
1201 |
|
} // class SubList |
1202 |
|
|
1203 |
|
/** |
1204 |
|
* This class is a RandomAccess version of SubList, as required by |
1205 |
|
* {@link AbstractList#subList(int, int)}. |
1206 |
|
* |
1207 |
|
* @author Eric Blake <ebb9@email.byu.edu> |
1208 |
|
*/ |
1209 |
|
private static final class RandomAccessSubList extends SubList |
1210 |
|
implements RandomAccess |
1211 |
|
{ |
1212 |
|
/** |
1213 |
|
* Construct the sublist. |
1214 |
|
* |
1215 |
|
* @param backing the list this comes from |
1216 |
|
* @param fromIndex the lower bound, inclusive |
1217 |
|
* @param toIndex the upper bound, exclusive |
1218 |
|
*/ |
1219 |
|
RandomAccessSubList(AbstractList backing, int fromIndex, int toIndex) |
1220 |
|
{ |
1221 |
|
super(backing, fromIndex, toIndex); |
1222 |
|
} |
1223 |
|
} // class RandomAccessSubList |
1224 |
|
|
1225 |
/** |
} // class AbstractList |
|
* This class is a RandomAccess version of SubList, as required by |
|
|
* {@link AbstractList#subList(int, int)}. |
|
|
* |
|
|
* @author Eric Blake <ebb9@email.byu.edu> |
|
|
*/ |
|
|
final class RandomAccessSubList extends SubList |
|
|
implements RandomAccess |
|
|
{ |
|
|
/** |
|
|
* Construct the sublist. |
|
|
* |
|
|
* @param backing the list this comes from |
|
|
* @param fromIndex the lower bound, inclusive |
|
|
* @param toIndex the upper bound, exclusive |
|
|
*/ |
|
|
RandomAccessSubList(AbstractList backing, int fromIndex, int toIndex) |
|
|
{ |
|
|
super(backing, fromIndex, toIndex); |
|
|
} |
|
|
} // class RandomAccessSubList |
|