在同一个类中强制使用Getter / Setter(C ++)

时间:2011-08-25 08:16:27

标签: c++ member setter getter invariants

在C ++中是否有办法在类中强制使用getter或setter?

class C{
   private:
   int x;        // should only be Changed by setX();

   private:
   setX(int i){
       (...)     // enforce some complicated invariantes
       x = i;
   };

   m(){
      x = 5;     // should not not allowed
   }
}

我唯一想到的是将所有 super-private 成员作为私有变量放入带有受保护getter / setter的抽象基类中。

但这听起来不太好。

是否有更常见的方法或惯例可以确保每个人都使用制定者?

(我的目的: 如果类变大,我发现很难记住哪些变量带有不变量。目前在设置我搜索的任何变量之前,我是否创建了一个getter或setter(以确定我是否必须考虑不变量)。但我希望每次都能摆脱这种不专业的搜索。)

4 个答案:

答案 0 :(得分:3)

你可以利用这样的构图:

class C_int
{
public:
    void setX(int i)
    {
        /* enforce invariants */
        x = i;
    }

private:
    int x;
};

class C
{
pulbic:
    void m()
    {
        x.setX(5);
        // x.x = 5; // Won't compile.
    }

private:
    C_int x;
};

但我觉得奇怪,这对你来说是个实际问题,恕我直言。你是C班及其成员的作家。您可以控制x变量的读/写方式,x不属于该类的公共接口。虽然其他人(例如维护者)确实可以编写将来打破不变量的代码,但单元测试应该能够涵盖这些情况。

答案 1 :(得分:1)

a)在整个代码库中使用访问器以保持一致性。那么您将更容易发现对成员的直接访问。如果你需要特殊的访问器,那么创建特殊的方法:

void setFoo(const t_foo& foo) {
    assert(foo.isValid());
    this->d_foo = foo;
}

void invalidateFoo() {
    this->d_foo = t_foo::InvalidFoo();
}

b)得到答案:我经常创建一个内部类(暂时在某些情况下):

class C {
    class t_inner {
    public:
    /* ... */
        void setX(int arg) {
            /* enforce some complicated invariants... */
            this->x = arg;
        }
        const int& getX() const {
            /* ... */
            return this->x;
        }
    private:
        int x;
    };
public:
/* ... */
private:
/* ... */
    void m() {
        this->inner().setX(5);
    }
private:
    t_inner d_inner;
};

答案 2 :(得分:0)

干净的答案是。没有语言功能;你可以做一些变化来实现它,但这会使你的代码混乱。

答案 3 :(得分:0)

在Visual C ++中,__declspec( property )可用于具有此功能:

__declspec(property(put=setFunction, get=getFunction)) data-type property-name; 

请参阅此article