error C2678: 二进制“+”: 没有找到接受类型 'volatile A' 的左手操作数的运算符(或者没有可接受的转换)

error C2678: binary '+': no operator found which takes a left-hand operand of type 'volatile A' (or there is no acceptable conversion)

我以前用 C++ 编程过,但已经好几年了。我是 C++11 的新手,遇到以下问题。

我的 class 比仅仅存储 "twice the value given in the constructor" 更复杂,但为了简单起见,这个例子只是将构造函数输入乘以 2。 class 必须隐式转换为 &来自 int,因此 operator int()operator=(const int) 和采用 int.

的构造函数

一切正常,除非我的 class 的一个实例被定义为 volatile。当我随后尝试对 volatile 实例进行操作时,Visual Studio 抱怨:

#include <iostream

class A
{
private:
   int _i;
public:
   A() = default;
   constexpr A(const int i) : _i(i*2) {}
   constexpr operator int() const { return _i/2; }
   A& operator=(const int i) { _i = i*2; return *this; }
};

//A va; // <---- this works (though I need it to be 'volatile')
volatile A va; // <--- this gives error C2678: binary '+': no operator found which takes a left-hand operand of type 'volatile A' (or there is no acceptable conversion)

int main()
{
   int j;
   j = va + 12; // <--- Here's where the error occurs
   std::cout << "j = " << j << std::endl;
}

看到错误表明存在 "no acceptable conversion",我尝试向 class 添加一个复制构造函数,该构造函数采用 volatile 其他构造函数,但这并没有解决问题:

   constexpr A(volatile const A& other) : _i(other._i) {}

我可以 "fix" 通过丢弃 volatile...

   j = (A)va + 12;

...但该解决方案对我不起作用,因为我的 class 实际上是模拟器环境的一部分,该环境试图模拟嵌入式硬件和 运行 模拟环境中的嵌入式代码.我的 class 必须充当硬件寄存器的替代品,我不能(或不想)在语句 j = va + 12; 中丢弃 volatile 因为那一行是嵌入式固件本身的一部分。是否有一些转换运算符或方法可以添加到我的 class A 中以使语句 j = va + 12; 无需修改即可工作?

您将 volatile 添加到了错误的位置。

为了在 j = va + 12 中执行加法,va 需要转换为 int,因为 A 中没有定义 operator+ =].现有的转换运算符被标记为 const,编译器将不会使用它来转换 volatile 对象。

解决方案是在您的 class 中添加一个额外的 operator int 来支持可变对象的转换:

constexpr operator int() volatile { return _i/2; }

您将需要现有的 const 一个和这个。