代码之家  ›  专栏  ›  技术社区  ›  alfC

在Range-v3中有读写视图的方法吗?

  •  1
  • alfC  · 技术社区  · 5 年前

    Range-v3 可以轻松创建现有容器的视图。例如

    #include<range/v3/view/transform.hpp>
    #include<cassert>
    
    int main(){
        std::vector<double> v = {1,2,3};
        auto range = v | ranges::v3::view::transform([](auto x){return x*2;});
        assert( range[1] == 4 );
    //    range[1] = 4; // error cannot write to an l-value
    }
    

    这些视图自然是只读的。 我想知道是否有任何方法可以在范围v3内创建读写视图?

    我很感激这样的事情比只读要复杂得多,而且并不总是可能的,但是我仍然想知道在range-v3中是否有一个协议可以直接使用它或者实现它。

    例如,我看到了派生类的示例 ranges::view_facade 实现成员函数的 read() (我再也找不到这个例子,范围v3的文档确实分散在周围)。A怎么样 write(...) 成员函数?

    我在找一些假设 bi 方向性 transform 像这样的代码:

    #include<range/v3/view/transform.hpp>
    #include<cassert>
    
    int main(){
        std::vector<double> v = {1,2,3};
        auto range = v | ranges::v3::view::bitransform([](double x){return x*2;}, [](double x){return x/2;}); // direct and inverse function for read and write
        assert( range[1] == 4 );
        range[1] = 8; // error cannot write to an l-value
        assert( range[1] == 8 );
        assert( v[1] == 4 );
    }
    
    1 回复  |  直到 5 年前
        1
  •  1
  •   cpplearner    5 年前

    你可以做 transform_view 具有代理类型的元素:

    #include<vector>
    #include<range/v3/view/transform.hpp>
    #include<cassert>
    
    struct proxy {
        double& x;
        operator double() { return x*2; }
        void operator=(double y) { x = y / 2; }
    };
    
    int main(){
        std::vector<double> v = {1,2,3};
        auto range = v | ranges::v3::view::transform([](auto& x){return proxy{x};});
        assert( range[1] == 4 );
        range[1] = 8;
        assert( range[1] == 8 );
        assert( v[1] == 4 );
    }