marmeladze
marmeladze

Reputation: 6572

passing block to x.times method

I'm playing with ruby's built-in functions. I'm wondering how can I dynamically assign values and print it in a block.

Let me show you my example.

irb(main):001:0> i = 0
=> 0
irb(main):002:0> a = "a"
=> "a"
irb(main):003:0> while i<10
irb(main):004:1> x,a = a, a.next
irb(main):005:1> print x, " "
irb(main):006:1> i+=1
irb(main):007:1> end
a b c d e f g h i j => nil

Now I want to get same result with x.times method. 10.times {puts x,a=a, a.next} raises error. How can I achieve same result using x.times? My ruby version is 1.8.7

Edit: I tried a bit more and get this. But can't we use assignment like I've done in while loop? Except printing "a" and spaces, everything seems ok. Can you help me to print out "a" and spaces?

irb(main):011:0> x="a"
=> "a"
irb(main):012:0> 10.times {print x=x.next}
bcdefghijk=> 10

Upvotes: 0

Views: 157

Answers (3)

marmeladze
marmeladze

Reputation: 6572

I achieved my goal with some alternatives. Here I am listing them. I'll update by time.

10.times { x,a= a, a.succ; print x, " "}

1.upto(10) {x,a=a, a.next; print x, " "}

Upvotes: 0

Matt Brictson
Matt Brictson

Reputation: 11102

This seems like an artificial and convoluted problem, but I assume it is more of a thought exercise to get familiar with functional Ruby.

Here are some more solutions to try on for size.

Too easy?

("a".."j").each { |c| print c, " " }

Alternatively, since you have a starting value ("a") and are "summing" subsequent values onto that "total", that feels like an application of reduce:

10.times.reduce("a") { |c| print c, " "; c.next }

The result of a reduce block is used as the input for the next iteration. I think this is the "assignment in a loop" behavior that you were aiming for.

Upvotes: 1

Derrell Durrett
Derrell Durrett

Reputation: 576

I can't see an obvious way to do what you're asking for in a single line of code, but a='a'; 10.t­imes {x,a = a, a.nex­t; print x,' '} seems to work for me:

> a='a'; 10.ti­mes {x,a = a, a.nex­t; print­ x,' '}
=> "a b c d e f g h i j "

In Ruby you can use the ; as a command separator, but write everything in one line.

Of course, you could just as easily write:

> a='a'; 
  10.ti­mes do
    x,a = a, a.nex­t; 
    print­ x,' '
  end
=> "a b c d e f g h i j "

and achieve the same result.

Upvotes: 1

Related Questions