[REBOL] Re: Binding
From: brett:codeconscious at: 20-Nov-2002 23:45
Hi Robert,
> > expression: compose/deep [ rejoin [(instances-of-greeting)] ]
>
> I have question here: How does the evaluation sequence look like? Will
> compose/deep (a) evaluate instance-of-greeting and replace the parens
> with the result or (b) keep a live reference to the different greeting
> so that I even could change the value?
I think (a). In my example, instance-of-greeting when evaluated results in a
block.
> > ; But just because it looks like code doesn't mean we can't
> > ; treat it as data.
>
> ;-) That's cool and I'm not used to it...
Oh good. ;^)
> > ; Or demonstrate how the words in a function body are bound
> > ; to the function arguments.
>
> This sounds logical but it's really tricky I think. This means that
> EXPRESSION is switching clothes.
Yes the wording is not good (I should have been in bed). I think Ladislav
and Gabriele explain it better.
> I mean, if you think of the words as
> pointers to some value, in C the pointers would stay the same. No matter
> where you look at the pointes. In Rebol the pointers get new values
> depending of the context ;-) you read them out. Pretty nice, but very
> complex to understand and even more complex to keep track of.
With much respect, thinking "of the words as pointers" is your concept :^)
Thinking in this way is making things complex to understand. When thinking
this way it *seems* that pointers get new value depending on the context.
But I believe REBOL does not have or need that idea.
In C a variable brings to mind a a memory location where some bits are
stored. I think there's even an operator or function that can get the actual
memory address when given a variable. Compiled languages do that.
In REBOL a word can be used to represent variable data but I think it is
*not* helpful to imagine it as a memory location - it a symbol for something
else.
Joel published an interesting link to an article on "Leaky Abstractions".
REBOL gives a nice strong abstraction, but we should not try too hard to
drill holes in it! :^)
> > g: func [ greeting ] expression
> > g "Yo"
> >
> > ; Which is like using BIND on the expression itself - lets
> > bind it to ; the swedish context.
> >
> > new-expression: bind/copy expression in sweden 'self
> > do new-expression
>
> For GREETING it's now clear what happens. But what happens for REJOIN? I
> mean this word isn't in the swedish context. So Rebol key-words must
> somehow be marked so that BIND knowns to skip these. Is it this way?
Yes - the spelling of the words identifies them :^)
I think BIND parses the block. Each word it encouters it tries to find a
match in the supplied "known" context. If
it finds a word in the known context with the same spelling it will bind the
word it is working on to the "known" context.
Something like that :^)
When you load the script (paste it into the console) all the words start in
the global context (system/words). After the bind in the example has
finished all the GREETING words are modified [or replaced - ask Ladislav
:^) ] but REJOIN is left unchanged because it does not exist in the "known"
context.
> > ; BIND changes the context of words in a block
>
> Ok, to the context you specify through the KNOWN-WORD argument.
>
> > so does FUNC to its body block.
>
> And here, to what context are those words bound?
I think Ladislav in another post said that the context is created when the
function is evaluated.
> > CONTEXT (make object!) also changes the
> > context of ; words in a block it is given. ; In this next
> > example, treat the script block as data like we did ; before.
> >
> > currency-name: "Dollar"
> > script: [
> > euro-zone: context [
> > currency-name: "Euro"
> > print-currency: does [print currency-name]
> > ]
> > ]
> > get script/context/does/2
>
> == "Dollar" because executed in the "global" context.
>
> > ; Now see the change after the script block is evaluated.
> >
> > do script
> > get script/context/does/2
>
> Ok, and here the code is doing a name-lookup for "currency-name" and
> finds this first definitio within the "euro-zone" context.
This line:
get script/context/does/2
is not dependent on what the code is doing. So there is no name-lookup for
currency-name
.
This bit:
script/context/does/2
results in the word "currency-name" in the context symbolised by euro-zone.
The GET then gets the value of this currency-name-in-the-euro-zone word.
In my mind, the currency-name-in-the-euro-zone word *is a different word
instance* to
the currency-name-in-the-global-context word. But that is just my mind :^)
> Thanks a lot for all these very helpful examples. Robert
You are very welcome.
Brett.