提问人:Henry Nissen 提问时间:11/2/2023 更新时间:11/2/2023 访问量:66
“多个运算符”!=“与这些操作数匹配”错误未停止编译?
"More than one operator "!=" matches these operands" error not stopping compilation?
问:
因此,我有一个模板类,它本质上只是另一个变量的包装器,这样我就可以为该变量设置目标值以及达到该值需要多少帧。每一帧,我都会调用一个进程函数,将其值向目标值移动。TargetVar
TargetVar
这是课程:
class BaseTargetVar {
public:
BaseTargetVar() {
TargetVarManager::get_instance()->register_target_var(this); //TargetVarManager just iterates
//through all registered TargetVars and calls their process funcs
}
virtual ~BaseTargetVar() {
TargetVarManager::get_instance()->unregister_target_var(this);
}
virtual void process() {}
};
template <class T> class TargetVar : public BaseTargetVar {
public:
TargetVar() = default;
TargetVar(T& other) {
if (val != other) {
val = other;
frames = 0;
}
}
TargetVar(const T& other) {
if (val != other) {
val = other;
frames = 0;
}
}
void process() override {
if (frames) {
val += target_change_per_frame;
frames--;
if (!frames) {
val = target_val;
}
}
}
void set_target_val(T target_val, unsigned int frames) {
if (target_val == this->target_val) return;
this->target_val = target_val;
target_change_per_frame = target_val - val;
target_change_per_frame /= frames;
this->frames = frames;
}
void set_val(const T& val) {
this->val = val;
}
T get_val() const {
return val;
}
T* get_val_addr() const {
return &val;
}
T get_target_change_per_frame() const {
return target_change_per_frame;
}
unsigned int get_frames() const {
return frames;
}
private:
T val{};
T target_val{};
T target_change_per_frame{};
unsigned int frames = 0;
};
在我的项目中,此类的主要用途之一是使用 a 来处理纹理的位置。因此,通常将 a 与 a 进行比较(例如,将纹理的位置与屏幕上的位置进行比较,即 to ),但将一个纹理与另一个纹理进行比较也很常见(例如,将纹理的位置与另一个纹理的位置进行比较,即 更改为 )。为了更方便,我在类中添加了以下运算符重载:TargetVar<glm::vec3>
TargetVar<T>
T
TargetVar<glm::vec3>
glm::vec3
TargetVar<T>
TargetVar<T>
TargetVar<glm::vec3>
TargetVar<glm::vec3>
TargetVar
template <typename U>
TargetVar<T>& operator=(const U& rhs) {
val = (T)rhs;
frames = 0;
return *this;
}
template <typename U>
bool operator==(const U& rhs) {
return val == rhs;
}
template <typename U>
bool operator!=(const U& rhs) {
return val != rhs;
}
template <typename U>
TargetVar<T>& operator=(const TargetVar<U>& rhs) {
if (this != &rhs) {
val = rhs.get_val();
frames = 0;
}
return *this;
}
template <typename U>
bool operator==(const TargetVar<U>& rhs) {
return val == rhs.get_val();
}
template <typename U>
bool operator!=(const TargetVar<U>& rhs) {
return val != rhs.get_val();
}
这个系统已经工作了几个星期,没有任何问题,但我注意到某些比较会导致 VS 出现错误。例如:
TargetVar<glm::vec3> tv1 = glm::vec3(0.0);
TargetVar<glm::vec3> tv2 = glm::vec3(0.0);
if (tv1 != tv2) {
/*
Error E0350 - more than one operator "!=" matches these operands:
function template "bool TargetVar<T>::operator==(const U &rhs) [with T=glm::vec3]", with reversed arguments
function template "bool TargetVar<T>::operator==(const TargetVar<U> &rhs) [with T=glm::vec3]", with reversed arguments
function template "bool TargetVar<T>::operator!=(const U &rhs) [with T=glm::vec3]"
function template "bool TargetVar<T>::operator!=(const TargetVar<U> &rhs) [with T=glm::vec3]"
operand types are: TargetVar<glm::vec3> != TargetVar<glm::vec3>
*/
}
if (tv1 == tv2) {
/*
Error E0350 - more than one operator "==" matches these operands:
function template "bool TargetVar<T>::operator==(const U &rhs) [with T=glm::vec3]", with reversed arguments
function template "bool TargetVar<T>::operator==(const TargetVar<U> &rhs) [with T=glm::vec3]", with reversed arguments
function template "bool TargetVar<T>::operator==(const U &rhs) [with T=glm::vec3]"
function template "bool TargetVar<T>::operator==(const TargetVar<U> &rhs) [with T=glm::vec3]"
operand types are: TargetVar<glm::vec3> == TargetVar<glm::vec3>
*/
}
if (tv1 != tv2.get_val()) {
//No errors
}
if (tv1 == tv2.get_val()) {
//No errors
}
if (tv1.get_val() != tv2.get_val()) {
//No errors
}
if (tv1.get_val() == tv2.get_val()) {
//No errors
}
这些错误实际上并没有阻止程序编译,但我想知道为什么 VS 认为 tv1 到 tv2 的比较有问题,而不是 tv1 到 tv2.get_val() 的比较有问题。
此外,出于好奇,我删除了 != 运算符重载,看看“带有反向参数”位是否会消失。它没有对现有错误进行任何更改,但它确实引入了以下错误,这些错误确实导致程序无法编译:
if (tv1 != tv2) {
/*
Error C2666 - 'TargetVar<glm::vec3>::operator ==': overloaded functions have similar conversions
*/
}
if (tv1 == tv2) {
/*
Error C2666 - 'TargetVar<glm::vec3>::operator ==': overloaded functions have similar conversions
*/
}
归根结底,该程序按原样运行良好,但我想知道为什么 VS 只在特定情况下有问题,以及除了手动将 .get_val() 放入我的所有操作之外,我是否还能做些什么。
答:
所以。。。。 运行生成时,序列错误来自实际编译器。 错误来自编辑器。编辑器对 C++ 代码的解释有时有点不稳定,因为它努力找出无效的代码,因为它正在编辑过程中。不再与类本身的声明匹配的类成员主体,诸如此类。Cxxxx
Exxxx
当编辑器出错时,它会影响“GoTo Definition”等操作,但不会阻止您构建。
编辑器经常出错,以至于我通常会从“错误列表”顶部的下拉列表中关闭编辑器的错误/警告消息。
实际上,我甚至几乎不使用“错误列表”窗口,而是更喜欢“输出”窗口的“构建”选项卡,在那里可以看到完整的错误消息,而无需强制进入整齐的 n 列表。
评论
const
template <typename U> bool operator==(const U& rhs) const { ... }