You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C++20 std::ranges代码在不同编译器下的兼容性问题咨询

C++20 Ranges代码的编译器合规性判定

这段使用C++20 ranges库提取二维vector第一列的代码,在不同编译器版本中表现差异明显,以下是具体情况及合规性分析:

代码示例

#include <vector>
#include <string>
#include <ranges>
#include <iostream>

int main()
{
    // 返回仅包含可迭代容器第i个元素的范围
    auto ith_element = [](size_t i) {
        // 跳过前i个元素后取第一个元素
        return std::views::drop(i) | std::views::take(1);
    };

    // 返回第i列的遍历范围
    auto column = [ith_element](size_t i) {
        return std::views::transform(ith_element(i)) | std::views::join; // 提取输入范围中每个元素的第i个元素组成新范围
    };


    std::vector<std::vector<std::string>> myvec = {
        { "a", "aaa",   "aa"},
        {"bb",   "b", "bbbb"},
        {"cc",  "cc",  "ccc"}
    };

    for (auto const& v: myvec | column(0)){
        std::cout << v << std::endl;
    }
    return 0;
}

各编译器表现

  • GCC 10.1~10.4:编译通过,但输出错误内容
b
  • GCC 11.1、Clang:编译失败,报错信息如下
error: no match for 'operator|' (operand types are 'std::vector<std::vector<std::__cxx11::basic_string<char> > >' and 'std::ranges::views::__adaptor::_Pipe<std::ranges::views::__adaptor::_Partial<std::ranges::views::_Transform, std::ranges::views::__adaptor::_Pipe<std::ranges::views::__adaptor::_Partial<std::ranges::views::_Drop, long unsigned int>, std::ranges::views::__adaptor::_Partial<std::ranges::views::_Take, int> > >, std::ranges::views::_Join>')
  • GCC 11.2~12.2、MSVC 19.33:编译通过,输出预期结果
a
bb
cc

合规性分析

这段代码通过std::views::transform结合drop+take的视图管道,再用join扁平化结果,完全符合C++20标准中ranges库的规范。

  • GCC 10.x的错误输出源于早期ranges实现的bug,对视图组合的处理逻辑错位,导致元素提取错误。
  • GCC 11.1和Clang的编译失败,是因为当时的版本对ranges适配器的管道组合支持不完善,无法正确解析transform与join的复合适配类型。
  • GCC 11.2+和MSVC 19.33的行为符合C++20标准,它们正确实现了ranges库中视图组合、适配的规范逻辑,能够正常编译并输出预期结果。

内容的提问来源于stack exchange,提问作者joergbrech

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 04:05:28