ProtoObject and comparison for equality and ordering
Jonathan Marler
johnnymarler at gmail.com
Wed May 15 14:05:16 UTC 2019
On Wednesday, 15 May 2019 at 00:19:05 UTC, Andrei Alexandrescu
wrote:
> On 5/14/19 10:06 PM, Mike Franklin wrote:
>> On Tuesday, 14 May 2019 at 20:36:08 UTC, Eduard Staniloiu
>> wrote:
>>
>>> Should `opCmp` return a float?
>>>
>>> The reason: when we attempt to compare two types that aren't
>>> comparable (an unordered relationship) we can return
>>> float.NaN. Thus we can differentiate between a valid -1, 0, 1
>>> and an invalid float.NaN comparison.
>>
>> Seems like a job for an enum, not a float or an integer.
>
> I repeat myself: this won't work.
>
> Recall that a < b is lowered into a.opCmp(b) < 0. So we have a
> comparison against the literal 0. For that float works nicely
> because nan etc etc.
Like you say, returning a float is the only way to allow a
4-state result when comparing with 0. However, since the Ordered
interface is now a template, we can query the Type to see what
they prefer:
//
// Allow the application to pick a result they want to use.
// Here's some example options that could be made available.
//
enum AlwaysComparableOpCmpResult : int
{
lower = -1, equal = 0, higher = 1
}
enum SometimesNonComparableOpCmpResult : float
{
lower = -1, equal = 0, higher = 1, nonComparable = float.nan
}
//
// A template that exposes the logic used to determine the opCmp
return type
//
template OpCmpReturnType(T)
{
static if (is(typeof(T.OpCmpResult))
alias OpCmpReturnType= T;
else
alias OpCmpReturnType= AlwaysComparableOpCmpResult; //
Default?
}
interface Ordered(T)
{
OpCmpReturnType!T opCmp(scope const T rhs);
}
Policy-Based Programming anyone?
In the end, the only requirement of the return type of opCmp is
that it being comparable to a literal "0". So why not let the
application decide?
More information about the Digitalmars-d
mailing list