*/
Set<String> nonPositionalFeatureGroups;
+ /*
+ * the total length of all positional features; contact features count 1 to
+ * the total and 1 to size(), consistent with an average 'feature length' of 1
+ */
+ int totalExtent;
+
/**
* Constructor
*/
}
}
+ /*
+ * record the total extent of positional features, to make
+ * getAverageFeatureLength possible; we count the length of a
+ * contact feature as 1
+ */
+ if (added && !feature.isNonPositional())
+ {
+ int featureLength = feature.isContactFeature() ? 1 : 1
+ + feature.getEnd() - feature.getBegin();
+ totalExtent += featureLength;
+ }
+
return added;
}
if (removed)
{
rebuildFeatureGroups(sf.getFeatureGroup(), removedNonPositional);
+ // TODO and recalculate totalExtent (feature may have changed length!)
}
return removed;
return matched;
}
+
+ /**
+ * Answers the number of positional (or non-positional) features stored
+ *
+ * @param positional
+ * @return
+ */
+ public int size(boolean positional)
+ {
+ if (!positional)
+ {
+ return nonPositionalFeatures == null ? 0 : nonPositionalFeatures
+ .size();
+ }
+
+ int size = nonNestedFeatures.size();
+
+ if (contactFeatureStarts != null)
+ {
+ // note a contact feature (start/end) counts as one
+ size += contactFeatureStarts.size();
+ }
+
+ if (nestedFeatures != null)
+ {
+ size += nestedFeatures.size();
+ }
+
+ return size;
+ }
+
+ /**
+ * Answers the average length of positional features (or zero if there are
+ * none). Contact features contribute a value of 1 to the average.
+ *
+ * @return
+ */
+ public float getAverageFeatureLength()
+ {
+ int d = size(true);
+ return d == 0 ? 0f : (float) totalExtent / d;
+ }
}