On Wednesday, March 20, 2013 01:17:13 Dan wrote: > This is true, but then my code is by definition not standard. > However, theoretically, the language writers could. For example, > any '==' could be lowered to a 'standard' function, probably > better named 'intancesDeepEqual(a,b)' and that function could use > reflection to provide equal when not available else call opEquals > if it is available. Similar with opCmp, dup, idup, ... > In other words, in the vein of the original poster, why not allow > all of these nice goodies (equality comparison, opCmp comparison, > dup) without requiring boilerplate code while still > honoring/using it when it is provided.
There _are_ defaults for ==, and it really does quite a lot for you (e.g. recursively using == on each of a type's member variables), so you don't always have to define opEquals, but as soon as you have a layer of indirection (aside from arrays), you do have to define opEquals, or you'll generally end up checking for reference/pointer equality rather than equality of the actual objects. And in some cases, that's exactly the right thing to do. In others, it's not. It all depends on the context. As for comparing ranges, it would actually be very bad for performance if they defaulted to what equal does (particularly with regards to strings), and the language really doesn't do much to support ranges directly. Aside from foreach, they're completely a library construct. And really, equal exists with the idea that ranges of different types (but the same element type) can be compared, which isn't what you're generally trying to do with opEquals at all. If you want to avoid boilerplate, then use mixins. It should be fairly trivial to define a mixin such that you can do something like mixin(defineOpEquals!(typeof(this))); which defines an opEquals which does deep comparison. But also remember that what is necessary for deep comparison often depends on the types being compared (e.g. a range may or may not require equal to get the comparison that you want), so while it may be possible to define a mixin which creates an opEquals which will work in most situations, there are plenty where it won't. For instance, given that the standard library supports ranges, it's likely that something like defineOpEquals would know about them and do what is most likely to be the correct thing for them, but if ranges weren't part of the standard library, thhen defineOpEquals wouldn't know about them and couldn't handle them properly. The same will be true for any user-defined type that requires a particular idiom in order to be compared correctly. - Jonathan M Davis