[英]Is there faster way to find distinct elements using Java
我已經編寫了代碼,以在大量字符串中查找不同的元素。 代碼如下
HashMap<String, Integer> countMap = new HashMap<>();
String[] str={"aa","bb","cc","bb","aa","cc","aa","bb","cc","bb"};
for (String e : str) {
if (!countMap.containsKey(e)) {
countMap.put(e, 1);
}
}
Iterator it=countMap.keySet().iterator();
String[] db= new String[countMap.size()];
for(int i=0;i<countMap.size();i++){
db[i]=(String)it.next();
System.out.println(db[i]);
}
有沒有比這更快的代碼,因為我必須處理非常大的數組。
這不會(非常快),但是使用HashSet
絕對會更優雅:
String[] str={"aa","bb","cc","bb","aa","cc","aa","bb","cc","bb"};
Set<String> distinct = new HashSet<>(Arrays.asList(str));
for(String s : distinct) {
System.out.println(s);
}
您可以使用Java 8並行化所有工作:
String[] largeArray = null;
Set<String> distinctStrings =
Arrays.stream(largeArray).parallel()
.collect(Collectors.toConcurrentMap((s) -> s, (s) -> s)).keySet();
這將一直擴展到ConcurrentMap
的爭用成為問題為止。
您還可以在流上使用distinct
函數:
Set<String> distinctStrings = Arrays.stream(largeArray).parallel()
.distinct().collect(Collectors.toSet())
微基准
兩種方法都以1m GUID作為輸入運行(最壞的情況),進行了100次重復,測量了從中取出一組數據的時間。
Statistics stats = new Statistics();
for (int i = 0; i < 100; i++) {
String[] largeArray = generate(1_000_000); // generates 1m UUIDs
Stopwatch watch = Stopwatch.createStarted();
// add the lambda here
long time = watch.elapsed(TimeUnit.MILLISECONDS);
System.out.println(distinctStrings.size());
stats.add(time);
}
請注意 ,這不能衡量可伸縮性,您需要為該實驗改變輸入大小,以更准確地了解較大輸入的速度。
對於Java Stream Distinct
解決方案:
[Min=358.0, Max=2236.0, Median=456.0, Mean=542.26, StandardDeviation=335.21174263441304]
對於ConcurrentMap
解決方案:
[Min=85.0, Max=1020.0, Median=120.0, Mean=153.58, StandardDeviation=119.78281846742465]
順序使用HashSet
[Min=258.0, Max=1312.0, Median=281.0, Mean=307.39, StandardDeviation=125.63032237481526]
結果
您從並行化中獲得了相當不錯的加速, ConcurrentMap
解決方案在輸入大小上的性能比順序版本好一些(對於更大的輸入大小/更多線程,可能有所不同)。
但是,並行Stream#distinct
慢於順序版本。
哈希是正確的方法。 除了保留Map
我們更喜歡Set
。 僅在內部使用地圖設置。
String[] str={"aa","bb","cc","bb","aa","cc","aa","bb","cc","bb"};
HashSet<String> uniques = new HashSet<String>();
for (String string : str) {
uniques.add(string);
}
String[] result = new String[uniques.size()];
uniques.toArray(result);
System.out.println(Arrays.toString(result));
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.