David Robins wrote:
On Thu, 19 Dec 2002, Leopold Toetsch wrote:
This method is primarily used when the interpreter has need ofIn pdd02_vtables.pod morph() is defined to do exactly this.
coercing a PMC to a particular type, and isn't meant as a general
purpose casting tool. Compilers should only emit valid
transformations.
which doesn't seem to indicate that morph is the Right Thing,
docs also say, "If the morphing
can't be reasonably done, for example if an integer is
asked to turn into a PerlArray, then the PMC is first
destroyed, then recreated as an empty PMC ..."
which seems to indicate that morph is the Right Thing ;-)
Currently we are "morphing" perlscalars all over the place. We do this by replacing the vtable (and in case of strings) also changing flags. This is what morph would do anyway, w/o actually destroying the PMC but reusing the header (new vtable, new value, changed flags gives actually the same as a freshly allocated PMC of the desired type).
The current way to change a float to an int or a string is probably just what was intended to be done by the morph vtable func.
PMC* ret = SELF.clone();
Cloning or making a new PMC for each LHS isn't that cheap. I think we should reuse existing headers where possible. The same holds for string headers, which are currently sparely reused.
The (or one of the) subjects of the op has a better idea of the result type than the caller (for example, $b and $c could be floats, or integers, and the target should match, but the HL doesn't know which they are at compile time).
The HL probably doesn't know, which scalar type, but should know e.g. aggregate yes/no or which aggregate.
Another interesting question: interoperability between languages. What do you get when you add a PerlInteger and a RubyInteger? This seems like an interesting can of worms, actually - the best idea I can come up with is that a whole lot of morphing should be done at the interface ("interface" defined as "the place where the two languages meet", in this case).
Yep.
Actually we don't have a general scalar type now, because there is no "general" scalar. Each HL probably wants different behaviours in
- type stability / type promotion
- range checking / auto extending
- range of values / promotion to bigint/float
- exception handling / warning / nothing
As perl6/P6C is the major user of current classes, there are perl* types all over the place, e.g. a plain Array has a PerlUndef for non existent values.
I'm not sure, if we even can have a general scalar (or Array) base type, but when more HLs define their needs, we might find some common base, which might be enough to make a general base class.
Dave
leo