1. /*
  2. * Copyright 1999-2004 The Apache Software Foundation
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. * http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. */
  16. package org.apache.commons.collections.iterators;
  17. import java.util.ListIterator;
  18. import java.util.NoSuchElementException;
  19. import org.apache.commons.collections.ResettableListIterator;
  20. /**
  21. * Implements a {@link ListIterator} over an array of objects.
  22. * <p>
  23. * This iterator does not support {@link #add} or {@link #remove}, as the object array
  24. * cannot be structurally modified. The {@link #set} method is supported however.
  25. * <p>
  26. * The iterator implements a {@link #reset} method, allowing the reset of the iterator
  27. * back to the start if required.
  28. *
  29. * @see org.apache.commons.collections.iterators.ObjectArrayIterator
  30. * @see java.util.Iterator
  31. * @see java.util.ListIterator
  32. *
  33. * @since Commons Collections 3.0
  34. * @version $Revision: 1.13 $ $Date: 2004/02/18 00:59:50 $
  35. *
  36. * @author Neil O'Toole
  37. * @author Stephen Colebourne
  38. * @author Phil Steitz
  39. */
  40. public class ObjectArrayListIterator extends ObjectArrayIterator
  41. implements ListIterator, ResettableListIterator {
  42. /**
  43. * Holds the index of the last item returned by a call to <code>next()</code>
  44. * or <code>previous()</code>. This is set to <code>-1</code> if neither method
  45. * has yet been invoked. <code>lastItemIndex</code> is used to to implement the
  46. * {@link #set} method.
  47. */
  48. protected int lastItemIndex = -1;
  49. /**
  50. * Constructor for use with <code>setArray</code>.
  51. * <p>
  52. * Using this constructor, the iterator is equivalent to an empty iterator
  53. * until {@link #setArray} is called to establish the array to iterate over.
  54. */
  55. public ObjectArrayListIterator() {
  56. super();
  57. }
  58. /**
  59. * Constructs an ObjectArrayListIterator that will iterate over the values in the
  60. * specified array.
  61. *
  62. * @param array the array to iterate over
  63. * @throws NullPointerException if <code>array</code> is <code>null</code>
  64. */
  65. public ObjectArrayListIterator(Object[] array) {
  66. super(array);
  67. }
  68. /**
  69. * Constructs an ObjectArrayListIterator that will iterate over the values in the
  70. * specified array from a specific start index.
  71. *
  72. * @param array the array to iterate over
  73. * @param start the index to start iterating at
  74. * @throws NullPointerException if <code>array</code> is <code>null</code>
  75. * @throws IndexOutOfBoundsException if the start index is out of bounds
  76. */
  77. public ObjectArrayListIterator(Object[] array, int start) {
  78. super(array, start);
  79. }
  80. /**
  81. * Construct an ObjectArrayListIterator that will iterate over a range of values
  82. * in the specified array.
  83. *
  84. * @param array the array to iterate over
  85. * @param start the index to start iterating at
  86. * @param end the index (exclusive) to finish iterating at
  87. * @throws IndexOutOfBoundsException if the start or end index is out of bounds
  88. * @throws IllegalArgumentException if end index is before the start
  89. * @throws NullPointerException if <code>array</code> is <code>null</code>
  90. */
  91. public ObjectArrayListIterator(Object[] array, int start, int end) {
  92. super(array, start, end);
  93. }
  94. // ListIterator interface
  95. //-------------------------------------------------------------------------
  96. /**
  97. * Returns true if there are previous elements to return from the array.
  98. *
  99. * @return true if there is a previous element to return
  100. */
  101. public boolean hasPrevious() {
  102. return (this.index > this.startIndex);
  103. }
  104. /**
  105. * Gets the previous element from the array.
  106. *
  107. * @return the previous element
  108. * @throws NoSuchElementException if there is no previous element
  109. */
  110. public Object previous() {
  111. if (hasPrevious() == false) {
  112. throw new NoSuchElementException();
  113. }
  114. this.lastItemIndex = --this.index;
  115. return this.array[this.index];
  116. }
  117. /**
  118. * Gets the next element from the array.
  119. *
  120. * @return the next element
  121. * @throws NoSuchElementException if there is no next element
  122. */
  123. public Object next() {
  124. if (hasNext() == false) {
  125. throw new NoSuchElementException();
  126. }
  127. this.lastItemIndex = this.index;
  128. return this.array[this.index++];
  129. }
  130. /**
  131. * Gets the next index to be retrieved.
  132. *
  133. * @return the index of the item to be retrieved next
  134. */
  135. public int nextIndex() {
  136. return this.index - this.startIndex;
  137. }
  138. /**
  139. * Gets the index of the item to be retrieved if {@link #previous()} is called.
  140. *
  141. * @return the index of the item to be retrieved next
  142. */
  143. public int previousIndex() {
  144. return this.index - this.startIndex - 1;
  145. }
  146. /**
  147. * This iterator does not support modification of its backing array's size, and so will
  148. * always throw an {@link UnsupportedOperationException} when this method is invoked.
  149. *
  150. * @param obj the object to add
  151. * @throws UnsupportedOperationException always thrown.
  152. */
  153. public void add(Object obj) {
  154. throw new UnsupportedOperationException("add() method is not supported");
  155. }
  156. /**
  157. * Sets the element under the cursor.
  158. * <p>
  159. * This method sets the element that was returned by the last call
  160. * to {@link #next()} of {@link #previous()}.
  161. *
  162. * <b>Note:</b> {@link ListIterator} implementations that support <code>add()</code>
  163. * and <code>remove()</code> only allow <code>set()</code> to be called once per call
  164. * to <code>next()</code> or <code>previous</code> (see the {@link ListIterator}
  165. * javadoc for more details). Since this implementation does not support
  166. * <code>add()</code> or <code>remove()</code>, <code>set()</code> may be
  167. * called as often as desired.
  168. *
  169. * @param obj the object to set into the array
  170. * @throws IllegalStateException if next() has not yet been called.
  171. * @throws ClassCastException if the object type is unsuitable for the array
  172. */
  173. public void set(Object obj) {
  174. if (this.lastItemIndex == -1) {
  175. throw new IllegalStateException("must call next() or previous() before a call to set()");
  176. }
  177. this.array[this.lastItemIndex] = obj;
  178. }
  179. /**
  180. * Resets the iterator back to the start index.
  181. */
  182. public void reset() {
  183. super.reset();
  184. this.lastItemIndex = -1;
  185. }
  186. }