国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

為什么list.sort()比Stream().sorted()更快?

這篇具有很好參考價(jià)值的文章主要介紹了為什么list.sort()比Stream().sorted()更快?。希望對(duì)大家有所幫助。如果存在錯(cuò)誤或未考慮完全的地方,請(qǐng)大家不吝賜教,您也可以點(diǎn)擊"舉報(bào)違法"按鈕提交疑問。

真的更好嗎?

先簡(jiǎn)單寫個(gè)demo

List<Integer> userList = new ArrayList<>();
        Random rand = new Random();
        for (int i = 0; i < 10000 ; i++) {
            userList.add(rand.nextInt(1000));
        }
        List<Integer> userList2 = new ArrayList<>();
        userList2.addAll(userList);

        Long startTime1 = System.currentTimeMillis();
        userList2.stream().sorted(Comparator.comparing(Integer::intValue)).collect(Collectors.toList());
        System.out.println("stream.sort耗時(shí):"+(System.currentTimeMillis() - startTime1)+"ms");

        Long startTime = System.currentTimeMillis();
        userList.sort(Comparator.comparing(Integer::intValue));
        System.out.println("List.sort()耗時(shí):"+(System.currentTimeMillis()-startTime)+"ms");

輸出

stream.sort耗時(shí):62ms
List.sort()耗時(shí):7ms

由此可見list原生排序性能更好。

能證明嗎?

證據(jù)錯(cuò)了。

再把demo變換一下,先輸出stream.sort

List<Integer> userList = new ArrayList<>();
        Random rand = new Random();
        for (int i = 0; i < 10000 ; i++) {
            userList.add(rand.nextInt(1000));
        }
        List<Integer> userList2 = new ArrayList<>();
        userList2.addAll(userList);

        Long startTime = System.currentTimeMillis();
        userList.sort(Comparator.comparing(Integer::intValue));
        System.out.println("List.sort()耗時(shí):"+(System.currentTimeMillis()-startTime)+"ms");

        Long startTime1 = System.currentTimeMillis();
        userList2.stream().sorted(Comparator.comparing(Integer::intValue)).collect(Collectors.toList());
        System.out.println("stream.sort耗時(shí):"+(System.currentTimeMillis() - startTime1)+"ms");

此時(shí)輸出變成了

List.sort()耗時(shí):68ms
stream.sort耗時(shí):13ms

這能證明上面的結(jié)論錯(cuò)誤了嗎?

都不能。

兩種方式都不能證明什么。

使用這種方式在很多場(chǎng)景下是不夠的,某些場(chǎng)景下,JVM會(huì)對(duì)代碼進(jìn)行JIT編譯和內(nèi)聯(lián)優(yōu)化。

Long startTime = System.currentTimeMillis();
...
System.currentTimeMillis() - startTime

此時(shí),代碼優(yōu)化前后執(zhí)行的結(jié)果就會(huì)非常大。

基準(zhǔn)測(cè)試是指通過設(shè)計(jì)科學(xué)的測(cè)試方法、測(cè)試工具和測(cè)試系統(tǒng),實(shí)現(xiàn)對(duì)一類測(cè)試對(duì)象的某項(xiàng)性能指標(biāo)進(jìn)行定量的和可對(duì)比的測(cè)試。

基準(zhǔn)測(cè)試使得被測(cè)試代碼獲得足夠預(yù)熱,讓被測(cè)試代碼得到充分的JIT編譯和優(yōu)化。

下面是通過JMH做一下基準(zhǔn)測(cè)試,分別測(cè)試集合大小在100,10000,100000時(shí)兩種排序方式的性能差異。

import org.openjdk.jmh.annotations.*;
import org.openjdk.jmh.infra.Blackhole;
import org.openjdk.jmh.results.format.ResultFormatType;
import org.openjdk.jmh.runner.Runner;
import org.openjdk.jmh.runner.RunnerException;
import org.openjdk.jmh.runner.options.Options;
import org.openjdk.jmh.runner.options.OptionsBuilder;

import java.util.*;
import java.util.concurrent.ThreadLocalRandom;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

@BenchmarkMode(Mode.AverageTime)
@OutputTimeUnit(TimeUnit.MICROSECONDS)
@Warmup(iterations = 2, time = 1)
@Measurement(iterations = 5, time = 5)
@Fork(1)
@State(Scope.Thread)
public class SortBenchmark {

    @Param(value = {"100", "10000", "100000"})
    private int operationSize; 


    private static List<Integer> arrayList;

    public static void main(String[] args) throws RunnerException {
        // 啟動(dòng)基準(zhǔn)測(cè)試
        Options opt = new OptionsBuilder()
                .include(SortBenchmark.class.getSimpleName()) 
                .result("SortBenchmark.json")
                .mode(Mode.All)
                .resultFormat(ResultFormatType.JSON)
                .build();
        new Runner(opt).run(); 
    }

    @Setup
    public void init() {
        arrayList = new ArrayList<>();
        Random random = new Random();
        for (int i = 0; i < operationSize; i++) {
            arrayList.add(random.nextInt(10000));
        }
    }


    @Benchmark
    public void sort(Blackhole blackhole) {
        arrayList.sort(Comparator.comparing(e -> e));
        blackhole.consume(arrayList);
    }

    @Benchmark
    public void streamSorted(Blackhole blackhole) {
        arrayList = arrayList.stream().sorted(Comparator.comparing(e -> e)).collect(Collectors.toList());
        blackhole.consume(arrayList);
    }

}

性能測(cè)試結(jié)果:

為什么list.sort()比Stream().sorted()更快?,junit,java,后端

可以看到,list sort()效率確實(shí)比stream().sorted()要好。

為什么更好?

流本身的損耗

java的stream讓我們可以在應(yīng)用層就可以高效地實(shí)現(xiàn)類似數(shù)據(jù)庫(kù)SQL的聚合操作了,它可以讓代碼更加簡(jiǎn)潔優(yōu)雅。

但是,假設(shè)我們要對(duì)一個(gè)list排序,得先把list轉(zhuǎn)成stream流,排序完成后需要將數(shù)據(jù)收集起來重新形成list,這部份額外的開銷有多大呢?

我們可以通過以下代碼來進(jìn)行基準(zhǔn)測(cè)試

import org.openjdk.jmh.annotations.*;
import org.openjdk.jmh.infra.Blackhole;
import org.openjdk.jmh.results.format.ResultFormatType;
import org.openjdk.jmh.runner.Runner;
import org.openjdk.jmh.runner.RunnerException;
import org.openjdk.jmh.runner.options.Options;
import org.openjdk.jmh.runner.options.OptionsBuilder;

import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.Random;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

@BenchmarkMode(Mode.AverageTime)
@OutputTimeUnit(TimeUnit.MICROSECONDS)
@Warmup(iterations = 2, time = 1)
@Measurement(iterations = 5, time = 5)
@Fork(1)
@State(Scope.Thread)
public class SortBenchmark3 {

    @Param(value = {"100", "10000"})
    private int operationSize; // 操作次數(shù)


    private static List<Integer> arrayList;

    public static void main(String[] args) throws RunnerException {
        // 啟動(dòng)基準(zhǔn)測(cè)試
        Options opt = new OptionsBuilder()
                .include(SortBenchmark3.class.getSimpleName()) // 要導(dǎo)入的測(cè)試類
                .result("SortBenchmark3.json")
                .mode(Mode.All)
                .resultFormat(ResultFormatType.JSON)
                .build();
        new Runner(opt).run(); // 執(zhí)行測(cè)試
    }

    @Setup
    public void init() {
        // 啟動(dòng)執(zhí)行事件
        arrayList = new ArrayList<>();
        Random random = new Random();
        for (int i = 0; i < operationSize; i++) {
            arrayList.add(random.nextInt(10000));
        }
    }

    @Benchmark
    public void stream(Blackhole blackhole) {
        arrayList.stream().collect(Collectors.toList());
        blackhole.consume(arrayList);
    }

    @Benchmark
    public void sort(Blackhole blackhole) {
        arrayList.stream().sorted(Comparator.comparing(Integer::intValue)).collect(Collectors.toList());
        blackhole.consume(arrayList);
    }
 
}

方法stream測(cè)試將一個(gè)集合轉(zhuǎn)為流再收集回來的耗時(shí)。

方法sort測(cè)試將一個(gè)集合轉(zhuǎn)為流再排序再收集回來的全過程耗時(shí)。

測(cè)試結(jié)果如下:

為什么list.sort()比Stream().sorted()更快?,junit,java,后端

可以發(fā)現(xiàn),集合轉(zhuǎn)為流再收集回來的過程,肯定會(huì)耗時(shí),但是它占全過程的比率并不算高。

因此,這部只能說是小部份的原因。

排序過程

我們可以通過以下源碼很直觀的看到。

為什么list.sort()比Stream().sorted()更快?,junit,java,后端

  • 1 begin方法初始化一個(gè)數(shù)組。
  • 2 accept 接收上游數(shù)據(jù)。
  • 3 end 方法開始進(jìn)行排序。
    這里第3步直接調(diào)用了原生的排序方法,完成排序后,第4步,遍歷向下游發(fā)送數(shù)據(jù)。

所以通過源碼,我們也能很明顯地看到,stream()排序所需時(shí)間肯定是 > 原生排序時(shí)間。

只不過,這里要量化地搞明白,到底多出了多少,這里得去編譯jdk源碼,在第3步前后將時(shí)間打印出來。

這一步我就不做了。
感興趣的朋友可以去測(cè)一下。

不過我覺得這兩點(diǎn)也能很好地回答,為什么list.sort()比Stream().sorted()更快。

補(bǔ)充說明:文章來源地址http://www.zghlxwxcb.cn/news/detail-629100.html

  1. 本文說的stream()流指的是串行流,而不是并行流。
  2. 絕大多數(shù)場(chǎng)景下,幾百幾千幾萬(wàn)的數(shù)據(jù),開心就好,怎么方便怎么用,沒有必要去計(jì)較這點(diǎn)性能差異。

到了這里,關(guān)于為什么list.sort()比Stream().sorted()更快?的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點(diǎn)僅代表作者本人,不代表本站立場(chǎng)。本站僅提供信息存儲(chǔ)空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請(qǐng)注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實(shí)不符,請(qǐng)點(diǎn)擊違法舉報(bào)進(jìn)行投訴反饋,一經(jīng)查實(shí),立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費(fèi)用

相關(guān)文章

  • 【排序算法】插入排序與希爾排序,你不想知道為什么希爾比插入更快嗎?

    【排序算法】插入排序與希爾排序,你不想知道為什么希爾比插入更快嗎?

    大家好??!本文阿輝講介紹插入排序和希爾排序,并將解釋為什么希爾排序比插入排序更快。 插入排序,實(shí)際上是我們平時(shí)都使用過的排序,為什么這么說呢???想必大家都玩過撲克牌吧,大家是如何整理手中的牌的呢?一定是想下面這樣對(duì)吧?? 沒錯(cuò),插入排序也是的么實(shí)

    2024年02月02日
    瀏覽(25)
  • Maven 項(xiàng)目中為什么Junit之@Test 單元測(cè)試無(wú)法使用

    Maven 項(xiàng)目中為什么Junit之@Test 單元測(cè)試無(wú)法使用

    由于框架項(xiàng)目的使用,會(huì)有很多模塊,所以Junit中的@Test注解是我們比較常用的注解,但是有些小問題我們需要注意 在創(chuàng)建完Maven項(xiàng)目后,我們通常呢會(huì)導(dǎo)入以下這樣的依賴包: 但是我們這時(shí)候去代碼中使用@Test,會(huì)出現(xiàn)報(bào)紅,這是為什么呢??? 這里先說明下,org.junit是導(dǎo)入

    2024年02月02日
    瀏覽(27)
  • Redis的速度不夠用?為什么你應(yīng)該考慮使用 KeyDB,一個(gè)更快、更強(qiáng)大、更靈活的開源數(shù)據(jù)庫(kù)

    Redis的速度不夠用?為什么你應(yīng)該考慮使用 KeyDB,一個(gè)更快、更強(qiáng)大、更靈活的開源數(shù)據(jù)庫(kù)

    你是否正在使用?Redis?作為您的數(shù)據(jù)結(jié)構(gòu)存儲(chǔ),享受它的高性能、高可用的特性?如果是這樣,那么你可能會(huì)對(duì)?KeyDB?感興趣。 KeyDB?一個(gè)由?Snap?提供支持、專為擴(kuò)展而構(gòu)建的開源數(shù)據(jù)庫(kù)。它是?Redis?的高性能分支,專注于多線程、內(nèi)存效率和高吞吐量。KeyDB?采用?MVCC?體系

    2024年02月08日
    瀏覽(31)
  • python list.sort方法和內(nèi)置函數(shù)sorted

    list.sort 方法會(huì)就地排序列表,也就是說不會(huì)把原列表復(fù)制一份。這也是這個(gè)方法的返回值是 None 的原因,提醒你本方法不會(huì)新建一個(gè)列表。在這種情況下返回 None 其實(shí)是Python 的一個(gè)慣例:如果一個(gè)函數(shù)或者方法對(duì)對(duì)象進(jìn)行的是就地改動(dòng),那它就應(yīng)該返回None,好讓調(diào)用者知道

    2024年01月18日
    瀏覽(21)
  • 使用Java的stream().sorted方法對(duì)集合進(jìn)行排序

    Java Stream API 提供了豐富的方法來對(duì)流中的元素進(jìn)行處理和操作。其中, sorted() 方法用于對(duì)流中的元素進(jìn)行排序。本文將深入探討 sorted() 方法的用法、示例代碼以及詳細(xì)解釋,以幫助您更好地理解和使用這個(gè)方法。 StreamT sorted() : 這個(gè)方法用于對(duì)流中的元素進(jìn)行自然排序。要

    2024年02月04日
    瀏覽(20)
  • C# list的sort排序

    目錄 前言: 值類型的排序: 方法一:直接調(diào)用sort函數(shù) 方法二:通過C# ling表達(dá)式與CompareTo接口配合使用 方法三:降序的實(shí)現(xiàn) 對(duì)于自定義類型的sort排序? 方法一:通過實(shí)現(xiàn)IComparable接口重寫CompareTo方法來排序 方法二:通過ling表達(dá)式實(shí)現(xiàn)? ????????有時(shí)需要對(duì)List列表中內(nèi)

    2024年02月15日
    瀏覽(618)
  • 1028 List Sorting (PAT甲級(jí))

    Excel can sort records according to any column. Now you are supposed to imitate this function. Input Specification: Each input file contains one test case. For each case, the first line contains two integers?N?(≤105) and?C, where?N?is the number of records and?C?is the column that you are supposed to sort the records with. Then?N?lines follow, eac

    2024年02月15日
    瀏覽(16)
  • PTA 1052 Linked List Sorting

    個(gè)人學(xué)習(xí)記錄,代碼難免不盡人意。 A linked list consists of a series of structures, which are not necessarily adjacent in memory. We assume that each structure contains an integer key and a Next pointer to the next structure. Now given a linked list, you are supposed to sort the structures according to their key values in increasing order. Inp

    2024年02月15日
    瀏覽(17)
  • list集合對(duì)sort的使用方法

    List集合的排序: java提供了兩種排序方式,分別是Collections.sort(List)和Collections.sort(List,Commparator),下面就這兩種方法的使用做詳細(xì)的說明: 方法一:Collections.sort(List) 這個(gè)方法有分兩種情況:1、比較的是基礎(chǔ)數(shù)據(jù) 2、比較的是引用數(shù)據(jù) 1、基礎(chǔ)數(shù)據(jù)的比較呢,一般都是直接比較,因

    2024年02月09日
    瀏覽(26)
  • Stream流實(shí)踐(五):使用group by然后緊跟sum sort等操作

    本文會(huì)用幾個(gè)例子去講解Stream流 group by基本用法,以及group by分組之后對(duì)于分組數(shù)據(jù)的匯總、排序等操作 1.1 Group by 集合,并展示最后的匯總數(shù)據(jù) 1.2 Group by 集合,并且將他按順序加入到新Map中去 2.1 對(duì)象的基本處理 2.2 Collectors.mapping 的例子

    2024年02月14日
    瀏覽(23)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請(qǐng)作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包