std::string_view 类

是什么?为什么?怎么用?

将 std::string_view 作为函数的参数的类型,在向函数传参时,既可以传 std::string,还可以传 C 风格字符串,就不用再因为字符串的类型有多种,而不得不写多个函数重载。

当函数需要一个只读字符串作为其参数之一时,推荐使用 std::string_view 代替 const string&const char*

返回字符串的函数应返回 const string& 或 string ,但不能返回 string_view 。返回 string_view 会带来使返回的 string_view 无效的风险。

代码如下:

#include <iostream>
#include <string>
#include <string_view>

// 提取文件的扩展名
std::string extractExtension(std::string_view filename) {
    // 为了防止意外复制 `string_view` 中的字符串,不能隐式地从 `string_view` 构造 `string`,
    // 因此这里使用显式的 `string` 构造函数
    return std::string {filename.substr(filename.rfind('.'))};
}

int main() {
    {
        // 可以向接收 std::string_view 类型参数的函数传多种类型的字符串
        
        // 传 std::string
        std::string filename{R"(c:\temp\my file.txt)"};
        std::cout << "C++ string: " << extractExtension(filename) << std::endl;

        // 传 const char*
        const char* filename2{R"(c:\temp\my file.txt)"};
        std::cout << "C string: " << extractExtension(filename2) << std::endl;

        // 传字符串字面量
        std::cout << "Literal: " << extractExtension(R"(c:\temp\my file.txt)") << std::endl;
    }

    {
        // 拼接 string 和 string_view
        std::string str1 {"hello"};
        std::string_view sv1 {" world"};

        // 方法1,不能直接用 + 运算符拼接 string 和 string_view
        // auto result {str1 + sv1};  // 编译出错
        auto result {str1 + std::string{sv1}};
        std::cout << result << std::endl;

        // 方法2,使用 string 的 append() 成员函数
        std::string result2 {str1};
        result2.append(sv1.data(), sv1.size());
        std::cout << result2 << std::endl;
    }

    return 0;
}

成员函数 remove_prefix()

代码参考自:std::basic_string_view<CharT,Traits>::remove_prefix – cppreference.com

#include <iostream>
#include <string>
#include <string_view>

// 计算一个字符串内,某子字符串出现的次数
std::size_t count_substrings(std::string_view hive, std::string_view const bee) {
    if (hive.empty() || bee.empty()) {
        return 0;
    }

    std::size_t buzz{};
    while (bee.size() <= hive.size()) {
        const auto pos {hive.find(bee)};
        if (pos == hive.npos) {
            break;
        }

        ++buzz;
        hive.remove_prefix(pos + bee.size());
    }

    return buzz;
}

int main() {
    const char* hive {"bee buzz bee buzz bee"};
    std::cout << count_substrings(hive, "bee") << " 个 bee 在 hive 中" << std::endl;

    return 0;
}

std::string_view 类》有一个想法

  1. Pingback引用通告: Chapter 2 Exercises – Professional C++ | 煲仔饭

发表回复

您的电子邮箱地址不会被公开。 必填项已用 * 标注