# Iterators and Assigment

**URL:** <https://www.ruby-forum.com/t/iterators-and-assigment/54276>\
**Category:** Ruby\
**Created:** [February 28, 2006, 2:23pm UTC](https://www.ruby-forum.com/t/iterators-and-assigment/54276 "2006-02-28T14:23:56Z")\
**Posts on this page:** 4\
**Page:** 1

<div class="post-metadata">

**Author:** ![Godspeed](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/c4cdca/32.png) [@Godspeed](https://www.ruby-forum.com/u/Godspeed)\
**Post date:** [February 28, 2006, 2:23pm UTC](https://www.ruby-forum.com/t/iterators-and-assigment/54276/1 "2006-02-28T14:23:56Z")

</div>

Consider…

def fred  
yield $k  
puts “in fred #{$k}”  
end

$k=2  
fred {|o| o = 3}  
puts “outside fred #{$k}”

produces:

in fred 2  
outside fred 2

why is $k still 2 after the call to fred?

Thanks in advance.

---

<div class="post-metadata">

**Author:** ![Godspeed](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/c4cdca/32.png) [@Godspeed](https://www.ruby-forum.com/u/Godspeed)\
**Post date:** [February 28, 2006, 2:39pm UTC](https://www.ruby-forum.com/t/iterators-and-assigment/54276/2 "2006-02-28T14:39:18Z")

</div>

Godspeed wrote:

> produces:
> 
> in fred 2  
> outside fred 2
> 
> why is $k still 2 after the call to fred?

Because Ruby does call by value where values are object references.  
Same  
holds for blocks and their parameters. There is no implicit aliasing  
between k$ and o. When the block is invoked you get a new reference  
which  
initially points to the same instance as $k. Then you assign it and it  
points to some other object leaving $k still pointing to the old  
instance.

Kind regards

```
robert
```

---

<div class="post-metadata">

**Author:** ![Godspeed](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/c4cdca/32.png) [@Godspeed](https://www.ruby-forum.com/u/Godspeed)\
**Post date:** [March 1, 2006, 1:23pm UTC](https://www.ruby-forum.com/t/iterators-and-assigment/54276/3 "2006-03-01T13:23:50Z")

</div>

Thanks guys. Your responses have cleared this up. I was assumig some  
sort of  
substitution (of the block into the def) going on, but I realise it is  
the  
other way round, the parameters to yield are parameters to the block.  
Makes  
perfect sense now.

“Jonathan L.” [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid) wrote in message  
news:removed\_email\_address@domain.invalid…

---

<div class="post-metadata">

**Author:** ![Godspeed](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/c4cdca/32.png) [@Godspeed](https://www.ruby-forum.com/u/Godspeed)\
**Post date:** [March 1, 2006, 3:42am UTC](https://www.ruby-forum.com/t/iterators-and-assigment/54276/4 "2006-03-01T03:42:16Z")

</div>

On Tue, 2006-02-28 at 22:38 +0900, Robert K. wrote:

> > puts “outside fred #{$k}”  
> > between k$ and o. When the block is invoked you get a new reference which  
> > initially points to the same instance as $k. Then you assign it and it  
> > points to some other object leaving $k still pointing to the old instance.
> 
> Kind regards
> 
> ```
> robert
> 
> ```

So, try this:

def fred  
$k = yield  
puts “in fred #{$k}”  
end

$k = 2  
fred { 3 }  
puts “outside fred #{$k}”

Returns:

in fred 3  
outside fred 3

You can call yield with parameters if you need the value of $k to be  
accessible inside the block. Although $k is accessible inside the block  
anyway as it’s a global. Although you’re probably not using a global in  
your actual code.

Regards
