scope issue of variable in iterator

M

Mohammad Khan

--------------050008030408040106030702
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 7bit

mkhan@mkhan:~$ irb
irb(main):001:0> batman = 'robin'
=> "robin"
irb(main):002:0> [ 'cat', 'dog', 'horse', 'chicken' ].each { |batman|
puts batman }
cat
dog
horse
chicken
=> ["cat", "dog", "horse", "chicken"]
irb(main):003:0> puts "Now you might think this would say 'robin', but
it says: #{batman}"
Now you might think this would say 'robin', but it says: chicken
=> nil
irb(main):004:0>



--
Mohammad Khan | Software Engineer
Lextranet | 107 Union Wharf | Boston, MA 02109
http://www.lextranet.com
(617) 227-4469 Extension 218

Smart Tools. Smart Team. Smart Choice.




THE INFORMATION IN THIS MESSAGE IS INTENDED ONLY FOR THE PERSONAL AND
CONFIDENTIAL USE OF THE DESIGNATED RECIPIENTS NAMED ABOVE AND MAY
CONTAIN LEGALLY PRIVILEGED INFORMATION. If the reader of this message
is not the intended recipient or an agent responsible for delivering
it to the intended recipient, you are hereby notified that you have
received this document in error, and that any review, dissemination,
distribution or copying of this message is strictly prohibited. If
you have received this communication in error, please notify us
immediately by telephone at 617-227-4469 Ext. 200. Thank you.


--------------050008030408040106030702
Content-Type: text/x-vcard; charset=utf-8;
name="mkhan.vcf"
Content-Transfer-Encoding: 7bit
Content-Disposition: attachment;
filename="mkhan.vcf"

begin:vcard
fn:Mohammad Khan
n:Khan;Mohammad
org:Legal Computer Solutions, Inc.
adr:;;107 Union Wharf;Boston;MA;02109;USA
email;internet:[email protected]
title:Software Engineer
tel;work:(617) 227-4469 Extension 218
tel;home:(781) 598-8947
x-mozilla-html:FALSE
url:http://www.lextranet.com
version:2.1
end:vcard


--------------050008030408040106030702--
 
M

Mark Volkmann

mkhan@mkhan:~$ irb
irb(main):001:0> batman =3D 'robin'
=3D> "robin"
irb(main):002:0> [ 'cat', 'dog', 'horse', 'chicken' ].each { |batman|
puts batman }
cat
dog
horse
chicken
=3D> ["cat", "dog", "horse", "chicken"]
irb(main):003:0> puts "Now you might think this would say 'robin', but
it says: #{batman}"
Now you might think this would say 'robin', but it says: chicken
=3D> nil

It's true that blocks introduce a new scope.
However, if they use variables that are in scope outside the block,
they don't shadow those variables, they use them.
 
R

Robert Klemme

Mark Volkmann said:
mkhan@mkhan:~$ irb
irb(main):001:0> batman = 'robin'
=> "robin"
irb(main):002:0> [ 'cat', 'dog', 'horse', 'chicken' ].each { |batman|
puts batman }
cat
dog
horse
chicken
=> ["cat", "dog", "horse", "chicken"]
irb(main):003:0> puts "Now you might think this would say 'robin',
but it says: #{batman}"
Now you might think this would say 'robin', but it says: chicken
=> nil

It's true that blocks introduce a new scope.
However, if they use variables that are in scope outside the block,
they don't shadow those variables, they use them.

.... like in other programming languages as well.

robert
 
D

David King Landrith

It's true that blocks introduce a new scope. However, if they use
variables that are in scope outside the block, they don't shadow
those variables, they use them.

about this block posted by Mohammad Khan
batman = 'robin'
[ 'cat', 'dog', 'horse', 'chicken' ].each { |batman| puts batman }
puts "Now you might think this would say 'robin', but it says: #
{batman}"

where the last line outputs:
Now you might think this would say 'robin', but it says: chicken

With no variable declarations in Ruby, there's no way to control the
scope, so the "first occurrence dictates scope" rule applies to
Mohammad's example. I think that this is counter intuitive. I think
that the pipe operators should be treated analogously to the way that
C++ treats declarations that occur within an expression; viz., they
are scoped to the end of the block dependent upon the expression.

Specifically, in C++ you have this:

int i = 5;
for (int i = 0; i < 100; i++) ...
printf("i=%u\n", i);

vs

int i = 5;
for (i = 0; i < 100; i++) ...
printf("i=%u\n", i);

I contend that the pipe operators are most intuitively understood as
being an example of the first type of operation and not the second.
It's safer, in any case, not to use duplicate variable names. Perhaps
I'm too comfortable with this sort of thing because of the deeply
entrenched habits accumulated from a background primarily in C, C++,
and (later) Java. In perl, this would require the use of a local
scope, which I've always hated.

In any case, before I ran the script that Mohammad has posted here, I
fully expected such a piece of code to behave like the first instance
and not like the second. This would have caused a bug that would have
been nearly impossible for me to find.

-------------------------------------------------------
David King Landrith
(w) 617.227.4469x213
(h) 617.696.7133

One useless man is a disgrace, two
are called a law firm, and three or more
become a congress -- John Adams
 
M

Mohammad Khan

When we are enjoying the freedom of using variable without
declearation, we are also loosing control over scope.


Mohammad



On 3/22/06, Mark Volkmann <[email protected]> wrote
^^^^^^^^^^^^^^^^^^^^^^^^^
gmail bug !!! ..

:
It's true that blocks introduce a new scope. However, if they use
variables that are in scope outside the block, they don't shadow
those variables, they use them.

about this block posted by Mohammad Khan
batman =3D 'robin'
[ 'cat', 'dog', 'horse', 'chicken' ].each { |batman| puts batman }
puts "Now you might think this would say 'robin', but it says: #
{batman}"

where the last line outputs:
Now you might think this would say 'robin', but it says: chicken

With no variable declarations in Ruby, there's no way to control the
scope, so the "first occurrence dictates scope" rule applies to
Mohammad's example. I think that this is counter intuitive. I think
that the pipe operators should be treated analogously to the way that
C++ treats declarations that occur within an expression; viz., they
are scoped to the end of the block dependent upon the expression.

Specifically, in C++ you have this:

int i =3D 5;
for (int i =3D 0; i < 100; i++) ...
printf("i=3D%u\n", i);

vs

int i =3D 5;
for (i =3D 0; i < 100; i++) ...
printf("i=3D%u\n", i);

I contend that the pipe operators are most intuitively understood as
being an example of the first type of operation and not the second.
It's safer, in any case, not to use duplicate variable names. Perhaps
I'm too comfortable with this sort of thing because of the deeply
entrenched habits accumulated from a background primarily in C, C++,
and (later) Java. In perl, this would require the use of a local
scope, which I've always hated.

In any case, before I ran the script that Mohammad has posted here, I
fully expected such a piece of code to behave like the first instance
and not like the second. This would have caused a bug that would have
been nearly impossible for me to find.

-------------------------------------------------------
David King Landrith
(w) 617.227.4469x213
(h) 617.696.7133

One useless man is a disgrace, two
are called a law firm, and three or more
become a congress -- John Adams
 
R

Robert Klemme

Mohammad said:
When we are enjoying the freedom of using variable without
declearation, we are also loosing control over scope.

What exactly are you trying to convey? I don't see how the absence of
variable declarations makes a difference with regard to scoping. By
deciding where to use a variable I have exact the same control as in
other languages.

Kind regards

robert
 
M

Mohammad Khan

Let me correct myself,
Actually we are not loosing control, its sort of inconvenience.

When I am writing
array.each do | blah | end

It would be really convenient if blah is scopped only in this iterator
block, regardless of blah decleared before or not.

Mohammad
 
R

Robert Klemme

Mohammad said:
Let me correct myself,
Actually we are not loosing control, its sort of inconvenience.

When I am writing
array.each do | blah | end

It would be really convenient if blah is scopped only in this iterator
block, regardless of blah decleared before or not.

You wouldn't be able to do things like this:

sum = 0
enum.each {|item| sum += item}

(I know there is inject for these cases but if you need to have more
state variables it gets inconvenient at times.)

Regards

robert
 
M

Mauricio Fernandez

You wouldn't be able to do things like this:

sum = 0
enum.each {|item| sum += item}

Not really; item being block-scoped wouldn't preclude access to other local
variables. What you wouldn't be able to do is:

def set_get
a = nil
[lambda{|a|}, lambda{a}]
end
set, get = set_get
set[1]
get[] # => 1

forcing you to go this way:
[lambda{|b| a = b}, lambda{a}]
 
R

Robert Klemme

Mauricio said:
Not really; item being block-scoped wouldn't preclude access to other local
variables.

Right. Apparently I wasn't fully awake when I wrote that.
What you wouldn't be able to do is:

def set_get
a = nil
[lambda{|a|}, lambda{a}]
end
set, get = set_get
set[1]
get[] # => 1

forcing you to go this way:
[lambda{|b| a = b}, lambda{a}]

Seems like a rare thing to do. This is another thing you cannot do with
the proposed change:

last = nil
enum.each {|last|}
puts "last was #{last}"

Although you can of course with #inject.

Kind regards

robert
 
M

Mohammad Khan

Seems like a rare thing to do. This is another thing you cannot do with
the proposed change:

last =3D nil
enum.each {|last|}
puts "last was #{last}"

last =3D nil
last =3D enum.last


I think, out of 100 uses of iterator, less then one would be the
example you shown above.

Key point of this thread was, what is more convenient,
To keep variable in iterator scoped in its block, even though the same
name already used as vairable name or not.


Mohammad
 
E

Erik Hollensbe

last = nil
last = enum.last


I think, out of 100 uses of iterator, less then one would be the
example you shown above.

Key point of this thread was, what is more convenient,
To keep variable in iterator scoped in its block, even though the same
name already used as vairable name or not.

Regardless of where it's used, ruby does not have dynamic scoping
(explicitly or implicitly)
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,770
Messages
2,569,583
Members
45,072
Latest member
trafficcone

Latest Threads

Top