19

In IF block i need to check if some condition true and if it does, exit from block.

#something like this
if 1 == 1
  return if some_object && some_object.property
  puts 'hello'
end

How can i do it?

3 Answers 3

21

You can't break out of an if like that. What you can do is add a sub-clause to it:

if (cond1)
  unless (cond2)
    # ...
  end
end

If you're having problems with your logic being too nested and you need a way to flatten it out better, maybe what you want to do is compute a variable before hand and then only dive in if you need to:

will_do_stuff = cond1
will_do_stuff &&= !(some_object && some_object.property)

if (will_do_stuff)
  # ...
end

There's a number of ways to avoid having a deeply nested structure without having to break it.

Sign up to request clarification or add additional context in comments.

4 Comments

+1 for computing a variable beforehand, which gives a name to the condition. A good name will vastly improve the readability.
I'd recommend avoiding this and defining more methods if you need to. This is the pattern that Rails uses and it works very well. Split up methods into doing the most atomic thing that you can live with — in this case, another (private?) method in the same class/object can be used to test this condition. E.g. def will_parse?(obj); !obj.nil? && obj.respond_to?(:parse) && obj.is_ready_and_willing?; end
&&= is the binary-and equivalent of ||=, so a &&= b is the same as a && a = b. So if a is truthy, then the value of b is assigned to a.
@coreward: Defining methods is certainly one way to refactor this, and having helper methods like should_do_x? instead of a pile of complicated logic is a great way to do it, but in this case it's not clear how much logic there is.
2

Use care in choosing the words you associate with things. Because Ruby has blocks, I'm not sure whether you're under the impression that a conditional statement is a block. You can't, for example, do the following:

# will NOT work:
block = Proc.new { puts "Hello, world." }
if true then block

If you need to have a nested conditional, you can do just that without complicating things any:

if condition_one?
  if condition_two?
    # do some stuff
  end
else
  # do something else
end

3 Comments

This is a bit misleading, because if you changed the second line of that first snippet to if true then block.call end then it would work
@DaveMongoose That's because you're calling the 'call' method on a Proc instance, but thanks for the downvote
is there a counter example of something in ruby that is a block but can be substituted for a proc instance (like block)? I think the syntax requires it to be &block if you're using it in place of an explicit block.
0

Instead of if, you can use a while loop that never actually loop, and put breaks wherever fits your need.

while some·condition
  something·likely
  break unless some·additional·condition
  something·less·likely
  break
end

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.