Jon Lang wrote:
On Wed, Sep 30, 2009 at 11:58 PM, <pugs-comm...@feather.perl6.nl> wrote:
+C<Complex> is an immutable type. Each C<Complex> object stores two numbers,
+the real and imaginary part. For all practical purposes a C<Complex> with
+a C<NaN> in real or imaginary part may be considered a C<NaN> itself (and
+C<(NaN + 1i) ~~ NaN> is C<True>).
I'm not sure that I feel comfortable locking C<Complex> into
rectilinear coordinates as its internal storage method, as there will
be cases where the code operates more smoothly if you're using polar
coordinates to store the numbers: we should leave the inner workings
up to the Parrots to decide. But whichever approach gets used, if
either component is NaN, then the complex number should also be NaN.
I'm not sure if the idea is applicable to Perl 6 because Perl 6 already has an
alternative but ...
One of the features of my Muldis D language is called possreps (possible
representations) where you may define more than one alternative set of
attributes for a data type (and if more than one, you also define functions to
map between each attribute set) and then the implementation can choose for
itself which of those representations (or it can pick yet another one of its
own) is the actual one used physically behind the scenes and which is virtual,
and the user could use either as if it were the real one.
What Perl 6 could do with this concept is for example it can define for some
classes multiple possible object attribute sets, so users know they can use any
of those, and then each Perl 6 implementation can choose what to do natively.
So the Perl 6 spec can and should enumerate the various reasonable alternative
sets of attributes that a Complex object could have, and the Parrots can choose
which to use internally, or could use more than one on a case-by-case basis.
Note that ideally this would be a feature that user-defined classes can use, and
not just language built-in ones.
Now that I think about it, one way this could work within Perl 6's existing
features is that Complex could be a role and each of the possible
representations could be a class that does that role. On the other hand ...
Perhaps how my actual proposal could be realized is as sugar in the language
where one could write say:
class A {
possrep B {
has $c;
has $d;
}
possrep E {
has $f;
has $g;
}
my submethod E_from_B ($c, $d) { <returns $f, $g values> }
my submethod B_from_E ($f, $g) { <returns $c, $d values> }
}
Then users could say for example:
my A $x = A.B.new( :c<1>, :d<2> );
my A $y = A.E.new( :f<4>, :g<5> );
my $c = $y.B.c;
my $f = $x.E.f;
Of course, actual details or syntax could be different, but I think this general
idea would be useful.
Note that in my actual proposal, B and E are *not* classes so doing "my E $foo"
is invalid; the only class here is A. Now Perl 6 may choose to design differently.
Now in Muldis D this system is strict and requires that one can round-trip
between any 2 possreps and have identical attribute values to what one started
with, so the Complex example where conversion would by nature be approximate
wouldn't work there; but in Perl or a language where nonidentical round-trips
are allowed, this may work for Complex too. But then the implementation would
have to always use the same physical representation for all objects of the same
class, or else it wouldn't always DWIM when some one tries an exact equality
test with objects.
-- Darren Duncan