Dan Sugalski wrote:
> 
> I've talked about this before and generally I've assumed that people
> know what I'm talking about, but that's not true anymore, so an
> explanation of this is in order.
> 
> "Active Data" is data that takes some active role in its
> use--reading, writing, modifying, deleting, or using in some activity.
> 
> As a point of reference, data in the C sense, ints, floats, pointers,
> and so forth, are passive. It doesn't matter what's in them, your
> program has complete control and it doesn't matter what data is in
> those variables, things always behave the same. What's nice here is
> that the compiler can predict, soley from the code, what will happen
> when an operation occurs. It may lose track of the referents to data
> (if, for example, a pointer escapes the code visible to the compiler)
> but everything's nicely static, and the only thing actually *doing*
> anything is the code.
> 
> Active data is data that in some way affects program behavior
> independent (or semi-independent) of the code being executed.
> 
> The common case, one most folks are familiar with (if they're
> familiar with this stuff at all) is operator overloading. Addition
> may not really be addition, if one or the other of the data in the
> operation overloads the addition operator. (Whether both sides, or
> just the left, is checked, and whether the types of both sides
> matters depends on the language) The compiler can't necessarily tell
> whether addition is really addition any more--it might really be
> subtraction, or multiplication, or some bizarre way to encrypt the
> contents of your hard drive.

Be a bit verbose in saying why this is so.  Something like:

The compiler can always tell that "+" between variables known to be
numeric types will always be addition; further, it can always tell that
"+" on variables known to be objects with an overloaded "+" will always
be a subroutine call.  What it *can't* always tell, is whether "+"
between two variables whose types it doesn't know will be addition or a
subroutine call.

A language like C++ never has to deal with the uncertainty of the latter
situation, since it always knows the types of the variables.

In a language like perl5, the types of the variables aren't ever known,
so it generally can't *know* whether "+" will be addition or an
overloaded operator.  (In few cases where it *can* know that it's
numeric addition, then it can usually constant fold.  After constant
folding, we're left back in the ambigous case).

> In some languages the compiler can at least make some predictions of
> what operations will do, but we're not really interested in those
> languages.

Why not?  You mean we won't be implementing them?

> Or, rather, it doesn't matter if we are or not, since
> perl, python, and ruby are all untyped so there's not much to be
> done, and full type inferencing's a halting-problem sort of thing.
> (Though a useful subset of many programs can be analyzed enough to do
> some optimization)

If it's a halting-problem sort of thing, then how does smalltalk work?

> Perl, at least, and because of it Parrot, goes one step further. Not
> only are operations overloaded, but assignment is overloaded.

In C++, overloading "=" overloads assignment.

In perl, overloading "=" doesn't overload assignment (it's still just a
pointer copy).  Instead, it overloads how perl reacts to doing an
overloaded mutating operation (+=, -=, *=, /=, .=, etc.) on an object
whose refcount is > 1.  (Obviously, that refcount only *got* to a number
> 1 due to an assignment.  But it's the later overloaded operation, not the assignment 
> itself, which triggers the subroutine which we passed to 'use overload "=" => ..."). 
>  The overloaded "=" is used to make a clone of the original object, and that clone 
> is put into the variable... thus, your += (or whatever) changes the clone, not any 
> of the other variables which formerly shared that pointer with it.

I suspect that in perl6, overloading "=" will overload assignment.

> If you're coming from a pure OO sort of language where assignment is
> just the association of a name and pointer to an object, this may
> seem kind of strange, but it is really useful.
> 
> The canonical example is associating a hash with a database.

*Blink*.  Now we're switching discussion from overloading to tieing.

Or were we really talking about tieing, and I was confused and thinking
of overloading?

> Reading or writing from the hash does a lookup in the backing database
> and reads or writes from it. A handy thing, with the variable getting in
> the way of reads or writes to itself. However, you can do this with
> plain scalar variables.
> 
> For example, if you had code:
> 
>     int Foo;
>     Dog Bar = new();
>     Foo = Bar;
> 
> you wouldn't want there to be a Dog in Foo--you've declared it an
> integer, so it can only hold an integer. The assignment can't do a
> plain pointer copy the way it would in the case where both sides can
> hold objects.

Indeed ... the compiler needs to detect that a conversion is necessary.

Fortunatly, since we've told the compiler the types of the variables, it
can do that.

> As an alternate example, try this:
> 
>      TempMeter kitchentemp = new('kitchenroom');
>      TempMeter bedroomtemp = new('bedroom');
>      bedroomtemp = kitchentemp;
> 
> Where in this case kitchentemp *is* an object, but one of type
> TempMeter, and bound to an object that represents the temperature in
> your kitchen, while bedroomtemp is a TempMeter object that represents
> the temperature in your bedroom. (Code I'd not recommend using in CGI
> programs....) The assignment does *not* bind the bedroomtemp name to
> the object for the kitchen temp, rather it sets the bedroom
> temperature to be the same as that in the kitchen. Even being an
> object, the object's methods still intercept read and write requests
> and instead of assignment being rebinding, it's instead a get or set
> call on the object.

Again, we've told the compiler the types, so it can do that.

> The part that affects us is that we can't tell at compiletime whether
> assignment is rebinding or is a get/set, because we could have code
> like:
> 
>      kitchentemp = new('kitchenroom');
>      bedroomtemp = new('bedroom');
>      bedroomtemp = kitchentemp;
>
> which is typeless,

Actually, we *could* try to infer the types of the variables, based on
our knowledge of the types of the values assigned to them.  I'll ignore
that,
and pretend that we don't know the return type of new() at compile time.

>and yet should still respect the fact that the
> objects bound to the name intercept assignment (basically overloading
> it) rather than having the compiler or runtime doing the rebinding
> for you.
>
> Since, of course, we're dealing with basically typeless languages we
> have to do all the checking at runtime (lucky us) which is why the
> PMCs have generic get and set methods so they can decide whether
> we're doing rebinding or something more funky. (Whether this affects
> languages where = is an explicit binding rather than assignment is up
> in the air, but neither python nor ruby is truly that way, though
> they're close. But we can fake it so that things do what they ought
> when they ought)

I forget, should "bedroomtemp = kitchentemp" be using set_pmc, or clone?

-- 
$a=24;split//,240513;s/\B/ => /for@@=qw(ac ab bc ba cb ca
);{push(@b,$a),($a-=6)^=1 for 2..$a/6x--$|;print "[EMAIL PROTECTED]
]\n";((6<=($a-=6))?$a+=$_[$a%6]-$a%6:($a=pop @b))&&redo;}

Reply via email to