STL find 算法、set内置find算法性能测试

本文对比了STL库中list和set容器的查找性能,通过大量数据测试,发现STL find算法在list中的性能优于while循环,而set的查找性能又优于list。

时常会遇到从list中查找某个值是否存在,由于STL库中的list并未提供find方法,此时我们有两种选择(这里指通用方法,其他还有建立hash值索引等方法):一是通过STL算法中的find方法查找给定值;二是通过while循环对比给定值。基于这两种通用的方法,现做一个查找性能对比。

对比方法:向list中存入大量的数据,分别通过这两种方法在该list中查找一个相同的给定数据值。

给定值条件:

1、给定值在list容器中一定存在。

2、给定值在list顺序容器中的位置靠近容器末尾位置,这样尽量增加查找对比次数。

测试结论:STL find算法内部做了对比优化,性能优于while循环方法。

测试代码如下:

#include "pch.h"
#include <iostream>
#include <list>
#include <set>
#include <algorithm>
#include <time.h>
#include <windows.h>

void logCurrentTime()
{
    SYSTEMTIME st = { 0 };
    GetLocalTime(&st);
    char mTime[255] = { 0 };
    sprintf_s(mTime, 100, "%d-%02d-%02d %02d:%02d:%02d",
        st.wYear,
        st.wMonth,
        st.wDay,
        st.wHour,
        st.wMinute,
        st.wSecond);
    std::cout << mTime << std::endl;
}

int main()
{
    std::cout << "Hello World!\n"; 
    std::list<std::string> myList;
    
    try 
    { 
        for (int i = 0; i < 8000000; ++i)
        {
            char myString[100] = { 0 };
            sprintf_s(myString, 100, "test string %d", i);
            //std::cout << "is index" << i<< std::endl;
            myList.emplace_back(myString);
        }
    }
    catch (std::bad_alloc) 
    { 
        std::cout << "is this has an memory error!" << std::endl;
        return 0;
    }
    
    const char *pStr = "test string 7999999";

    for (int i = 0; i < 2; ++i)
    {
        logCurrentTime();
        std::list<std::string>::iterator iter = std::find(myList.begin(), myList.end(), pStr);
        logCurrentTime();
        if (myList.end() != iter)
        {
            std::cout << "this value in list is finded:" << ((std::string)*iter).c_str() << std::endl;
        }

        logCurrentTime();
        iter = myList.begin();
        while (myList.end() != iter)
        {
            if (*iter == pStr)
            {
                break;
            }
            ++iter;
        }
        logCurrentTime();
        std::cout << "while this value is finded:" << ((std::string)*iter).c_str() << std::endl;
    }
}



二、list容器与set容器查找指定元素的对比:

对比方法:

分别向list和set容器中放入相同条目数的相同数据,通过各自的查找函数查找指定元素,对比查找输出时间。

给定值条件:参照第一条。

结论:set查找优于list(STL find算法)。

#include "pch.h"
#include <iostream>
#include <list>
#include <set>
#include <algorithm>
#include <time.h>
#include <windows.h>

void logCurrentTime()
{
    SYSTEMTIME st = { 0 };
    GetLocalTime(&st);
    char mTime[255] = { 0 };
    sprintf_s(mTime, 100, "%d-%02d-%02d %02d:%02d:%02d",
        st.wYear,
        st.wMonth,
        st.wDay,
        st.wHour,
        st.wMinute,
        st.wSecond);
    std::cout << mTime << std::endl;
}

int main()
{
    std::cout << "Hello World!\n"; 
    std::list<std::string> myList;
    std::set<std::string> mySet;
    
    try 
    { 
        for (int i = 0; i < 4000000; ++i)
        {
            char myString[100] = { 0 };
            sprintf_s(myString, 100, "test string %d", i);
            //std::cout << "is index" << i<< std::endl;
            myList.emplace_back(myString);
            mySet.emplace(myString);
        }
    }
    catch (std::bad_alloc) 
    { 
        std::cout << "is this has an memory error!" << std::endl;
        return 0;
    }
    
    const char *pStr = "test string 3999999";

    for (int i = 0; i < 2; ++i)
    {
        logCurrentTime();
        std::list<std::string>::iterator iter = std::find(myList.begin(), myList.end(), pStr);
        logCurrentTime();
        if (myList.end() != iter)
        {
            std::cout << "this value in list is finded:" << ((std::string)*iter).c_str() << std::endl;
        }

        logCurrentTime();
        std::set<std::string>::iterator iterS = mySet.find(pStr);
        logCurrentTime();
        if (mySet.end() != iterS)
        {
            std::cout << "this value in set is finded:" << ((std::string)*iter).c_str() << std::endl;
        }
    }
}

 

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值