Skip to content

Instantly share code, notes, and snippets.

@zoffixznet
Created May 1, 2017 20:48
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save zoffixznet/f29917b3930b3e877df6da68271f192d to your computer and use it in GitHub Desktop.
Save zoffixznet/f29917b3930b3e877df6da68271f192d to your computer and use it in GitHub Desktop.
diff --git a/src/core/allomorphs.pm b/src/core/allomorphs.pm
index 1d3be22..5f03db4 100644
--- a/src/core/allomorphs.pm
+++ b/src/core/allomorphs.pm
@@ -1,5 +1,11 @@
+
+my role NumericStr {
+ # We use an empty role we make all allomorphs do so that we can
+ # make candidates that dispatch on it
+}
+
# the uses of add_I in this class are a trick to make bigints work right
-my class IntStr is Int is Str {
+my class IntStr is Int is Str does NumericStr {
method new(Int $i, Str $s) {
my \SELF = nqp::add_I($i, 0, self);
nqp::bindattr_s(SELF, Str, '$!value', $s);
@@ -13,7 +19,7 @@ my class IntStr is Int is Str {
multi method perl(IntStr:D:) { self.^name ~ '.new(' ~ self.Int.perl ~ ', ' ~ self.Str.perl ~ ')' }
}
-my class NumStr is Num is Str {
+my class NumStr is Num is Str does NumericStr {
method new(Num $n, Str $s) {
my \SELF = nqp::create(self);
nqp::bindattr_n(SELF, Num, '$!value', $n);
@@ -28,7 +34,7 @@ my class NumStr is Num is Str {
multi method perl(NumStr:D:) { self.^name ~ '.new(' ~ self.Num.perl ~ ', ' ~ self.Str.perl ~ ')' }
}
-my class RatStr is Rat is Str {
+my class RatStr is Rat is Str does NumericStr {
method new(Rat $r, Str $s) {
my \SELF = nqp::create(self);
nqp::bindattr(SELF, Rat, '$!numerator', $r.numerator);
@@ -44,7 +50,7 @@ my class RatStr is Rat is Str {
multi method perl(RatStr:D:) { self.^name ~ '.new(' ~ self.Rat.perl ~ ', ' ~ self.Str.perl ~ ')' }
}
-my class ComplexStr is Complex is Str {
+my class ComplexStr is Complex is Str does NumericStr {
method new(Complex $c, Str $s) {
my \SELF = nqp::create(self);
nqp::bindattr_n(SELF, Complex, '$!re', $c.re);
@@ -61,33 +67,7 @@ my class ComplexStr is Complex is Str {
}
# we define cmp ops for these allomorphic types as numeric first, then Str. If
-# you want just one half of the cmp, you'll need to coerce the args
-multi sub infix:<cmp>(IntStr:D $a, IntStr:D $b) {
- $a.Int cmp $b.Int || $a.Str cmp $b.Str
-}
-multi sub infix:<cmp>(RatStr:D $a, RatStr:D $b) {
- $a.Rat cmp $b.Rat || $a.Str cmp $b.Str
-}
-multi sub infix:<cmp>(NumStr:D $a, NumStr:D $b) {
- $a.Num cmp $b.Num || $a.Str cmp $b.Str
-}
-multi sub infix:<cmp>(ComplexStr:D $a, ComplexStr:D $b) {
- $a.Complex cmp $b.Complex || $a.Str cmp $b.Str
-}
-
-multi sub infix:<eqv>(IntStr:D $a, IntStr:D $b) {
- $a.Int eqv $b.Int || $a.Str eqv $b.Str
-}
-multi sub infix:<eqv>(RatStr:D $a, RatStr:D $b) {
- $a.Rat eqv $b.Rat || $a.Str eqv $b.Str
-}
-multi sub infix:<eqv>(NumStr:D $a, NumStr:D $b) {
- $a.Num eqv $b.Num || $a.Str eqv $b.Str
-}
-multi sub infix:<eqv>(ComplexStr:D $a, ComplexStr:D $b) {
- $a.Complex eqv $b.Complex || $a.Str eqv $b.Str
-}
-
+# you want just one half of the ===, you'll need to coerce the args
multi sub infix:<===>(IntStr:D $a, IntStr:D $b) {
$a.Int === $b.Int && $a.Str === $b.Str
}
diff --git a/src/core/operators.pm b/src/core/operators.pm
index 80910ad..2c49ba4 100644
--- a/src/core/operators.pm
+++ b/src/core/operators.pm
@@ -44,12 +44,18 @@ multi sub infix:<does>(Mu:U \obj, **@roles) is raw {
X::Does::TypeObject.new(type => obj).throw
}
-# we need this candidate tighter than infix:<cmp>(Real:D, Real:D)
-# but can't yet use `is default` at the place where that candidate
-# is defined because it uses `infix:<does>`
+# We need these candidate tighter than other ambiguous ones,
+# but can't yet use `is default` at the place where those candidates
+# are defined because `is default` uses `infix:<does>`
multi sub infix:<cmp>(Rational:D \a, Rational:D \b) is default {
a.isNaN || b.isNaN ?? a.Num cmp b.Num !! a <=> b
}
+multi sub infix:<cmp>(NumericStr:D $a, NumericStr:D $b) is default {
+ $a.Numeric cmp $b.Numeric || $a.Str cmp $b.Str
+}
+multi sub infix:<eqv>(NumericStr:D $a, NumericStr:D $b) is default {
+ $a.Numeric eqv $b.Numeric || $a.Str eqv $b.Str
+}
proto sub infix:<but>(|) is pure { * }
multi sub infix:<but>(Mu:D \obj, Mu:U \rolish) {
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment