Most efficient way to assign values to maps

前端 未结 6 1282
北荒
北荒 2021-02-07 19:30

Which way to assign values to a map is most efficient? Or are they all optimized to the same code (on most modern compilers)?

   // 1) Assignment using array ind         


        
6条回答
  •  野趣味
    野趣味 (楼主)
    2021-02-07 20:03

    Even though there has been a couple of good answers already I thought I might as well do a quick benchmark. Ran each one 5 million times and used c++11's chrono to measure the time it took.

    Heres the code:

    #include 
    #include 
    #include 
    #include 
    
    // 5 million
    #define times 5000000
    
    int main()
    {
        std::map foo1, foo2, foo3, foo4, foo5;
        std::chrono::steady_clock::time_point timeStart, timeEnd;
        int x = 0;
    
        // 1) Assignment using array index notation
        timeStart = std::chrono::steady_clock::now();
        for (x = 0; x <= times; x++)
        {
            foo1[std::to_string(x)] = 12345;
        }
        timeEnd = std::chrono::steady_clock::now();
        printf("1) took %i milliseconds\n", (unsigned long long)std::chrono::duration_cast(timeEnd-timeStart).count());
    
        // 2) Assignment using member function insert() and STL pair
        timeStart = std::chrono::steady_clock::now();
        for (x = 0; x <= times; x++)
        {
            foo2.insert(std::pair(std::to_string(x), 12345));
        }
        timeEnd = std::chrono::steady_clock::now();
        printf("2) took %i milliseconds\n", (unsigned long long)std::chrono::duration_cast(timeEnd-timeStart).count());
    
        // 3) Assignment using member function insert() and "value_type()"
        timeStart = std::chrono::steady_clock::now();
        for (x = 0; x <= times; x++)
        {
            foo3.insert(std::map::value_type(std::to_string(x), 12345));
        }
        timeEnd = std::chrono::steady_clock::now();
        printf("3) took %i milliseconds\n", (unsigned long long)std::chrono::duration_cast(timeEnd-timeStart).count());
    
        // 4) Assignment using member function insert() and "make_pair()"
        timeStart = std::chrono::steady_clock::now();
        for (x = 0; x <= times; x++)
        {
            foo4.insert(std::make_pair(std::to_string(x), 12345));
        }
        timeEnd = std::chrono::steady_clock::now();
        printf("4) took %i milliseconds\n", (unsigned long long)std::chrono::duration_cast(timeEnd-timeStart).count());
    
        // 5) Matthieu M.'s suggestion of C++11's emplace
        timeStart = std::chrono::steady_clock::now();
        for (x = 0; x <= times; x++)
        {
            foo5.emplace(std::to_string(x), 12345);
        }
        timeEnd = std::chrono::steady_clock::now();
        printf("5) took %i milliseconds\n", (unsigned long long)std::chrono::duration_cast(timeEnd-timeStart).count());
    
        return 0;
    }
    

    The output for 5 million iterations is:

    1) took 23448 milliseconds
    2) took 22854 milliseconds
    3) took 22372 milliseconds
    4) took 22988 milliseconds
    5) took 21356 milliseconds
    

    GCC version:

    g++ (Built by MinGW-builds project) 4.8.0 20121225 (experimental)
    

    My machine:

    Intel i5-3570k overclocked at 4.6 GHz
    

    EDIT1: Fixed the code and redid the benchmark.

    EDIT2: Added Matthieu M.'s suggestion for C++11's emplace and he is right, emplace is fastest

提交回复
热议问题