45
45
import java.util.Comparator;
48
* @author Michael Koch
48
* <code>SetOfIntegerSyntax</code> is the abstract base class of all attribute
49
* classes which provide a set of non-negative integers as value (e.g. the
50
* page ranges to print) represented as single values or ranges of values.
52
* A <code>SetOfIntegerSyntax</code> instance consists of an integer array of
53
* ranges. Ranges may have the same lower and upper bound representing a single
54
* integer value. Ranges with a lower bound greater than the upper bound are
55
* null ranges and discarded. Ranges may overlap in their values. In no case
56
* negative integers are allowed.
59
* There are several constructors available:
61
* <li><code>SetOfIntegerSyntax(int member)</code><br>
62
* Constructor for an instance with only one integer value.
64
* <li><code>SetOfIntegerSyntax(int lowerBound, int upperBound)</code><br>
65
* Constructor for an instance with one range of integer values.
67
* <li><code>SetOfIntegerSyntax(int[][] members)</code><br>
68
* Flexible constructor for an instance with several single integer values
69
* and/or several ranges of integer values. The allowed array form is an
70
* array of integer arrays of length one or two. Examples are:
71
* <code>int[0][]</code> for empty set of integers, <code>int[][] {{1}}</code>
72
* , <code>int[][] {{1,5}}</code>, <code>int[][] {{1,5},{7,9}}</code>,
73
* <code>int[][] {{3,7},{19}}</code>.
75
* <li><code>SetOfIntegerSyntax(String s)</code><br>
76
* Flexible constructor for an instance with several single integer values
77
* and/or several ranges of integer values. The allowed String instance have
78
* to be a String with comma separated ranges of integer values or single
79
* values. Ranges are represented by two integer with a hypen (-) or colon (:)
80
* between the lower and upper bound value. Whitespace characters are ignored.
81
* Examples are: <code>""</code> for an empty set of integers,
82
* <code>"1"</code>, <code>"1-5"</code>, <code>"1-5,7-9"</code>,
83
* <code>"3-7,19"</code> and <code>"1:2,4"</code>.
88
* <b>Internal storage:</b><br>
89
* The set of integers are stored internally in a normalized array form.
90
* In the normalized array form the set of integer ranges are represented
91
* in as few ranges as possible and overlapping ranges are merged. The ranges
92
* are always represented as an integer array of length two with ranges
93
* stored in {lower bound, upper bound} form. The ranges are stored in
94
* ascending order, without any null ranges.
96
* @author Michael Koch (konqueror@gmx.de)
50
98
public abstract class SetOfIntegerSyntax
51
99
implements Cloneable, Serializable
229
* Creates a <code>SetOfIntegerSyntax</code> object.
231
* @param s the members to use in this set in string form. If
232
* <code>null</code> an empty set is created.
234
* @exception IllegalArgumentException if any element is invalid
179
236
protected SetOfIntegerSyntax(String s)
181
ArrayList vals = new ArrayList();
183
StringCharacterIterator it = new StringCharacterIterator(s);
188
if (skipWhitespace(it))
192
int index = it.getIndex();
193
if (! skipNumber(it))
194
throw new IllegalArgumentException();
195
int[] item = new int[2];
196
item[0] = Integer.parseInt(s.substring(index, it.getIndex()));
198
if (! skipWhitespace(it))
239
this.members = normalize(new int[0][], 0);
242
ArrayList vals = new ArrayList();
244
StringCharacterIterator it = new StringCharacterIterator(s);
200
char c = it.current();
201
if (c == ':' || c == '-')
249
if (skipWhitespace(it))
253
int index = it.getIndex();
254
if (! skipNumber(it))
255
throw new IllegalArgumentException();
256
int[] item = new int[2];
257
item[0] = Integer.parseInt(s.substring(index, it.getIndex()));
259
if (! skipWhitespace(it))
204
if (skipWhitespace(it))
205
throw new IllegalArgumentException();
206
index = it.getIndex();
207
if (! skipNumber(it))
208
throw new IllegalArgumentException();
209
item[1] = Integer.parseInt(s.substring(index, it.getIndex()));
261
char c = it.current();
262
if (c == ':' || c == '-')
265
if (skipWhitespace(it))
266
throw new IllegalArgumentException();
267
index = it.getIndex();
268
if (! skipNumber(it))
269
throw new IllegalArgumentException();
270
item[1] = Integer.parseInt(s.substring(index, it.getIndex()));
212
276
item[1] = item[0];
278
if (item[0] <= item[1])
281
if (skipWhitespace(it))
283
if (it.current() != ',')
284
throw new IllegalArgumentException();
217
if (item[0] <= item[1])
220
if (skipWhitespace(it))
222
if (it.current() != ',')
223
throw new IllegalArgumentException();
288
members = normalize((int[][]) vals.toArray(new int[0][]), vals.size());
227
members = normalize((int[][]) vals.toArray(new int[0][]), vals.size());