Простой 'или' не работает, как ожидалось - PullRequest
1 голос
/ 11 сентября 2010

У меня интересная проблема с относительно простым заданием ниже. Каждый из блоков в скобках в начале оценивается как nil , оставляя Rubygame::Surface.new в качестве значения, которому @image должно быть присвоено. К сожалению, на следующей строке, где я установил @rect, он выдает NoMethodError , потому что @image равен nil .

@image = (image unless image.nil?) or 
         (Rubygame::Surface.autoload(image_file) unless image_file.nil?) or 
         (Rubygame::Surface.autoload("#{@name}.png") unless @name.nil?) or 
         Rubygame::Surface.new([16, 16])
@rect = Rubygame::Rect.new [0, 0], [@image.width, @image.height]

Подобные тесты выполняются в IRB, как и ожидалось, поэтому я вполне уверен, что оператор 'or' правильно сформирован, но я не могу понять, почему он не возвращает новую поверхность, когда все остальное ноль .

Ответы [ 3 ]

5 голосов
/ 11 сентября 2010

Ключевые слова or и and в Ruby имеют очень, очень низкий приоритет .Даже ниже, чем оператор присваивания =.Поэтому просто замените их на || и && соответственно (оба переплета крепче, чем =), и все должно работать так, как вы ожидаете.Здесь указан приоритет оператора в Ruby .

В дополнение к этому, я бы сказал, что ваш код очень плотный.Подумайте над рефакторингом чего-то подобного следующему, которое, я думаю, гораздо лучше передает смысл вашего кода.

@image = case
  when image then image
  when image_file then Rubygame::Surface.autoload(image_file)
  when @name then Rubygame::Surface.autoload("#{@name}.png")
  else Rubygame::Surface.new([16, 16])
end

@rect = Rubygame::Rect.new [0, 0], [@image.width, @image.height]
1 голос
/ 11 сентября 2010

Вы пробовали дополнительные уровни скобок?

@image = ((image unless image.nil?) or 
         (Rubygame::Surface.autoload(image_file) unless image_file.nil?) or 
         (Rubygame::Surface.autoload("#{@name}.png") unless @name.nil?) or 
         Rubygame::Surface.new([16, 16]))
0 голосов
/ 12 сентября 2010

Почему вы используете RubyGame? Gosu среда разработки игр для Ruby стала быстрее и популярнее.

...