在程序中使用STL(第7章)(条款44,45)

条款44:容器的成员函数优先于同名的算法

这个条款应该是毫无疑问的,下面是书中给出的理由:

1)成员函数往往更快;

2)成员函数通常与容器集合的更加紧密,特别是关联容器,而这时算法所不能的,算法比较处理通用性的东西;

    void listTest() {
        // 成员函数
        list<int> l1{1,9,7,6,4};
        list<int> l2{2,8,3,5,};
        l1.sort();
        l2.sort();
//        l1.merge(l2);

        // 算法
        list<int> l;
        std::merge(l1.begin(), l1.end(), l2.cbegin(), l2.cend(), std::back_inserter(l));

        return;
    }

条款45:正确区分count, find, binary_search, lower_bound, upper_bound, equal_range

场景一、区间无序

场景二、区间有序

场景三、关联容器

直接上一张书中的截图

练习代码

    void vectorTest() {
        vector<int> vec{5, 5, 9, 7, 8, 6, 1, 2, 6, 7, 6, 3, 4};
        // 无序场景的查找、计数
        auto i1 = std::find(vec.cbegin(), vec.cend(), 6);  // 使用 operator==
        if (i1 != vec.cend()) {
            // exist 6
        } else {
            // not exist 6
        }
        int num = std::count(vec.cbegin(), vec.cend(), 6); // 6的数量
        auto i2 = std::find_if(vec.cbegin(), vec.cend(), [](int x) { return x == 6; });  // 是否存在6

        // 有序场景的查找、计数
        std::sort(vec.begin(), vec.end());
        bool exist6 = std::binary_search(vec.cbegin(), vec.cend(), 6); // 是否存在6
        auto il = std::lower_bound(vec.cbegin(), vec.cend(), 6);
        if (il != vec.end() && *il == 6) {
            // exist 6
            // 特别说明,这儿的用法在别的地方可能有问题,*il == 6是相等性的判断,其实算法是等价性的判断
            // 因此如果序列中是对象,排序规则中很可能只用到了部分成员,比如工号,而没有用到员工名字,则这样的相等判断是有问题的
            // upper_bound同理
        }
        auto iu = std::upper_bound(vec.cbegin(), vec.cend(), 6);
        int num6 = std::distance(il, iu);  // 6的数量
        auto ipair = std::equal_range(vec.cbegin(), vec.cend(), 6);
        if (ipair.first != ipair.second) {
            // exist 6
        }
        num6 = std::distance(ipair.first, ipair.second); // 6的数量
        num6 = ipair.second - ipair.first; // 6的数量

        // 有序场景针对某些位置的操作
        vec.insert(vec.begin(), 0); // 仅测试,这个插入会导致顺序错误
        vec.insert(std::lower_bound(vec.cbegin(), vec.cend(), 6), 20); // 仅测试,这个插入会导致顺序错误
        std::sort(vec.begin(), vec.end());
        vec.insert(std::upper_bound(vec.cbegin(), vec.cend(), 6), 20); // 仅测试,这个插入会导致顺序错误
        std::sort(vec.begin(), vec.end());

        vec.erase(vec.begin(), std::lower_bound(vec.cbegin(), vec.cend(), 5)); // 将5前面的元素都删除
        vec.erase(std::upper_bound(vec.cbegin(), vec.cend(), 6), vec.end()); // 将6后面的元素都删除

        return;
    }

猜你喜欢

转载自blog.csdn.net/u010323563/article/details/112408207