views:

140

answers:

3

Is there any better way to write this condition?

if (self.expense.nil? && self.income.nil?) || (!self.expense.nil? && !self.income.nil?)
  puts "test"
end
+17  A: 

You are testing to see if the expressions are both true or both false. Try this:

if (self.expense.nil? == self.income.nil?)

You don't care whether they are both true or both false, just that they are the same.

Mark Byers
Holy crap, I didn't know that Ruby had a XOR operator. That's the last time I skip the boring syntax chapter! ;-)
Tom Morris
@Tom Morris: Actually I think the xor isn't even necessary here. Check my update!
Mark Byers
Yup. That's better in the context of the question. But I'm still grateful for learning about the XOR operator (^).
Tom Morris
A: 

You could use Demorgan's law for the second half of the if condition

so (!self.expense.nil? && !self.income.nil?) becomes !(self.expense.nil? || self.income.nil?)

Albinoswordfish
+1  A: 

Despite the logic, since you're using an if to check for nil you could shorten the code like so:

if ((expense && income) || (!expense && !income))
  puts "test"
end

Correct me if I'm wrong.

tybro0103
A problem that *might* occur (depending on the possible values for the variables) is if one of the variables is `false`. Then the original if-statment returns a different result than yours. But that only needs to be considered if `false` is a possible value for one of the used variables.
Ragmaanir
good point... though depending on the business logic, it may still work fine
tybro0103