1

我需要为定义如下的接口实现模拟:

class Foo
{
public:
  void sendEvent(int id) const = 0;
}

我的模拟类需要保存所有发送给类的事件 ID。这就是我打算这样做的方式。

class FooMock : Foo
{
private: 
  m_vector std::vector<int>;
public:
  void sendEvent(int id) const {m_vector.push_back(id);}

}

但显然编译器拒绝这种构造。是否有任何解决方案(假设界面无法更改)?

我意识到我可以为此使用两个类。但是有没有办法让编译器关闭并允许我这样做,类似于 const_cast?

4

4 回答 4

6

您可以制作矢量mutable,以便可以从 const 方法中对其进行修改,如下所示:

mutable std::vector<int> m_vector;

但是请注意,这使得向量在所有方法中都是可变的。如果您只想从单个方法对其进行写入,则 a 的侵入性较小,因为您只需为单个调用const_cast就将 constness 转换为away :this

FooMock * const that = const_cast<FooMock * const>(this);
that->m_vector.push_back(id);

我在这里有点迂腐 - 在 const 方法中,this具有类型T const * const(因此被指向的对象以及指针本身都是 const )。const_cast只是抛弃了对象的常量,而不是指针的常量。

于 2011-09-16T14:51:53.500 回答
2

另一种没有可变(当它不可用时)和 const_cast 的方法是使用指针成员。指针不遵循常量。

class FooMock : Foo
{
private: 
  boost::scoped_ptr<std::vector<int> > m_vector;
public:
  FooMock() : m_vector(new std::vector<int>) { }
  void sendEvent(int id) const {m_vector->push_back(id);}
}

如果可能,我会使用 mutable 进行模拟。

于 2011-09-16T15:17:48.033 回答
1

成员函数的 const-ness 是函数签名的一部分。你无法摆脱它。

但是,您可以将成员定义为mutable,您希望在 const 成员函数中对其进行变异。mutable即使在 const 成员函数中,即使对象是 const ,关键字也会使成员可变/可修改。

于 2011-09-16T14:55:14.460 回答
0

您可以标记m_vectormutable

mutable std::vector<int> m_vector;

mutable产生了一些类似的争议const_cast,并导致了一些关于它的真正含义的理论讨论const。基本上,只要外部行为保持类似 const 的状态,这里就是合理的,我认为在这个例子中是正确的。

于 2011-09-16T14:52:27.203 回答