2 * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$)
3 * Copyright (C) $$Year-Rel$$ The Jalview Authors
5 * This file is part of Jalview.
7 * Jalview is free software: you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation, either version 3
10 * of the License, or (at your option) any later version.
12 * Jalview is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty
14 * of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with Jalview. If not, see <http://www.gnu.org/licenses/>.
19 * The Jalview Authors are detailed in the 'AUTHORS' file.
21 package jalview.datamodel.features;
23 import jalview.datamodel.SequenceFeature;
25 import java.util.ArrayList;
26 import java.util.List;
28 import intervalstore.api.IntervalStoreI;
29 import intervalstore.impl.BinarySearcher;
30 import intervalstore.impl.IntervalStore;
33 * A data store for a set of sequence features that supports efficient lookup of
34 * features overlapping a given range. Intended for (but not limited to) storage
35 * of features for one sequence and feature type.
40 public class FeatureStoreImpl extends FeatureStore
43 public FeatureStoreImpl()
45 features = new IntervalStore<>();
49 * Adds contact features to the result list where either the second or the
50 * first contact position lies within the target range
57 protected void findContactFeatures(long from, long to,
58 List<SequenceFeature> result)
60 if (contactFeatureStarts != null)
62 findContactStartOverlaps(from, to, result);
63 findContactEndOverlaps(from, to, result);
68 * Adds to the result list any contact features whose end (second contact
69 * point), but not start (first contact point), lies in the query from-to
77 private void findContactEndOverlaps(long from, long to,
78 List<SequenceFeature> result)
81 * find the first contact feature (if any)
82 * whose end point is not before the target range
84 int index = BinarySearcher.findFirst(contactFeatureEnds,
85 f -> f.getEnd() >= from);
87 int n = contactFeatureEnds.size();
90 SequenceFeature sf = contactFeatureEnds.get(index);
91 if (!sf.isContactFeature())
93 System.err.println("Error! non-contact feature type " + sf.getType()
94 + " in contact features list");
99 int begin = sf.getBegin();
100 if (begin >= from && begin <= to)
103 * this feature's first contact position lies in the search range
104 * so we don't include it in results a second time
110 if (sf.getEnd() > to)
113 * this feature (and all following) has end point after the target range
119 * feature has end >= from and end <= to
120 * i.e. contact end point lies within overlap search range
128 * Adds contact features whose start position lies in the from-to range to the
136 private void findContactStartOverlaps(long from, long to,
137 List<SequenceFeature> result)
139 int index = BinarySearcher.findFirst(contactFeatureStarts,
140 f -> f.getBegin() >= from);
142 while (index < contactFeatureStarts.size())
144 SequenceFeature sf = contactFeatureStarts.get(index);
145 if (!sf.isContactFeature())
147 System.err.println("Error! non-contact feature " + sf.toString()
148 + " in contact features list");
152 if (sf.getBegin() > to)
155 * this feature's start (and all following) follows the target range
161 * feature has begin >= from and begin <= to
162 * i.e. contact start point lies within overlap search range
170 * Returns a (possibly empty) list of features whose extent overlaps the given
171 * range. The returned list is not ordered. Contact features are included if
172 * either of the contact points lies within the range.
175 * start position of overlap range (inclusive)
177 * end position of overlap range (inclusive)
184 public List<SequenceFeature> findOverlappingFeatures(long start, long end,
185 List<SequenceFeature> result)
187 result = new ArrayList<>();
188 findContactFeatures(start, end, result);
189 findOverlaps(start, end, result);
193 private void findOverlaps(long start, long end,
194 List<SequenceFeature> result)
196 result.addAll(((IntervalStoreI<SequenceFeature>) features)
197 .findOverlaps(start, end));
198 // TODO Auto-generated method stub