local variable confusion 
Author Message
 local variable confusion

You are right! I didn't expect that at all, i.e. I've gotten a
redefinition error on other things in C++ that are in the same scope, so
I
would have never thought enclosing a redefinition in a while statement
(or
another similar one) would have made any difference.

Thanks for your help ...

Brandon

Quote:

> On Fri, Mar 19, 1999 16:10 Uhr, Brandon Corfman


Quote:

> >I understand that you can't assign a new value to an existing
binding.
> That makes
> >sense to me. But why does Dylan let the code go through? In C++, I
would
> get a
> >compiler error.

> >Brandon

> You wont get a compile error in C++ either! This is because in each
new
> scope you can define any number of new variables as long they have
mutually
> different names. If one name happens to be the same as a name from an
> enclosing scope, then the outer name will be hidden.

>         Gabor

[ Attached Message ]

From:
To:
Date: Fri, 19 Mar 1999 10:48:45 -0500
Local: Fri, Mar 19 1999 10:48 am
Subject: Re: Local variable confusion
Wow, you are right! I didn't expect that at all, i.e. I've gotten a
redefinition error on other things in C++ that are in the same scope, so I
would have never thought enclosing a redefinition in a while statement (or
another similar one) would have made any difference.

Thanks for your help..

Brandon

- Show quoted text -

Quote:



> >I understand that you can't assign a new value to an existing binding.
> That makes
> >sense to me. But why does Dylan let the code go through? In C++, I would
> get a
> >compiler error.

> >Brandon

> You wont get a compile error in C++ either! This is because in each new
> scope you can define any number of new variables as long they have mutually
> different names. If one name happens to be the same as a name from an
> enclosing scope, then the outer name will be hidden.

>         Gabor



Tue, 04 Sep 2001 03:00:00 GMT  
 local variable confusion

Although I've gotten a few comments from people pointing out that you
won't get a compiler error in C++ from the following:

void main()
{
    // OK, this a really silly example ...
    // but it illustrates my point ...
    char stuff[] = "Brandon";
    while (1)
    {
        char stuff[] = "Corfman";
    }

Quote:
}

You will get an error from this:
void main()
{
    char stuff[] = "Brandon";
    char stuff[] = "Corfman";

Quote:
}

at least I do under VC++.

But I won't get a compiler error with Dylan if I do this, but I think it
would be certainly nice if I did:

define method main () => ()
  let answer :: <string> = "Brandon";
  let answer :: <string> = "Corfman";

end method main;

So I think my point is still valid.

Brandon



Tue, 04 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:

> Although I've gotten a few comments from people pointing out that you
> won't get a compiler error in C++ from the following:

> void main()
> {
>     // OK, this a really silly example ...
>     // but it illustrates my point ...
>     char stuff[] = "Brandon";
>     while (1)
>     {
>         char stuff[] = "Corfman";
>     }
> }

> You will get an error from this:
> void main()
> {
>     char stuff[] = "Brandon";
>     char stuff[] = "Corfman";
> }

> at least I do under VC++.

> But I won't get a compiler error with Dylan if I do this, but I think it
> would be certainly nice if I did:

> define method main () => ()
>   let answer :: <string> = "Brandon";
>   let answer :: <string> = "Corfman";

> end method main;

> So I think my point is still valid.

Hi Brandon,

I think a Dylan implementation is free to warn you about the circumstance you
describe, its just the current implementations don't. ie you keep saying
"Dylan" which means the language, whereas you probably mean "Harlequin Dylan"
or whatever.

__Jason



Tue, 04 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:

> > You will get an error from this:
> > void main()
> > {
> >     char stuff[] = "Brandon";
> >     char stuff[] = "Corfman";
> > }

> > at least I do under VC++.

> > But I won't get a compiler error with Dylan if I do this, but I think it
> > would be certainly nice if I did:

> > define method main () => ()
>   let answer :: <string> = "Brandon";
>   let answer :: <string> = "Corfman";

> end method main;

> > So I think my point is still valid.

 No Becauce the equivalent C++ for the above Dylan code is

    void main ()
    {    
        char  stuff[] = "Brandon";
        { char stuff[] = "Corfman";
         }
    }

  Which again will NOT issue any warning at all.

  Every time you see the word 'let' a NEW lexical context created.
  If yo do not want a new lexical context, don't use the word.
  To bind variable to a new value you can use a -setter method or
  the syntactic sugar equivalent, ':=' .
  [ Personally, I think the word "assignment" carries too much baggage
    for C/Algol folks. The expectation is the "assignment" makes a
    copy. For the most part, no "copy" is created in Dylan unless you
    explicitly ask for one. ]

  If you want to keep this straight then I'd suggest a slightly different
  coding style.

    define method main () =>  ()
    let answer :: <string> = "Brandon";
       let answer :: <string> = "Corfman";

    end method main;

   Namely, indent for each new lexical scope you create.
   [ I think some folks avoid this because they keep the "rule" straight
     in their head and want to avoid the code "drifting to the right".
     This has a negative impact on "newbies" though. ]

Quote:
>I think a Dylan implementation is free to warn you about the circumstance you
> describe, its just the current implementations don't. ie you keep saying

   There is nothing wrong.  It could be "style" warning is you had some
   Dylan style checker. ( where the style violations is either indentation
   or "reuse" depending on your preference) However, semantically if you
   would "warn" for this you should also "warn" if a function/method
   parameter is the same name as one in the outer scope.  The two have
   effectively the same signficance.  If don't want one it seem
   "hypocritical" to want the other.

   Now this would be more blanantly obvious if there were either a
requirement
   for an explicit 'end' for each 'let' or Dylan still had the prefix
   syntax.  

     let answer ....
       let answer ...
       end let
     end let

   or
     (let ...
       (let  ...
        )
     )

    However, the current system has the benefit of cutting down on the
    number of "ends" you have to insert into your code.  Very often
    you would end up with sequence of 'end's.   The current systax
    manages to "reuse" the 'end' to close multiple "enclosures". This
    "special reuse" is only "combines" 'let' with others (or itself)
    so the meaning is straightforward once you know the rule.

Lyman



Tue, 04 Sep 2001 03:00:00 GMT  
 local variable confusion
 I forgot some stuff earlier. ;-)



Quote:
> Warning in VC++

  It is a warning in C++ (or C) because the compiler may
  "throw away" or "ignore" one of those redundant declarations.  
  A compiler should "say something" whenever it tries to attempt
  to do "ignore" what was "obviously" a mistake.

  In Dylan, those declarations aren't redundant.  I'm not sure
  it is correct to expect Dylan compiler to do checks to see
  you're an "unreformed" Basic or C programmer.  At least
  without setting a "switch" on the compiler to tell it that you
  are one.  :-)

  The following should generate a error ( or at least a warning) though
  ( I haven't checked d2c or harlequin ):

let  ( answer :: <string>  , answer :: <string>  ) =  values ( "Brandon" ,
                                                               "Corfman" ) ;

  The above is the closer equivalent to the C++ example.  Clearly there
  is a "problem" as to which "answer" is visible in the implicit body
  that follows.

  In the "other language idiom"  context the following would be
  useful too.

    ....
    a  =  b ;      // Lapsing back into C for a moment.
    ....

Quote:
>   or "reuse" depending on your preference) However, semantically if you
>   would "warn" for this you should also "warn" if a function/method
>   parameter is the same name as one in the outer scope.  The two have
>   effectively the same signficance.  If don't want one it seem
>   "hypocritical" to want the other.

  The following fits into the same category.

    let  index  = 23  ;
    for ( index  from 0  to 10 )
       a[index] := index * 23;
    end for;
    // index equals ??

  After the loop, 'index' is 23. The loop's 'index' masks the "outer" let.
--

Lyman S. Taylor           "Computers are too reliable to replace

                                Commander Nathan Spring, "Starcops"



Tue, 04 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:

> > Warning in VC++

>   It is a warning in C++ (or C) because the compiler may
>   "throw away" or "ignore" one of those redundant declarations.
>   A compiler should "say something" whenever it tries to attempt
>   to do "ignore" what was "obviously" a mistake.

>   In Dylan, those declarations aren't redundant.  I'm not sure
>   it is correct to expect Dylan compiler to do checks to see
>   you're an "unreformed" Basic or C programmer.  At least
>   without setting a "switch" on the compiler to tell it that you
>   are one.  :-)

> >   or "reuse" depending on your preference) However, semantically if you
> >   would "warn" for this you should also "warn" if a function/method
> >   parameter is the same name as one in the outer scope.  The two have
> >   effectively the same signficance.  If don't want one it seem
> >   "hypocritical" to want the other.

Hm. Two points.

One: If you're not trying to get the "unreformed" BASIC or C programmer into the
Dylan fold, who are you trying to get? The waiting legions of Lisp programmers
out there? All the C++ coders who got recursion conversion?

Two: I could also use your writing technique to belittle a Dylan or Java
programmer for using a language that doesn't have pointers. After all, it's
"obvious" to remember how to allocate and deallocate memory, and it's certainly
"way too slow" to use garbage collection compared to cleaning up pointers
yourself. How hard is that?

The point is that even if I know how to use pointers correctly, probably 80% (my
own estimate) of the C/C++ community either forgets to clean up memory
correctly, didn't know how to use pointers in the first place, or finds it a
rather cryptic way to do things that should be fairly simple.

Now, relating this back to my original topic (allocating memory for local
variables)  this scope thing in Dylan falls into the rather cryptic category --
no matter how much you want to shout that it isn't.

Further, I can't imagine a scenario where 99% of the time my previous example
wouldn't be a mistake (more like 100%, but I'll give some slack):

define method main () =>  ()
    let answer :: <string> = "Brandon";
    let answer :: <string> = "Corfman";
end method main;

If you think it's a scenario that doesn't come up very often, remember that it's
unlikely to come up when the two lines are next to each other, but when they are
more than a page apart, it is quite easy to forget that you are reusing a
variable name. Instead of the compiler shadowing the old definition (unhelpful),
why not have it post a warning (very helpful)?

C/C++ compilers help us out by acknowledging this common mistake; why can't our
Dylan compilers?

Brandon



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:

> Further, I can't imagine a scenario where 99% of the time my previous example
> wouldn't be a mistake (more like 100%, but I'll give some slack):

> define method main () =>  ()
>     let answer :: <string> = "Brandon";
>     let answer :: <string> = "Corfman";
> end method main;

If people are reluctant to add checking for this to compilers ( and it
looks worthwhile, a warning is different from an error after all ),
howabout a Dylan-Lint program?

- Rob.

__________________________________________________________________
                           __            __    _      __        

http://www.lostwax.com/  / /__/ _ \(_-</ __/  | |/ |/ / - `/\ \ /
                        /____/\___/___/\__/   |__/|__/\_,_//_\_\



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:


> > Further, I can't imagine a scenario where 99% of the time my previous example
> > wouldn't be a mistake (more like 100%, but I'll give some slack):

> > define method main () =>  ()
> >     let answer :: <string> = "Brandon";
> >     let answer :: <string> = "Corfman";
> > end method main;

> If people are reluctant to add checking for this to compilers ( and it
> looks worthwhile, a warning is different from an error after all ),
> howabout a Dylan-Lint program?

I don't think people are reluctant to add this to compilers.

__Jason



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:
> -----Original Message-----


> Sent: Monday, March 22, 1999 5:35 AM

> Subject: Re: local variable confusion

[...]

Quote:
> define method main () =>  ()
>     let answer :: <string> = "Brandon";
>     let answer :: <string> = "Corfman";
> end method main;

> If you think it's a scenario that doesn't come up very often,
> remember that it's
> unlikely to come up when the two lines are next to each
> other, but when they are
> more than a page apart, it is quite easy to forget that you
> are reusing a
> variable name. Instead of the compiler shadowing the old
> definition (unhelpful),
> why not have it post a warning (very helpful)?

> C/C++ compilers help us out by acknowledging this common
> mistake; why can't our
> Dylan compilers?

Brandon makes a good point here. Over the years, C/C++ compiler writers have
added a lot of warnings for things that are perfectly legal, but that
commonly surprise programmers. The classic example being:

    if (the_meaning_of_life = 42) {
      ...
    }

Even C/C++ programmers with years and years of experience sometimes get to
see this warning message.

Now, in this *particular* Dylan case, I can imagine that it's not trivial
for the compiler to look for this. [Because each let introduces a new block
of scope -- and while I might appreciate the warning in the case called out
above, it would infuriate me to see it every time I shadowed *any* variable
name.] But that doesn't mean it shouldn't be added to the wish-list.



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion



Quote:
> > -----Original Message-----


> > Sent: Monday, March 22, 1999 5:35 AM

> > Subject: Re: local variable confusion

> [...]
> > define method main () =>  ()
> >     let answer :: <string> = "Brandon";
> >     let answer :: <string> = "Corfman";
> > end method main;

> > If you think it's a scenario that doesn't come up very often,
> > remember that it's
> > unlikely to come up when the two lines are next to each
> > other, but when they are
> > more than a page apart, it is quite easy to forget that you
> > are reusing a
> > variable name. Instead of the compiler shadowing the old
> > definition (unhelpful),
> > why not have it post a warning (very helpful)?

> > C/C++ compilers help us out by acknowledging this common
> > mistake; why can't our
> > Dylan compilers?

> Brandon makes a good point here. Over the years, C/C++ compiler writers have
> added a lot of warnings for things that are perfectly legal, but that
> commonly surprise programmers. The classic example being:

>     if (the_meaning_of_life = 42) {
>       ...
>     }

> Even C/C++ programmers with years and years of experience sometimes get to
> see this warning message.

> Now, in this *particular* Dylan case, I can imagine that it's not trivial
> for the compiler to look for this. [Because each let introduces a new block
> of scope -- and while I might appreciate the warning in the case called out
> above, it would infuriate me to see it every time I shadowed *any* variable
> name.] But that doesn't mean it shouldn't be added to the wish-list.

An alternative that would have caught Brandon's mistake would be to warn about
unused bindings.

__Jason



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion


    Date: 19 Mar 1999 16:12:12 -0500

    let  ( answer :: <string>  , answer :: <string>  ) =  values ( "Brandon" ,
                                                                   "Corfman" ) ;

It seems to me that this should generate some kind of warning like
"X is bound more than once":

  begin
    let (x, x) = foo();
  end;

and this should generate "X is bound but never used":

  begin
    let x = foo();
    let x = bar();
  end;



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:
> An alternative that would have caught Brandon's mistake would be to warn about
> unused bindings.

> __Jason

Jason,

Would the "unused bindings" warning work in the following (slightly more complex)
scenario?

    let a = "Brandon";
    format-out ("%s",a);
    ....
    let a = "Corfman";
    format-out ("%s",a);

So, in other words, the bindings might be used (if I understand what you mean), but
you would still want a "redefinition" warning..

Brandon



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion


    Date: Mon, 22 Mar 1999 10:47:25 -0500

    > An alternative that would have caught Brandon's mistake would be to warn about
    > unused bindings.
    >
    > __Jason

    Jason,

    Would the "unused bindings" warning work in the following (slightly more complex)
    scenario?

        let a = "Brandon";
        format-out ("%s",a);
        ....
        let a = "Corfman";
        format-out ("%s",a);

    So, in other words, the bindings might be used (if I understand what you mean), but
    you would still want a "redefinition" warning..

Quite honestly, I see nothing here worth warning about.  You created a
context with a binding for 'a', used it, then created a new context
with a new bindining for 'a', and used it.

I do this sort of thing all the time.  Maybe a Dylan-Lint might say
something about this, but I don't think the compiler should warn.



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:

> > An alternative that would have caught Brandon's mistake would be to warn about
> > unused bindings.

> > __Jason

> Jason,

> Would the "unused bindings" warning work in the following (slightly more complex)
> scenario?

No.

Quote:
>     let a = "Brandon";
>     format-out ("%s",a);
>     ....
>     let a = "Corfman";
>     format-out ("%s",a);

> So, in other words, the bindings might be used (if I understand what you mean), but
> you would still want a "redefinition" warning..

It might be useful to warn in this case if the rebinding was in the same
block, but it probably shouldn't warn in the following case:

  let foos = begin
               let foos = make(<stretchy-vector>);
               // ... accumulate foos ...
               foos
             end;

as this is a common Dylan coding style.

__Jason



Fri, 07 Sep 2001 03:00:00 GMT  
 local variable confusion

Quote:

> Now, in this *particular* Dylan case, I can imagine that it's not trivial
> for the compiler to look for this. [Because each let introduces a new block
> of scope -- and while I might appreciate the warning in the case called out
> above, it would infuriate me to see it every time I shadowed *any* variable
> name.] But that doesn't mean it shouldn't be added to the wish-list.

I rebind variables all the time like this (OK, in Lisp, but I'd do the
same in Dylan), so I'd be against a warning.  It seems to me that
it would be adequate to warn for variables bound but not used, which is
useful in any case, and catches most of these cases I think.

--tim



Fri, 07 Sep 2001 03:00:00 GMT  
 
 [ 37 post ]  Go to page: [1] [2] [3]

 Relevant Pages 

1. local variable confusion

2. Local variable confusion

3. local variable and local variable in block behave differently

4. Sequence local = local variable?

5. Local variables - lifetime and access variables [Q]

6. accessing a local variable in from a widgets -variable or -command properties

7. missing data from variables, confusion over split

8. Confusion in variable scope & mega widget construction

9. variable name and type confusion...

10. Variables confusion

11. Beginner J questions: local variables

12. local variables in functions

 

 
Powered by phpBB® Forum Software