假設您從「流」源讀取數據項和相關分數(即無法隨機訪問或多次傳遞可能)。Java:來自流源的前n個元素
什麼是最好的方式來保持,在任何時候,只有那些在內存中的重量最輕的目前遇到的。我會對「Java」的做法感興趣,成語越短越好,而不是算法(「使用搜索樹,插入新元素,如果超過大小刪除最大值」)。
下面是我提出的解決方案,但是我覺得它有點冗長,也有一些行爲可能是意想不到的(同一項目不同分數可能保持多次,而同一項目添加相同分數是隻保留一次)。我也覺得應該有這樣的東西存在。
import java.util.AbstractMap.SimpleEntry;
import java.util.Map.Entry;
import java.util.Comparator;
import java.util.TreeSet;
/**
* Stores the n smallest (by score) elements only.
*/
public class TopN<T extends Comparable<T>> {
private TreeSet<Entry<T, Double>> elements;
private int n;
public TopN(int n) {
this.n = n;
this.elements = new TreeSet<Entry<T, Double>>(
new Comparator<Entry<T, Double>>() {
@Override
public int compare(Entry<T, Double> o1, Entry<T, Double> o2) {
if (o1.getValue() > o2.getValue()) return 1;
if (o1.getValue() < o2.getValue()) return -1;
return o1.getKey() == null ? 1 : o1.getKey().compareTo(o2.getKey());
}
});
}
/**
* Adds the element if the score is lower than the n-th smallest score.
*/
public void add(T element, double score) {
Entry<T, Double> keyVal = new SimpleEntry<T, Double>(element,score);
elements.add(keyVal);
if (elements.size() > n) {
elements.pollLast();
}
}
/**
* Returns the elements with n smallest scores.
*/
public TreeSet<Entry<T, Double>> get() {
return elements;
}
}
也有同樣的問題,但它不包括流源/內存要求: Find top N elements in an Array
PriorityQueues是無界的,我認爲他需要只保留一定數量的在存儲器元件中的一個的時間。 – MahdeTo 2012-03-06 10:14:09
啊 - 我在編寫評論時似乎一直在編輯我的編輯。看我的編輯。 – dty 2012-03-06 10:16:45
看起來確實如此。幾乎與他具有相同的解決方案,但具有優先隊列而不是樹集。 – MahdeTo 2012-03-06 10:18:11