Ramy
Ramy

Reputation: 21271

How to translate this code from python to ruby?

I'm trying to translate some code from Python to Ruby but i'm stuck on this one function in python:

def notNoneOf(a, b):
  return a is None and b or a

My naive translation into ruby is like this:

def notNoneOf(a, b):
  return a.nil? and b || a
end

But this is giving me a void value expression

The usage of the function in the python code is as follows:

for m in re.finditer('<input.*?name=(?:"([^"]*)"|([^" >]*)) value=(?:"([^"]*)"|([^" >]*))[^>]*>', data):
    formData[notNoneOf(m.group(1), m.group(2))] = notNoneOf(m.group(3), m.group(4))

From playing with the code in a python REPL, it seems like this ruby code should work:

def notNoneOf(a, b):
  return a || b
end

But that seems like I'm missing some case for this?

This test in python makes it look like it's a bit different:

>>> a = None
>>> b = None
>>> notNoneOf(a,b)
>>> 

Any help appreciated.

Upvotes: 2

Views: 294

Answers (1)

Tom Lord
Tom Lord

Reputation: 28305

Looking at python operator precedence, it appears that the python code:

a is None and b or a

is logically equivalent* to:

(!a && b) || a

* See comments below -- it's not quite equivalent, but the explanation still holds true.

However, this a pointless over-complication. This is, again, equivalent to the much simpler:

a || b

A slight giveaway is the bizarre function name of notNoneOf. A more sensible function name would be eitherOf - which makes the above implementation look immediately correct.

So in ruby, I would just write this as:

def either(a, b)
  a || b
end

(Or, more likely, not even bother abstracting this into a separate method at all!!)


Seeing the wood through the trees however, I would not continue "translating" this code between the two languages ad verbium. The python code looks extremely confusing and bug prone; it's using a regular expression to parse HTML - which is just asking for trouble!

A much better solution is to write this with a HTML parser such as Nokogiri. You could write code something like:

doc = Nokogiri::HTML(data)
doc.css('input').each do |input|
  puts input.name
  puts input.value
end

Figure out exactly what the python code does, and try to replicate its behaviour rather than its implementation.

Upvotes: 2

Related Questions