CSC/ECE 517 Fall 2012/ch1 1w58 am: Difference between revisions
(→Blocks) |
|||
Line 150: | Line 150: | ||
In the above code the <i>map</i> method iterates over all the elements in <i>fruits</i> and reverse them. These reverse strings are stored in a temporary array which <i>map</i> method uses and returns that array when all the elements in <i>fruits</i> are iterated. | In the above code the <i>map</i> method iterates over all the elements in <i>fruits</i> and reverse them. These reverse strings are stored in a temporary array which <i>map</i> method uses and returns that array when all the elements in <i>fruits</i> are iterated. | ||
<br> | |||
In ruby, there are many methods that iterate over a range of values. These iterators are so written that they take a code block as part of their calling syntax and then yield control to that code block. This code block is executed as many times as specified by the iterator. | |||
= Blocks = | = Blocks = |
Revision as of 05:02, 1 October 2012
Ruby Blocks, Iterators, Functional Idioms
This wiki-page serves as a knowledge source for understanding Ruby Blocks, Iterators, Functional Idioms.
Introduction
Ruby has simplified the way programmers use loops and iterators. Ruby helps programmers to use DRY principle effectively by using blocks and defining iterators over collections. This helps in minimizing the development work that programmers often find in any other O-O style programming language. In ruby, these iterators, blocks and functional idioms are explained as:
Iterators are Collection defined methods that helps to iterate over all the elements present in a Collection. Ruby Collections are basically objects that store a group of data members of various types. Examples of Collection are arrays, hashes etc. A block consists of chunks of codes with a name assigned to it. For example,
my_block { puts "Hello World" }
Functional idioms are ... (please feel free to add about functional idioms here and become the author of it :) )
Iterators
Iterators in ruby can be written in following ways:
The times iterator:
The times iterators works similar to the for loop used in programming languages. As the name suggests it allows to loop over a chunk of code n number of times. For example:
5.times { puts "Hello Viewers!" }
This code produces the following output:
Hello Viewers! Hello Viewers! Hello Viewers! Hello Viewers! Hello Viewers!
Any chunk of code enclosed within the curly braces will execute 5 times in the above example.
The upto iterator
The upto iterator is also similar to the for loop. However, the difference between times and upto iterator is that, upto allows the programmer to specify the start index m and the end index n of the loop. So, if we define an upto iterator as m.upto(n) { # do some work }, then the code in curly braces will be executed n - m + 1 number of times. For example:
m = 45 n = 48 m.utpo(n) {puts "Hello Viewers! This is really cool, isn't it?"}
This code produces the following output:
Hello Viewers! This is really cool, isn't it? Hello Viewers! This is really cool, isn't it? Hello Viewers! This is really cool, isn't it? Hello Viewers! This is really cool, isn't it?
Here the loop will be executed 48 - 45 + 1 = 4 number of times. If we had used times than 45.times would have printed the puts statement 45 number of times. Hence it allows us to make loop execution dynamic as compared to the times iterator which is relatively static.
The step iterator
The above iterators times and upto performs the loop execution in increments of 1. Step iterator allows us to vary the increments of loop execution. It gives the programmers the flexibility to skip a few iterations of the loop if it is required as per the programmers logic. For example, consider the code:
guess_my_string = "HfezlvlbomWyowrqlad" 0.step(guess_my_string.length, 2) {|i| print guess_my_string[i]}
This code produces the following output -
HelloWorld
In the above code, the variable i collects the iteration number and the print statement prints the character of the String guess_my_string at position i. Hence we get the above output.
The each iterator
All collections in Ruby have an each method defined, that will allow programmers to go over all of the data members in collection for which the each method is called and do some operation with them. For example, consider the code:
example = [82, 117, 98, 121, 32, 105, 115, 32, 103, 114, 101, 97, 116, 33] example.each {|i| print i.chr }
The above code prints the following output -
Ruby is great!
In the above code the each iterator takes every element of the array example and prints its character equivalent.
The each iterator can also be used for hash traversal. Ruby defines the following methods for hash traversal:
- each_key
This method returns a collection of all the keys present in the hash on which the each_key method was called. - each_value
This method returns a collection of all the values present in the hash on which the each_value method was called. - each_pair
This method returns a collection of all the key, value pairs present in the hash on which the each_pair method was called.
Consider the example which explains the behavior of all the above methods defined for hash.
breakfast_menu = {"Martini" => 4, "apple pie" => 3, "pan cakes" => 5 } puts "Today's break fast menu -" breakfast_menu.each_key { |i| puts i } puts "\nTheir respective prices -" breakfast_menu.each_value { |i| puts "$#{i}" } puts "\nThe breakfast menu with their respective prices -" breakfast_menu.each_pair { |i, j| puts "#{i}: $#{j}" }
The above code produces the following output:
Today's break fast menu - Martini apple pie pan cakes Their respective prices - $4 $3 $5 The breakfast menu with their respective prices - Martini: $4 apple pie: $3 pan cakes: $5
In the above code, breakfast_menu defines a hash. It contains key, value pair. When each_key method is called on breakfast_menu, it prints all the keys present in the hash breakfast_menu. Similarly for each_value. For each_pair it prints all the key value pairs present in the hash. Hence the output.
The collect iterator
This simply returns all the elements of the collection. The collect method works for arrays as well as hashes. For example:
a = ["ruby", "rails", "ruby on rails"]; b = Array.new b = a.collect{ |i| i.capitalize} puts b
This produces the following output:
Ruby Rails Ruby on rails
In the above code, a.collect iterates over all the elements of a and returns a collection of all elements in a and assigns it to b
The map iterator
The map method creates a temporary array and stores in it whatever value is returned from each iteration of the block of code on which the map method is called. Then that temporary array is returned as a collection. For example consider the ruby code
fruits = [ "apple", "banana", "cherry" ] puts fruits.map { |i| i.reverse }
The above code produces the following output:
elppa ananab yrrehc
In the above code the map method iterates over all the elements in fruits and reverse them. These reverse strings are stored in a temporary array which map method uses and returns that array when all the elements in fruits are iterated.
In ruby, there are many methods that iterate over a range of values. These iterators are so written that they take a code block as part of their calling syntax and then yield control to that code block. This code block is executed as many times as specified by the iterator.
Blocks
A Block consists of a chunk of codes with a name assigned to it.