相关疑难解决方法(0)

运算符重载的基本规则和习惯用法是什么?

注意:答案是按照特定的顺序给出的,但由于许多用户根据投票而不是给出的时间对答案进行排序,因此这里是答案索引,它们是最有意义的顺序:

(注意:这是Stack Overflow的C++常见问题解答的一个条目.如果你想批评在这种形式下提供常见问题解答的想法,那么发布所有这些的元数据的发布将是这样做的地方.这个问题在C++聊天室中受到监控,其中FAQ的想法一开始就出现了,所以你的答案很可能被那些提出想法的人阅读.)

c++ operator-overloading operators c++-faq

2074
推荐指数
8
解决办法
88万
查看次数

为什么我们必须在C#中定义==和!=?

C#编译器要求每当自定义类型定义运算符时==,它还必须定义!=(参见此处).

为什么?

我很想知道为什么设计师认为这是必要的,为什么当只有另一个运算符存在时,编译器不能默认为任何一个运算符的合理实现.例如,Lua允许您仅定义相等运算符,而您可以免费获得另一个运算符.C#也可以通过要求你定义==或者两者==和!=然后自动编译缺少的!=运算符来做同样的事情!(left == right).

我知道有一些奇怪的角落情况,其中一些实体可能既不平等也不平等(如IEEE-754 NaN),但这些似乎是例外,而不是规则.所以这并不能解释为什么C#编译器设计者将例外规则作为例外.

我已经看到了定义等式运算符的做工不好的情况,然后不等式运算符是一个复制粘贴,每个比较都被反转,每个&&切换到|| (你得到的重点......基本上!(a == b)通过De Morgan的规则扩展).编译器可以通过设计消除这种糟糕的做法,就像Lua的情况一样.

注意:对于运算符<> <=> =也是如此.我无法想象你需要以不自然的方式定义它们的情况.Lua允许您通过前者的否定自然地定义<和<=并定义> =和>.为什么C#不做同样的事情(至少'默认')?

编辑

显然有正当理由允许程序员实现对他们喜欢的平等和不平等的检查.一些答案指向可能很好的情况.

然而,我的问题的核心是为什么在C#中强制要求它通常逻辑上不必要?

它与.NET接口的设计选择形成鲜明对比,例如Object.Equals,IEquatable.Equals IEqualityComparer.Equals缺少NotEquals对应物表明框架将!Equals()对象视为不相等而且就是这样.此外,类Dictionary和类等方法.Contains()完全依赖于上述接口,即使定义了运算符也不直接使用运算符.事实上,当ReSharper生成相等成员时,它定义了两者==并且!=就其而言,Equals()即使只是用户选择生成运算符.框架不需要相等运算符来理解对象相等性.

基本上,.NET框架并不关心这些运算符,它只关心几种Equals方法.要求用户串联定义==和!=运算符的决定纯粹与语言设计有关,而与.NET有关的不是对象语义.

c# language-design

341
推荐指数
10
解决办法
1万
查看次数

为什么C++编译器没有定义operator ==和operator!=?

我非常喜欢让编译器为你做尽可能多的工作.在编写一个简单的类时,编译器可以为"free"提供以下内容:

  • 默认(空)构造函数
  • 复制构造函数
  • 析构函数
  • 赋值运算符(operator=)

但它似乎无法给你任何比较运算符 - 如operator==operator!=.例如:

class foo
{
public:
    std::string str_;
    int n_;
};

foo f1;        // Works
foo f2(f1);    // Works
foo f3;
f3 = f2;       // Works

if (f3 == f2)  // Fails
{ }

if (f3 != f2)  // Fails
{ }
Run Code Online (Sandbox Code Playgroud)

有这么好的理由吗?为什么执行逐个成员比较会成为问题?显然,如果类分配内存然后你要小心,但对于一个简单的类肯定编译器可以为你做这个?

c++ operators

286
推荐指数
11
解决办法
8万
查看次数