Object.toString, toHash, opCmp, opEquals

Quirin Schroll qs.il.paperinik at gmail.com
Wed Jun 5 17:42:20 UTC 2024


On Friday, 26 April 2024 at 18:28:00 UTC, Per Nordlöw wrote:
> On Thursday, 25 April 2024 at 23:06:27 UTC, Walter Bright wrote:
>> The prototypes are:
>>
>> ```
>> string toString();
>> size_t toHash() @trusted nothrow;
>> int opCmp(Object o);
>> bool opEquals(Object o);
>> ```
>>
>> which long predated `const`. The trouble is, they should be:
>
> Shouldn't some or all of them be qualified as scope aswell?

Being cheeky, if a class doesn’t have the following, you must 
explain yourself in code review:
```d
string toString() const scope pure nothrow;
size_t toHash() const scope pure nothrow @nogc;
int opCmp(const scope Object o) const scope pure nothrow @nogc;
bool opEquals(const scope Object o) const scope pure nothrow 
@nogc;
```

IMO, this is an all-or-nothing game. Either expect everything 
that’s reasonable or nothing. And the fact of the matter is, when 
you ask, “why would it mutate?” you must also ask, “why would it: 
keep a reference around, mutate global state, allocate memory 
(except for `toString`), or throw exceptions?” because doing any 
of those would be unorthodox.

However, I’m with Timon here, that those shouldn’t be forced onto 
the user. Ideally, `Object` is empty (devoid of any functions) 
and there is an optional-to-inherit-from class or a mixin 
template that adds all those functions with some default 
implementation which is `@safe`, too.


More information about the Digitalmars-d mailing list