如何为括号运算符定义一个setter?

时间:2015-08-23 02:27:09

标签: c++

让我说我有这个课程:

struct testy {
    std::array<int, 10> data;
    float operator[] (int idx) const        { return 1 / data[idx]; }
    float &operator[](int idx)              { return ??? }
};

我想要发生的事情是,例如,当我写

testy Pineapple;
Pineapple[1] = 0.1;

然后实际发生的是

Pineapple.data[1]= 1 / 0.1;

我开始编写括号重载,然后意识到通过引用返回的第二个实际上做了转换数据本身的任何逻辑,所以我有点难过。

是的,我知道我可以写一个setter函数,但是这个数组会被各种算法大量使用,我希望从编码方面尽可能方便地访问它。

2 个答案:

答案 0 :(得分:4)

通常的方法是使用代理来测试元素:

struct testy {
    std::array<int, 10> data;
    float operator[] (int idx) const        { return 1.0 / data[idx]; }
private:
    struct element {
        int &el;
        element(int &a) : el(a) {}
        operator float() const { return 1.0 / el; }
        float operator=(float val) const {
            el = 1.0/val;
            return val; } };
public:
    element operator[](int idx) { return element(data[idx]); }
};

答案 1 :(得分:1)

这是一个非常基本的代理类解决方案:

#include <iostream>
#include <array>

struct testy; // forward declaration

class proxy
{
private:
    testy& _t;
    int _idx;
public:
    proxy(testy& t, int idx): _t(t), _idx(idx) {}
    proxy& operator=(double val);
    operator double() const; // conversion to double
};

struct testy {
    std::array<double, 10> data;
    double operator[] (int idx) const { return 1 / data[idx]; }
    proxy operator[](int idx)        {return proxy(*this, idx);}
};

proxy& proxy::operator=(double val)
{
    _t.data[_idx] = 1. / val;
    return *this;
}

proxy::operator double() const
{
    return _t.data[_idx];
}

int main()
{
    testy Pineapple;
    Pineapple[1] = 0.1;
    std::cout << Pineapple[1] << std::endl;
}

Live on Coliru