Darren Duncan wrote:
Jonathan Lang wrote:
>In terms of ordinal types, '>', '<', '>=', and '<=' would be the
>"generic" ordinal comparators, and you'd do the same sort of implicit
>or explicit type coercion that's done with '=='. Mind you, if you go
>with the ('==', '+==', '~==') set of equivalence operators, '+>' and
>'+<' would now mean "numerically greater than" and "numerically less
>than", respectively, and the shift-right and shift-left operators
>would have to be relabelled (e.g., to '+>>' and '+<<').
> Better, ditch the letter soup entirely: in
>reverse analogy to my original suggestion, use a '*' leading character
>to denote the generic comparators: '*<', '*>', '*<=', and '*>='.
I like that proposal a lot, in principle, as it gives us a lot more
flexability and visual consistency. I hope that @Larry can get
behind something like it.
Note that this is two competing suggestions: one where '==' means
'generic equivalence', '+==' means 'numeric equivalence', and '*=='
means 'string equivalence'; and another where '*==' means 'generic
equivalence', '==' means 'numeric equivalence', and 'eq' means 'string
equivalence' (with '<', '>', etc. following suit). The goal of the
second proposal is to leave existing operator names unchanged, while
the goal of the first proposal is to provide a consistent and
intuitive naming convention.
One detail to work out is whether we use *< etc or < etc for the
generic. Either option has its advantages or disadvantages.
(Whatever's chosen and any renaming fall-out from that, I don't think
a main operator can contain a << or >> like your bit-shift examples
since those could be confused with hyper-operators.)
Yes and no; binary hyper-operators require double arrows on both
sides, so it's possible that the parser _could_ distinguish
double-angle bit-shift operators from hyper-operators. Still, for the
sake of clarity, I could see basing bit-shifting off of thin-tailed
arrowheads: '+->' and '+<-'. Note that this isn't a problem with the
'*<' model: '*<' would be a generic less-than; '<' would be a numeric
less-than; 'lt' would be a stringified less than; '+<' would be a
numeric bit-shift; and '~<' would be a string-based bit-shift. No
>(Technically, the existence of '+==' and '~==' would imply the
>existence of '?==' for completeness sake; but I can't think of any
>reasonable case where '?==' would be used.)
I don't see that it would be a bad thing. Even if little used, it
does make conceptual sense. ?== checks if both arguments are the
same truth-wise, and !?== checks if they are different. Assuming we
defined for repeatable ordering purposes that False < True (which is
consistent with any common string or numifications of booleans), then
?< et al produce predictable results.
True enough. It's not _much_ of a mark in favor of the 'consistent
and intuitive naming convention' proposal; but it's a mark in its
And in fact, once we have a third column of order-determing
operators rather than just Num + Str, the arrangement of some
alphabetic and some not comes to look positively ugly. So better to
make them all alpha or all non, and it would seem non is better. So
== and < and so on for all comparing operators. (And as an aside, we
get rid of !ne.)
Another mark in its favor... :)
The two biggest marks against it are what it does to the bit-shift
operators (which isn't much of an issue IMHO; they're already changed
from perl5) and the drastic change from perl5-style thinking, where
numeric comparisons are effectively the default (which could very well
be a show-stopper).
>In effect, we're talking about an Ordinal role, which would package
>together the generic ordinal comparators ('*<', '*>', '*<=', '*>=',
>and 'cmp'), along with 'sort', 'min', and 'max'.
Yes. And I was thinking about an Ordinal role before too.
Logically, some types are ordinal (eg, numbers (except complex?),
strings, dates), or could be assigned a canonical ordinal form (eg,
booleans, bits) and some are simply not ordinal (probably eg, a
polygon or a collection type).
Complex numbers can be ordered, but only if you're willing to accept
that multiplication by a complex number will mess with that order in a
not-always-intuitive way (as opposed to non-zero real numbers, where
the order will always be either preserved exactly or completely
reversed). I've seen the arguments against the validity of ordering
complex numbers, and I don't find them very persuasive. That said,
even if complex numbers aren't ordinal, they _can_ be assigned a
canonical ordinal form. Perhaps a better name for the role might be
something along the lines of "Sortable"...
And yes, there _are_ cases where assigning a canonical ordering to a
type is counterintuitive at best.
So, while it could make sense to have an Ordinal role, which types
individually can .does(), and only those have <, >, <=, >=, <=>, min,
max, sort, etc, there is the question about how to handle types that
don't .does() Ordinal in some generic situations. Either they fail,
or there is some sort of fallback provided by Object, such as they
end up sorting on their memory addresses; but in the latter case, we
don't need an Ordinal role because every type will be doing it in
some fashion or other due to Object's defaults.
Have them fail outright: telling an object to do something that it
isn't designed to do should raise very loud complaints from the
>Tangentially related, I'd like to suggest that the negation
>meta-operator be generalized from comparison operators to any binary
>operator that returns a boolean value (or possibly even to any
>operator that returns a boolean value, so that '!?$x' would mean
>"coerce to boolean, then negate its value").
If I'm not mistaken, the negation meta-operator already does this.
Negated relational operators
Any infix relational operator may be transformed into its negative by prefixing
And so on. The section is brief (four lines, a two-entry table, and a
short list of examples), fits between Assignment operators and Hyper
operators, and doesn't mention anything other than infix relational
Jonathan "Dataweaver" Lang