Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does this Ruby method return a "void value expression" error?

Tags:

ruby

I have this simple method

def is_palindrome?(sentence)
  raise ArgumentError.new('expected string') unless sentence.is_a?(String)
  safe_sentence = sentence.gsub(/\W+/, '').downcase
  return safe_sentence == safe_sentence.reverse
end

is_palindrome?"rails"

When I run it I get the error void value expression in line 4 which is the return statement

What's wrong here?

like image 340
Ahmad Al-kheat Avatar asked Mar 12 '15 23:03

Ahmad Al-kheat


2 Answers

I know this is long overdue but I noticed that this question didn't have an answer, as I was researching this exact same problem. I got the same kind of error not to long ago, what this error means is that Ruby is trying find a conditions change within your code and can't find it. This could be because Ruby isn't reading your code properly, or it could be because there's a bug somewhere. Fixing it is actually extremely easy.

def is_palindrome?(sentence)
  raise ArgumentError.new('expected string') unless sentence.is_a?(String)#<= Right here at 'unless' condition is changed
  safe_sentence = sentence.gsub(/\W+/, '').downcase
  return safe_sentence == safe_sentence.reverse
end

is_palindrome?"rails"

For some reason your version of Ruby is trying to find the condition change and defaulting to the original condition, it took a lot of research to come up with this.

So how do you fix this? The quick answer is to add an if/else statement instead of an unless:

def is_palindrome?(word)      
  to_rev = word.split('')
  rev_arr = to_rev.reverse
  new_word = rev_arr.join('')
  if new_word == word
    return true
  else
    return false
  end
end

is_palindrome?("racecar") #<= Returns true
is_palindrome?("test") #<= Returns false

If you wanted to use your regex:

def is_palindrome?(sentence)
  new_sentence = sentence.gsub(/\W+/, '').downcase.reverse
  if new_sentence == sentence.downcase
    return true
  elsif new_sentence != sentence.downcase
    return false
  else
    raise ArgumentError.new("String expected, instead found #{sentence}")
  end
end

is_palindrome?("racecar") #<= Returns true
is_palindrome?("test") <= Returns false

This is completely untested but you get the idea. This will add a change in conditions and will allow Ruby to realize that there is a change in the conditions.


Now why is your system outputting this? The short answer again is, nobody really knows, could be your system has a bug in it, could be that your version of Ruby somewhere is corrupted.

A couple things you can try:

  1. Reinstall the latest version of Ruby
  2. Go into the Ruby files within your system and check for anything that doesn't belong
  3. Move your directory to somewhere that is guaranteed to run with Ruby, IE into the Ruby directory itself. (This really shouldn't be an issue)
  4. Check your CPU usage, running program, etc., to see if there's anything that could be messing with your system
  5. LAST RESORT Hard reboot your system don't do this unless you absolutely have to, IE you find a virus that can't be wiped without you rebooting.

The reason people are unable to reproduce this error is probably because nobody can really see the way you're running the program, maybe you have a different version of Linux, or Windows, whatever. Hope this answered your question..

like image 174
13aal Avatar answered Nov 14 '22 21:11

13aal


I came to this question when I was trying to return evaluated boolean in return statement:

return x==1 or x==2

It turns out that ruby need brackets:

return (x==1 or x==2)
like image 34
Matzz Avatar answered Nov 14 '22 21:11

Matzz