--- /dev/null
+package tim.prune.data;
+
+/**
+ * Class to hold an ordered list of fields
+ * to match the value list in a data point
+ */
+public class FieldList
+{
+ /** Array of Field objects making the list */
+ private Field[] _fieldArray;
+
+
+ /**
+ * Constructor for an empty field list
+ */
+ public FieldList()
+ {
+ _fieldArray = new Field[0];
+ }
+
+ /**
+ * Constructor for a given number of empty fields
+ * @param inNumFields
+ */
+ public FieldList(int inNumFields)
+ {
+ if (inNumFields < 0) inNumFields = 0;
+ _fieldArray = new Field[inNumFields];
+ }
+
+ /**
+ * Constructor giving array of Field objects
+ * @param inFieldArray array of Field objects
+ */
+ public FieldList(Field[] inFieldArray)
+ {
+ if (inFieldArray == null || inFieldArray.length == 0)
+ {
+ _fieldArray = new Field[0];
+ }
+ else
+ {
+ _fieldArray = new Field[inFieldArray.length];
+ System.arraycopy(inFieldArray, 0, _fieldArray, 0, inFieldArray.length);
+ }
+ }
+
+ /**
+ * Get the index of the given field
+ * @param inField field to look for
+ * @return index number of the field starting at zero
+ */
+ public int getFieldIndex(Field inField)
+ {
+ if (inField == null) return -1;
+ for (int f=0; f<_fieldArray.length; f++)
+ {
+ if (_fieldArray[f] != null && _fieldArray[f].equals(inField))
+ return f;
+ }
+ return -1;
+ }
+
+
+ /**
+ * Check whether the FieldList contains the given Field object
+ * @param inField Field to check
+ * @return true if the FieldList contains the given field
+ */
+ public boolean contains(Field inField)
+ {
+ return (getFieldIndex(inField) >= 0);
+ }
+
+
+ /**
+ * @return number of fields in list
+ */
+ public int getNumFields()
+ {
+ if (_fieldArray == null) return 0;
+ return _fieldArray.length;
+ }
+
+
+ /**
+ * Get the specified Field object
+ * @param inIndex index to retrieve
+ * @return Field object
+ */
+ public Field getField(int inIndex)
+ {
+ if (_fieldArray == null || inIndex < 0 || inIndex >= _fieldArray.length)
+ {
+ return null;
+ }
+ return _fieldArray[inIndex];
+ }
+
+
+ /**
+ * Merge this list with a second list, giving a superset
+ * @param inOtherList other FieldList object to merge
+ * @return Merged FieldList object
+ */
+ public FieldList merge(FieldList inOtherList)
+ {
+ // count number of fields
+ int totalFields = _fieldArray.length;
+ for (int f=0; f<inOtherList._fieldArray.length; f++)
+ {
+ if (inOtherList._fieldArray[f] != null && !contains(inOtherList._fieldArray[f]))
+ {
+ totalFields++;
+ }
+ }
+ FieldList list = new FieldList(totalFields);
+ // copy these fields into array
+ System.arraycopy(_fieldArray, 0, list._fieldArray, 0, _fieldArray.length);
+ // copy additional fields from other array if any
+ if (totalFields > _fieldArray.length)
+ {
+ int fieldCounter = _fieldArray.length;
+ for (int f=0; f<inOtherList._fieldArray.length; f++)
+ {
+ if (inOtherList._fieldArray[f] != null && !contains(inOtherList._fieldArray[f]))
+ {
+ list._fieldArray[fieldCounter] = inOtherList._fieldArray[f];
+ fieldCounter++;
+ }
+ }
+ }
+ // return the merged list
+ return list;
+ }
+
+
+ /**
+ * Extend the field list to include the specified field
+ * @param inField Field to add
+ * @return new index of added Field
+ */
+ public int extendList(Field inField)
+ {
+ // See if field is already in list
+ int currIndex = getFieldIndex(inField);
+ if (currIndex >= 0) return currIndex;
+ // Need to extend - increase array size
+ int oldNumFields = _fieldArray.length;
+ Field[] fields = new Field[oldNumFields + 1];
+ System.arraycopy(_fieldArray, 0, fields, 0, oldNumFields);
+ _fieldArray = fields;
+ // Add new field and return index
+ _fieldArray[oldNumFields] = inField;
+ return oldNumFields;
+ }
+
+
+ /**
+ * Convert to String for debug
+ */
+ public String toString()
+ {
+ StringBuffer buffer = new StringBuffer();
+ buffer.append('(');
+ for (int i=0; i<_fieldArray.length; i++)
+ {
+ buffer.append(_fieldArray[i].getName()).append(',');
+ }
+ buffer.append(')');
+ return buffer.toString();
+ }
+}