簡體   English   中英

小字符串優化(SSO)和移動語義

[英]small string optimization(SSO) and move semantics

std::string test = "small_string";

std::string test2_1 = test;   // line 1

std::string test2_2 = std::move(test); // line 2

嗨,我很好奇哪個版本的字符串創建速度很快。 test2_1test2_2

我正在研究std::string VC ++版本上的實現,發現test2_1版本將調用memcpy(_First1, _First2, _Count))test2_2將調用memmove(_First1, _First2, _Count)) ,我只是想知道哪個如果我希望我的代碼運行得更快,那就更好。

================================================== ============

嗨,我只是做一些測試,有些東西我聽不懂...這是我的測試代碼:

{
    Timer t;
    for (int i = 0; i < 1000000; i++){
        char s[] = "small_string";
        char t[10];

        memcpy(&t, &s, 10);
        //std::cout << t << std::endl;
    }

    std::cout << "test, memcpy: " << t.elapsed() << " second" << std::endl;
}


{
    Timer t;
    for (int i = 0; i < 1000000; i++){
        char s[] = "small_string";
        char t[10];
        memmove(&t, &s, 10);
       // std::cout << t << std::endl;
    }

    std::cout << "test, memmove: " << t.elapsed() << " second" << std::endl;
}


{
    Timer t;
    for (int i = 0; i < 1000000; i++){

        std::string test = "small_string";
        std::string test2_1 = test;   // line 1
    }

    std::cout << "test, str copy: " << t.elapsed() << " second" << std::endl;
}


{
    Timer t;
    for (int i = 0; i < 1000000; i++){

        std::string test = "small_string";
        std::string test2_2 = std::move(test); // line 2
    }
    std::cout << "test, str move: " << t.elapsed() << " second" << std::endl;
}

結果是:(調試版本)

測試,memcpy:0.0090005秒

測試,記憶:0.0110006秒

測試,str復制:4.92528秒

測試,str移動:4.52926秒

我知道memcpy應該比memmove更快,而我的前兩個測試案例證明了這一點。 但是std :: string的結果不同...移動版本比復制版本快。 我什至不知道為什么甚至要研究std :: string的實現,但我沒有找到任何可以說服我這樣做的東西。

================================================== =====

結果:(發布版本)

測試,memcpy:0秒

測試,記憶:0.0080004秒

測試,str復制:0.0330019秒

測試,str移動:0.0290017秒

嗨,我很好奇哪個版本的字符串創建速度很快。 test2_1還是test2_2?

這似乎是一個過早優化的明顯例子。 兩種形式甚至都不相等,因此詢問哪種更快是荒謬的。

編寫正確的代碼,僅在出現性能問題時才擔心微優化。

第1行保持test不變,因此保持相同的值。 第2行修改了test ,使其處於未指定狀態。

如果您的代碼在創建另一個字符串后不依賴於test的值,則應使用std::move因為它表達了所需的語義(並且如果該字符串不適合小字符串緩沖區,它將肯定更快)。

如果您的代碼事后關心test的值,則不要使用std::move ,而只是執行一個副本。

對蘋果和橙子之間的差異進行基准測試是浪費時間。

在調試版本中對微小差異進行基准測試會浪費大量時間。 如果您關心性能,則需要啟用優化。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM