Boost Range适配器制作集合



我想编写一个提升适配器,以放在适配器链的末尾创建一个集合,例如:

set<string> s = input | filtered(...) | transformed(...) | to_set;

使用方法3.1我编写了下面的代码,该代码似乎按预期工作:

namespace detail
{
    struct to_set_forwarder
    {
    };
};
template <class R> inline auto operator|(R& r, detail::to_set_forwarder)
{
    return set<R::value_type>(r.begin(), r.end());
}
template <class R> inline auto operator|(const R& r, detail::to_set_forwarder)
{
    return set<const R::value_type>(r.begin(), r.end());
}
namespace
{
    const auto to_set = detail::to_set_forwarder();
}
void F()
{
    vector<string> input{ "1", "2", "3" };
    auto result = input
        //| boost::adaptors::filtered([](const auto& _) { return true; })
        | to_set;
}

错误C2338:C 标准的const元素的禁止容器,因为分配器不正确。

如果我将第一个参数用于operator|&&,那么直到我取消 filtered()行,然后才能得到:

错误c2825:'r':当后跟'::'

时,必须是类或名称空间

做到这一点的正确方法是什么?

就像它所说的那样,标准容器无法存储const元素。您也不想要(因为无论如何都存储了副本。如果您想要它们的const,则可以制作容器const(。

修复程序是:

template <class R> inline auto operator|(const R& r, detail::to_set_forwarder)
{
    return std::set<typename R::value_type>(r.begin(), r.end());
}

(删除const(。

活在coliru

#include <boost/range.hpp>
#include <boost/range/adaptors.hpp>
#include <set>
#include <vector>
#include <iostream>
#include <string>
namespace detail
{
    struct to_set_forwarder
    {
    };
}
template <class R> inline auto operator|(R& r, detail::to_set_forwarder)
{
    return std::set<typename R::value_type>(r.begin(), r.end());
}
template <class R> inline auto operator|(const R& r, detail::to_set_forwarder)
{
    return std::set<typename R::value_type>(r.begin(), r.end());
}
namespace
{
    const auto to_set = detail::to_set_forwarder();
}
void F()
{
    std::vector<std::string> input{ "1", "2", "3", "2" };
    auto result = input
        | boost::adaptors::filtered([](const auto& _) { return true; })
        | to_set;
    for (auto x : result)
        std::cout << x << " ";
}
int main() {
    F();
}

打印

1 2 3

ps:您缺少typename资格(有时尝试其他编译器(

ps:您可以boost::copy_range

auto result = boost::copy_range<std::set<std::string> >(input
    | boost::adaptors::filtered([](const auto& _) { return true; })
    );

相关内容

  • 没有找到相关文章

最新更新