What gain can I have with blocks over conventional methods?

I am a Java programmer and I am learning Ruby ...

But I don’t understand where these blocks of codes can give me an increase ... like what is the purpose of passing the block as an argument? why not use 2 specialized methods that can be reused?

Why do I need some code in a block that cannot be reused?

I would love the code examples ...

Thanks for the help!

+4
source share
2 answers

Consider some of the things you would use for anonymous classes in Java. for example, they are often used for plug-in behavior, such as event listeners, or for parameterizing a method that has a common layout.

Imagine that we want to write a method that accepts a list and returns a new list containing elements from the given list for which the specified condition is true. In Java, we will write an interface:

interface Condition { boolean f(Object o); } 

and then we could write:

 public List select(List list, Condition c) { List result = new ArrayList(); for (Object item : list) { if (cf(item)) { result.add(item); } } return result; } 

and then if we want to select even numbers from the list, we could write:

 List even = select(mylist, new Condition() { public boolean f(Object o) { return ((Integer) o) % 2 == 0; } }); 

To write the equivalent in Ruby, it could be:

 def select(list) new_list = [] # note: I'm avoid using 'each' so as to not illustrate blocks # using a method that needs a block for item in list # yield calls the block with the given parameters new_list << item if yield(item) end return new_list end 

and then we could choose even numbers with just

 even = select(list) { |i| i % 2 == 0 } 

Of course, this functionality is already built into Ruby, so in practice you just do

 even = list.select { |i| i % 2 == 0 } 

As another example, consider the code to open a file. You can do:

 f = open(somefile) # work with the file f.close 

but then you need to think about putting your close in the ensure block in case of an exception while working with the file. Instead you can do

 open(somefile) do |f| # work with the file here # ruby will close it for us when the block terminates end 
+9
source

The idea behind the blocks is that this is a highly localized code where it is useful to have a definition on the call site. You can use an existing function as an argument to a block. Just pass it as an optional argument and prefix it with &

+2
source

Source: https://habr.com/ru/post/1336797/


All Articles