Mailing List Archive: 49091 messages
  • Home
  • Script library
  • AltME Archive
  • Mailing list
  • Articles Index
  • Site search
 

Scope? Any advice would be appreciated.

 [1/19] from: rebol::mascari::org at: 27-Jan-2001 23:22


I stumbled across something tonight that appears to me to be a rather another nasty paradigm shift that I have to make (or perhaps its a bug). I have reduced the problem and wrote this function to illustrate it (I named it lcDoesnt because it doesn'd do what I expect): lcDoesnt: func [ /local b ] [ b: [ 0 0 0 ] print "The following line should ALWAYS be: 0 0 0 " print b b/3: b/3 + 1 print "The follwing line should ALWAYS be: 0 0 1 " print b print "......................." ] My expectations are the following: (1) the local variable "b" will be explicity set to [ 0 0 0 ] (2) the third element of "b" will be incremented by one, thus resulting in [ 0 0 1 ] (3) because "b" is declared local, it should not be accessable outside of the function (4) "b" will be destroyed when the function exits This pattern should repeat indefinitely as "b" is being explicity set within the function. However, this is *not* the case. Only item #3 holds. The problem is that "b" is somehow static, and so static, that even when the function explicitly *assigns* its value, that the explicit assignment is ignored in subsequent calls to the function (but not the first). Here is the output from my Rebol/View console (as you can see, the third element is being incremented, and is acting like a counter). Also note that "b" is indeed not accessable to the global area as it should be, but it must still exist somewhere else.
>> lcdoesnt
The following line should ALWAYS be: 0 0 0 0 0 0 The follwing line should ALWAYS be: 0 0 1 0 0 1 .......................
>> lcdoesnt
The following line should ALWAYS be: 0 0 0 0 0 1 The follwing line should ALWAYS be: 0 0 1 0 0 2 .......................
>> b
** Script Error: b has no value. ** Where: b
>>
Any advice would be appreciated. Thanks, Victor Mascari

 [2/19] from: petr:krenzelok:trz:cz at: 28-Jan-2001 5:53


----- Original Message ----- From: <[rebol--mascari--org]> To: <[rebol-list--rebol--com]> Sent: Sunday, January 28, 2001 5:22 AM Subject: [REBOL] Scope? Any advice would be appreciated.
> I stumbled across something tonight that appears to me to be a rather > another nasty paradigm shift that I have to make (or perhaps its a bug).
<<quoted lines omitted: 11>>
> ] > My expectations are the following:
Hi :-) I am not sure I am the one to answer context specific issues, but will try to :-)
> (1) the local variable "b" will be explicity set to [ 0 0 0 ]
right
> (2) the third element of "b" will be incremented by one, thus resulting
in
> [ 0 0 1 ]
right
> (3) because "b" is declared local, it should not be accessable outside of > the function
right
> (4) "b" will be destroyed when the function exits
not sure, the concet is called indefinite extent? Maybe it doesn't seem logical to you, but once you defined function, it is still alive (defined) and so reference to your block 'b exists ... The easiest solution is to use b: copy [0 0 0] as a declaration and Rebol will give you fresh copy of data you need, not those already referenced by local word 'b, which lives inside the context of the function ...
> This pattern should repeat indefinitely as "b" is being explicity set > within the function. However, this is *not* the case. Only item #3
holds.
> The problem is that "b" is somehow static, and so static, that even when > the function explicitly *assigns* its value, that the explicit assignment > is ignored in subsequent calls to the function (but not the first).
I don't think 'b is static - it should be really local to your function....
> Here is the output from my Rebol/View console (as you can see, the third > element is being incremented, and is acting like a counter). Also note
<<quoted lines omitted: 16>>
> ** Where: b > >>
And the result matches exactly to what I said above .... Hope-that-helps Cheers, -pekr-

 [3/19] from: al:bri:xtra at: 28-Jan-2001 23:17


Victor Mascari wrote:
> lcDoesnt: func [ /local b ] > [
<<quoted lines omitted: 6>>
> print "......................." > ]
It's normal behaviour. You'll need to read either "Rebol: The Official Guide", "Rebol for Dummies" or the Core manual book or PDF. They explain your "problem" in better detail. Basically the block assigned to the local word 'b in the function assigned to the word 'lcDoesnt "hangs around". It's called "indefinite extent", IIRC. It's like allocating an array to a pointer in C or Pascal. Andrew Martin ICQ: 26227169 http://members.nbci.com/AndrewMartin/

 [4/19] from: g:santilli:tiscalinet:it at: 28-Jan-2001 11:32


Hello [rebol--mascari--org]! On 28-Gen-01, you wrote: r> I stumbled across something tonight that appears to me to be a r> rather another nasty paradigm shift that I have to make (or r> perhaps its a bug). You will be enlightened if you look at the source of your function.
>> source lcdoesnt
lcdoesnt: func [/local b][ b: [0 0 0] print "The following line should ALWAYS be: 0 0 0 " print b b/3: b/3 + 1 print "The follwing line should ALWAYS be: 0 0 1 " print b print "......................." ]
>> lcdoesnt
The following line should ALWAYS be: 0 0 0 0 0 0 The follwing line should ALWAYS be: 0 0 1 0 0 1 .......................
>> source lcdoesnt
lcdoesnt: func [/local b][ b: [0 0 1] print "The following line should ALWAYS be: 0 0 0 " print b b/3: b/3 + 1 print "The follwing line should ALWAYS be: 0 0 1 " print b print "......................." ] All this is because you are still thinking in terms of variables, but REBOL does not have variables. REBOL has values only, and your 'b is a value of type WORD!. Words are able to refer to ONE other value (that is said to be its meaning). (Blocks are able to refer to MANY other values.) In the code above, you are changing the meaning of 'b, not 'b itself; 'b is "local" (actually, the association between 'b and its meaning is "local"), but the value it refers to is that very block above, not something that gets created and destroyed for every function call. To create a fresh block for each call, use: b: copy [0 0 0] or: b: make block! [0 0 0] Regards, Gabriele. -- Gabriele Santilli <[giesse--writeme--com]> - Amigan - REBOL programmer Amiga Group Italia sez. L'Aquila -- http://www.amyresource.it/AGI/

 [5/19] from: lmecir:mbox:vol:cz at: 28-Jan-2001 15:55


Hi Victor, I will try to explain the difference between the way Rebol works and you expect it to
> lcDoesnt: func [ /local b ] > [
<<quoted lines omitted: 8>>
> My expectations are the following: > (1) the local variable "b" will be explicity set to [ 0 0 0 ]
Rebol: the local variable B will be set to the second value of the LCDOESNT's body
> (2) the third element of "b" will be incremented by one, thus resulting
in
> [ 0 0 1 ]
Rebol: the third element of B will be incremented by one.
> (3) because "b" is declared local, it should not be accessable outside of > the function
Rebol: the value is accessible as the second value of the LCDOESNT's body
> (4) "b" will be destroyed when the function exits
Rebol: no destruction Rebgards Ladislav

 [6/19] from: rebol:mascari at: 28-Jan-2001 10:47


Thanks to all that replied! Everything somewhat makes sense. Everything is just an "object" that maintains itself once declared. And code appears to be self-modifying. Ok. However, I have a follow-up question. The following routine *does* work: lcWorks: func [ /local b ] [ b: 0 print "The following line s/b 0" print b b: b + 1 print "The follwing line s/b 1" print b ] It doesn't need to use "copy" to make it work. I guess this issue just boils down to assignment techniques. Why do I have to use different assignment techniques? That is, in the above example, a straightforward assignment of 0 to b works as one would expect. However, the same concept applied to a block, b: [ 0 0 0 ] as in the earlier example, does not work. Instead I have to make a copy of [ 0 0 0 ] - b: copy [ 0 0 0 ]. I am not clear as to why I would need to make a copy - why wouldn't the b: [ 0 0 0 ] just blow away the current contents, even if the function and its properties are maintained between calls? Similarly, in one of the previous answers from Gabriele, he showed what appears to me to be behavior of self modifying code. However, I still don't understand why using "copy" forces the code to update, whereas the normal assignment operator does not. Lastly, since the code appears to be self-modifying, and behavior of assignments change depdending upon whether it is the first call or a subsequent one, I am curious as to what advantages this has vs the confusion that it will cause people coming from other programming environments. Thanks again, Victor Mascari

 [7/19] from: g:santilli:tiscalinet:it at: 28-Jan-2001 20:48


Hello [rebol--mascari--org]! On 28-Gen-01, you wrote: r> Everything somewhat makes sense. Everything is just an r> "object" that maintains itself once declared. And code appears r> to be self-modifying. Ok. Yes, because code is nothing more than data. r> However, I have a follow-up question. The following routine r> *does* work: [...] I was expecting that question. :-) This is a matter of immutable vs mutable values. You cannot change an INTEGER! value in REBOL (in your function you are using the ADD native to create a *new* integer value), but you can change the elements of a BLOCK! value (you don't create a new BLOCK! value, you just change one of its elements). r> works as one would expect. However, the same concept applied r> to a block, b: [ 0 0 0 ] as in the earlier example, does not r> work. Instead I have to make a copy of [ 0 0 0 ] - b: copy [ 0 r> 0 0 ]. You need to create a new fresh block each time only if you really need it (that is, if you're going to change it). Doing this automatically for each block wouldn't be a good idea, because most of the time blocks are not changed (think about code blocks). r> I am not clear as to why I would need to make a copy - why r> wouldn't the b: [ 0 0 0 ] just blow away the current contents, The matter is not the assignments itself, but is what you are assigning. As you see, you changed that very block in the function, so the second call looks like: b: [0 0 1] and not: b: [0 0 0] r> Gabriele, he showed what appears to me to be behavior of self r> modifying code. However, I still don't understand why using r> "copy" forces the code to update, whereas the normal r> assignment operator does not. Because then 'b will refer to a copy of that block in the code, NOT that very block in the code. If you change the copy, the original remains the same. r> Lastly, since the code appears to be self-modifying, and r> behavior of assignments change depdending upon whether it is r> the first call or a subsequent one, I am curious as to what r> advantages this has vs the confusion that it will cause people r> coming from other programming environments. It's a bit confusing in the beginning, but you'll find it obvious and natural when you'll have some more experience with REBOL. To be better, you have to be different. :-) Regards, Gabriele. -- Gabriele Santilli <[giesse--writeme--com]> - Amigan - REBOL programmer Amiga Group Italia sez. L'Aquila -- http://www.amyresource.it/AGI/

 [8/19] from: lmecir:mbox:vol:cz at: 28-Jan-2001 21:07


Hi Victor,
> Thanks to all that replied! > Everything somewhat makes sense. Everything is just an "object" that
<<quoted lines omitted: 12>>
> It doesn't need to use "copy" to make it work. I guess this issue just > boils down to assignment techniques.
This issue doesn't have anything in common with the "assignment techniques".
> Why do I have to use different assignment techniques? That is, in the > above example, a straightforward assignment of 0 to b works as one would > expect.
The difference lies in the fact, that the expression b: b + 1 doesn't change the second value of the LCWORK function's body. In a different wording: the second value of the LCWORK's body remains unchanged, because it is Immutable. For more info on Immutable vs. Mutable see e.g. http://www.sweb.cz/LMecir/evaluation.html
> However, the same concept applied to a block, b: [ 0 0 0 ] as in > the earlier example, does not work. Instead I have to make a copy of [ 0
0
> 0 ] - b: copy [ 0 0 0 ]. > > I am not clear as to why I would need to make a copy - why wouldn't the b: > [ 0 0 0 ] just blow away the current contents, even if the function and
its
> properties are maintained between calls?
It would, but the problem lies in the fact, that the code looks different when modified. If you make a copy, any subsequent change will modify only a copy of the second value contained in the function body.
> Similarly, in one of the previous > answers from Gabriele, he showed what appears to me to be behavior of self > modifying code. However, I still don't understand why using "copy" forces > the code to update, whereas the normal assignment operator does not. >
As you might have seen above, quite the opposite is true. If you don't make a copy, a modification "updates" your code. If you make a copy, no modification of the original occurs.
> Lastly, since the code appears to be self-modifying, and behavior of > assignments change depdending upon whether it is the first call or a
<<quoted lines omitted: 7>>
> [rebol-request--rebol--com] with "unsubscribe" in the > subject, without the quotes.
HTH Ladislav

 [9/19] from: dvydra2:y:ahoo at: 28-Jan-2001 20:24


Gabriele, Is this a simple optimization issue or is there a deeper logic for this "strange" behaviour?

 [10/19] from: rebol:techscribe at: 28-Jan-2001 22:41


Hi David, The body of a function is a block and behaves like a block. What strikes you as an unusual behavior is part of REBOL's consistency. REBOL is different from other programming languages in that it applies a relatively small set of rules consistently across most of its types (including functions). Just as you expect any block (even one that is embedded in an outer block) to preserve its values, so too does REBOL preserve the values of a block that is embedded in a block even though the host block, besides being a block, also happens to be the body of a function. Given the block b that contains a single element, a block that in turn contains three integers, all of which are 0
>> b: [ [0 0 0] ]
I can access the internal block using the path notation with the index 1:
>> b/1
== [0 0 0] Now let me change the first 0 in the inner block to a 3
>> change b/1 3
== [0 0] The block b now contains a block that contains the three integers 3, 0, and 0
>> b/1
== [3 0 0] Now for a simple function whose body contains a block that contains three 0s
>> f: does [ [0 0 0] ]
I can access the body block of the function using the second function:
>> second :f
== [[0 0 0]] I can assign the word c as a reference to the body block:
>> c: second :f
The wird c is now a reference to a block (namely the body block of the function) like b is a reference to a block
>> c
== [[0 0 0]]
>> b
== [[3 0 0]] I can now change the first value of c's embedded block:
>> change c/1 3
== [0 0] Now c/1 looks like b/1:
>> c/1
== [3 0 0]
>> b/1
== [3 0 0] Indeed the are equal:
>> b/1 = c/1
== true Let me add a set-word! called block: to both blocks:
>> insert b [block:]
== [[3 0 0 ]] and let's do the same to c
>> insert c [block:]
== [[3 0 0]] What does b contain?
>> b
== [block: [3 0 0]] What does c contain?
>> c
== [block: [3 0 0]] If we try to get the value associated with block we get an error message in both cases, because the blocks haven't been evaluated yet, and therefore the set-words have not been associated with anything:
>> get b/1
** Script Error: block has no value. ** Where: get b/1
>> get c/1
** Script Error: block has no value. ** Where: get c/1 Now let's evaluate the function, which means that the block is reduced:
>> f
== [3 0 0 ] Now we can get the value of the set-word! block: in c (recall that c is simply a word associated with f's body block):
>> get c/1
== [3 0 0] Now block: is associated with the block [0 0 0] in the function f. Let's first get rid of this association, and then we'll look at b:
>> unset 'block
How about b? Since b's block is not associated with a function, we cannot evaluate this non-existent function. We can, however, reduce the block programmtically (reducing a block means evaluating its elements):
>> reduce b
== [[3 0 0]] The reduction has caused the set-word block! to be associated with the block [3 0 0] in the block b:
>> get b/1
== [3 0 0] Finally, we can express evaluation of a function without arguments, refinements, and locals as a block reduction: eval-function: func [body [block!] [ reduce body ] Let's first unset block:
>> unset 'block
If some f is a "does" function (i.e. without arguments, refinements, or locals), then evaluating the function is the equivalent of passing the function's body to our eval-function:
>> f: does [ block: [0 0 0] ] >> first second :f
== block:
>> get first second :f
** Script Error: block has no value. ** Where: get first second :f
>> fbody: second :f >> eval-function fbody
== [[0 0 0]]
>> get fbody/1
== [0 0 0]
>> first second :f
== block:
>> get first second :f
== [0 0 0] Hope this makes it more digestable. Elan David Vydra wrote:

 [11/19] from: lmecir:mbox:vol:cz at: 29-Jan-2001 21:05


Hi David,
> Is this a simple optimization issue or is there a > deeper logic for this "strange" behaviour?
Yes, if you would like to have even the "natural" behaviour, you would have to use a different datatype, namely an immutable-block datatype, which might complicate the datatype system and therefore even Rebol a bit. Another point of view may be, that the benefits of such a change can be greater than the complications caused by the datatype addition.

 [12/19] from: dvydra2:ya:hoo at: 29-Jan-2001 13:29


Thanks to Laidslav and Elan for your answers. Personally I can get used to the current implementation of block assignment in functions. However, I am a bit concerned about the wider acceptance of REBOL in the corporate community, after all that's probably where RT's payroll will come from :) I have always been interested in using higher-level languages to be productive. My career has progressed from dBase->Clarion->Gupta SqlWindows->Forte --->Java and Rebol. All of the above, except Java have a small market share these days. I just hope Rebol will stay around long enough for ME to get tired of it -- and that may be a long time :) Regards, David --- Ladislav Mecir <[lmecir--mbox--vol--cz]> wrote:

 [13/19] from: dvydra2:yaho:o at: 30-Jan-2001 18:15


Elan, Thanks for your reply. A few clarifications are in order: --- Elan <[rebol--techscribe--com]> wrote:
> A few comments: > 1. SQlWindows is not a programming language. It is a
<<quoted lines omitted: 8>>
> kicking last time I > checked ;-).
You are probably confusing SqlWindows with SqlBase. SqlWindows (now Centura developer) uses a language called SAL which is quite OO, even supports multiple inheritance.
> True, dBase includes its own programming language, > as does Clarion (so
<<quoted lines omitted: 10>>
> competition (of course, after all Oracle is also SQL > based).
actually Clarion bought TopSpeed which had cross-compilers for Pascal and some other language, I cant recall. It was something like MS .NET. I wrote systems in Clarion that had nothing to do with a DBMS.
> As for Forte, I'm not quite sure which Forte you are > referring to. I am
<<quoted lines omitted: 3>>
> mean something > else?
sorry I meant Forte 4GL www.forte.com, my once employer, now owned by Sun. I guess they liked the name adn
> 2. As for the specific REBOL feature we were > investigating: statically
<<quoted lines omitted: 26>>
> for quite a few > years, REBOL is quite safe.
actually C++ had a poor reputation in many IT shops that tried to build a system with it without having proper "geeks" on staff.
> I don't think that REBOL is weird, and I doubt that > the weirdness of a > language is a guarantee for its success. But Tcl, > Perl, and Visual Basic > still seem to be doing quite well ...
its all in the marketing, right? :) anyway, I really like REBOL. We started using it instead of JavaCC to write a domain-language to XML compiler. So far, it works well. david ===== please reply to: [david--vydra--net]

 [14/19] from: rebol:techscribe at: 30-Jan-2001 21:32


Hi David, I was talking about versions of the software that came out in the mid or late eighties. At the time the packages you mentioned were competing on the DBMS market. I think this would also be true for 4GL languages, even if they were not marketed as a companion product to a proprietary DBMS technology. Their fate is determined by the dynamics of the DBMS market. If a DBMS company eventually takes over a significant market share (Oracle), then it sets standards not only with respect to the DBMS itself, but also with respect to accompanying products. I believe that, in contrast, REBOL is competing on what has been traditionally the scripting or programming languages market. Here the dynamics may be a little different. A DBMS oriented product (also 4GL) will attempt to improve something with respect to existing DBMS technologies. A programming or scripting language, on the other hand, may include support for DBMSs to extend the sphere of influence of programmers who use this language. These two distinct developments may occassionally overlap, where a DBMS oriented shop will invest in a scripting language because it feels that the language improves their abilities to solve problems that are specific to their DBMS market, for instance, but that does not mean that the fate of the language is has now beomce dependent on the dynamics of the DBMS market, as a 4GL would be. Hope this clears it up, Elan

 [15/19] from: chaz:innocent at: 30-Jan-2001 22:31


Late and way off the tangent, here I am! At 11:22 PM 1/27/01 -0500, you wrote:
>I stumbled across something tonight that appears to me to be a rather >another nasty paradigm shift that I have to make (or perhaps its a bug).
<<quoted lines omitted: 12>>
>My expectations are the following: >(1) the local variable "b" will be explicity set to [ 0 0 0 ]
I would expect the local variable "b" to be set to a location in memory. You've initialized the contents of that location with 0 0 0
>(2) the third element of "b" will be incremented by one, thus resulting in >[ 0 0 1 ]
I would expect the same.
>(3) because "b" is declared local, it should not be accessable outside of >the function
It's not local scope, it's a local context, but it won't be visible in the global context, no.
>(4) "b" will be destroyed when the function exits
I don't expect that, because the current state of the block that is giving value to lcDoesnt is stored in system/words. b will be "destroyed" when the set-word lcDoesnt: is placed before a different word or a different block lcDoesnt: "b is gone"
>This pattern should repeat indefinitely as "b" is being explicity set >within the function. However, this is *not* the case. Only item #3 holds. >The problem is that "b" is somehow static, and so static, that even when >the function explicitly *assigns* its value, that the explicit assignment >is ignored in subsequent calls to the function (but not the first).
The set-word lcDoesnt takes the value of the function block it is adjacent to. The function block has been modified, so lcDoesnt acts accordingly. Source lcDoesnt shows the modifications of the block.
>> lcDoesnt: func [ /local b ][
[ b: [ 0 0 0 ] [ print "The following line should ALWAYS be: 0 0 0 " [ print b [ [ b/3: b/3 + 1 [ [ print "The follwing line should ALWAYS be: 0 0 1 " [ print b [ print "......................." [ ]
>> lcDoesnt
The following line should ALWAYS be: 0 0 0 0 0 0 The follwing line should ALWAYS be: 0 0 1 0 0 1 .......................
>> source lcDoesnt
lcDoesnt: func [/local b][ b: [0 0 1] print "The following line should ALWAYS be: 0 0 0 " print b b/3: b/3 + 1 print "The follwing line should ALWAYS be: 0 0 1 " print b print "......................." ]
>> lcDoesnt
The following line should ALWAYS be: 0 0 0 0 0 1 The follwing line should ALWAYS be: 0 0 1 0 0 2 .......................
>> source lcDoesnt
lcDoesnt: func [/local b][ b: [0 0 2] print "The following line should ALWAYS be: 0 0 0 " print b b/3: b/3 + 1 print "The follwing line should ALWAYS be: 0 0 1 " print b print "......................." ]
>Any advice would be appreciated. >
In my computer, there isn't "Code RAM" and "Data RAM", it's just all RAM, and all of it is there for me to modify at my will.

 [16/19] from: rebol:techscribe at: 29-Jan-2001 22:06


Hi David,
> I have always been interested in using higher-level > languages to be productive. My career has progressed
<<quoted lines omitted: 3>>
> around long enough for ME to get tired of it -- and > that may be a long time :)
A few comments: 1. SQlWindows is not a programming language. It is a product - a database management system - that happens to use SQL. The DBMS product may not have a major market share, but REBOL is not a dbms product, it's a programming language. So we should be comparing it to SqlWindow's programming language. And SQL is quite alive and kicking last time I checked ;-). True, dBase includes its own programming language, as does Clarion (so you never programmed in Paradox, huh?). But in both cases we are again talking about programming languages that are specific to a DBMS product. So the competition here is about DBMS products, not about programming languages. In other words dBase and Clarion (and SqlWindows) lost the database management system competition, not the programming language competition (of course, after all Oracle is also SQL based). As for Forte, I'm not quite sure which Forte you are referring to. I am aware of a Forte Newsgroup reader, and there's a Fort Java IDE. Right, there's also a theorem prover called Forte. You must mean something else? 2. As for the specific REBOL feature we were investigating: statically scoped local variables have been part of C for roughly thirty years and have happily made it into ANSI C++. That's pretty mainstream. The only thing that a C/C++ programmer has to realize is that a (REBOL) word that references a literal block (under all circumstances) acts similar to a (C) local variable that is a pointer (word) referencing a locally declared static buffer (or a globally declared buffer) (== REBOL literal block). Even though you may reassign the pointer to the buffer each time you enter the function, if that buffer was declared static (or the buffer is global), then the buffer will contain whatever was previously put into it during the previous evaluation of the C function. There's really nothing to it. My argument then is that if REBOL's success depends on the acceptance of REBOL's literal block behavior, then, given that mainstream languages C and C++ have been supporting an equivalent feature for quite a few years, REBOL is quite safe. I don't think that REBOL is weird, and I doubt that the weirdness of a language is a guarantee for its success. But Tcl, Perl, and Visual Basic still seem to be doing quite well ... Take Care, Elan

 [17/19] from: lmecir:mbox:vol:cz at: 30-Jan-2001 8:48


Hi Victor, I would like to answer your questions.
> Although I can "see" that the datatype determines the functionality of the > assignment operator,
The above is incorrect. Compare the samples: s1: function [] [x] [ x: 1 print either x = 1 ["Expected!"] ["Unexpected!"] x: 2 ] s1 ; Expected! ; == 2 s2: function [] [x] [ x: [1] print either x = [1] ["Expected!"] ["Unexpected!"] x: [2] ] s1 ; Expected! ; == [2]
> its not documented in the Rebol guide under "Setting > Words" and the behavior is not consistent with immutables. >
The assignment operator behaviour is consistent with immutables/immutables (see above). The only thing, that is inconsistent with mutables as opposed to immutables is the fact, that if you change the mutables contained in your code, you are causing the code to become self modifying, which is surely a dangerous practice, especially if you don't know what you are doing.
> On the surface, the first pass through the routine, b: [ 0 0 0 ] does the > same thing as b: 0. But on subsequent runs the behaviors part paths and > cause confusion and unexpected behavior for those of us who do not > understand the underlying logic of Rebol. But, then again, why should I > need to understand the underlying logic of Rebol? If the basic
instruction
> manual doesn't explain this, then how is anyone to know it? How many
other
> undocumented design decisions are there that impact basic operational > usage? > > Also, I still don't see the value here - what benefit is secured by making > these two different? Why do I have to use "copy" to accomplish with > mutables the same thing that is accomplished without "copy" for
immutables? Even with copy you still cannot accomplish exactly the same with mutables as with immutables. Immutables are really protected against change (no way to change them at all, which protects a programmer against a lot of errors). To have a better symmetry, the introduction of immutable blocks as a new dataty pe might help (especially the beginners may be less confused)?

 [18/19] from: g:santilli:tiscalinet:it at: 30-Jan-2001 12:05


David Vydra wrote:
> Is this a simple optimization issue or is there a > deeper logic for this "strange" behaviour?
Mora than "optimization", it's for simplification. The interpreter is very simple this way, yet very powerful (more than most languages). Regards, Gabriele. -- Gabriele Santilli <[giesse--writeme--com]> - Amigan - REBOL programmer Amiga Group Italia sez. L'Aquila -- http://www.amyresource.it/AGI/

 [19/19] from: rebol:mascari at: 29-Jan-2001 19:17


Thank-you all for the clarification of immutable and mutable. This fixes my problem, but just as David mentioned in a previous post, the lack of consistency in operations can confuse people unless they are intimate with the logical decisions that govern Rebol's design. Although I can "see" that the datatype determines the functionality of the assignment operator, its not documented in the Rebol guide under "Setting Words" and the behavior is not consistent with immutables. On the surface, the first pass through the routine, b: [ 0 0 0 ] does the same thing as b: 0. But on subsequent runs the behaviors part paths and cause confusion and unexpected behavior for those of us who do not understand the underlying logic of Rebol. But, then again, why should I need to understand the underlying logic of Rebol? If the basic instruction manual doesn't explain this, then how is anyone to know it? How many other undocumented design decisions are there that impact basic operational usage? Also, I still don't see the value here - what benefit is secured by making these two different? Why do I have to use "copy" to accomplish with mutables the same thing that is accomplished without "copy" for immutables? Shouldn't a single operator implement a single concept? I know there are a lot of questions above, but in order for me to understand the goals of the Rebol product, I need to ask them. I still don't see the big picture. Again, thanks to all, Victor Mascari

Notes
  • Quoted lines have been omitted from some messages.
    View the message alone to see the lines that have been omitted