def parse(range_str)
partial = '\d+(?:[.]\d+)?(?:[.][x]|[.]\d+(?:[-][0-9a-z.-]*)?)?'
exact = '\d+[.]\d+[.]\d+(?:[-][0-9a-z.-]*)?'
range = range_str.gsub(/([(><=~])[ ]+/, '\1')
range = range.gsub(/ - /, '#').strip
return case range
when /\A(#{partial})\Z/i
parse_loose_version_expression($1)
when /\A([><][=]?)(#{exact})\Z/i
parse_inequality_expression($1, $2)
when /\A~(#{partial})\Z/i
parse_reasonably_close_expression($1)
when /\A(#{exact})#(#{exact})\Z/i
parse_inclusive_range_expression($1, $2)
when /[ ]+/
parse_intersection_expression(range)
else
raise ArgumentError
end
rescue ArgumentError
raise ArgumentError, _("Unparsable version range: %{range}") % {range: range_str.inspect}
end