Есть ли лучшая альтернатива этой рубиевой идиоме? - PullRequest
4 голосов
/ 15 января 2010

Я часто пишу этот бит кода в моих контроллерах:

params[:task][:completed_at] = Time.parse(params[:task][:completed_at]) if params[:task][:completed_at]

Не зацикливайтесь на том, что я здесь делаю, потому что причины меняются каждый раз; но во многих случаях мне нужно проверить значение в параметрах и изменить его, прежде чем передать его на create или update_attributes.

Повтор params[:task][:completed_at] три раза кажется очень плохим. Есть ли лучший способ сделать это?

Ответы [ 3 ]

11 голосов
/ 15 января 2010

Один способ немного укоротить это:

if c = params[:task][:completed_at]
  params[:task][:completed_at] = Time.parse(c)
end

Или, возможно, вы предпочтете это:

params[:task][:completed_at] &&= Time.parse(params[:task][:completed_at])

Во втором случае назначение произойдет, только если левая сторона "правдива".

0 голосов
/ 15 января 2010

Я не очень хорошо знаком с Ruby, но, поскольку он имеет корни Perl, может существовать конструкция, позволяющая записать его так:

$_ = Time->parse($_) for params[:task][:completed_at] || ();

в основном использует цикл for для создания псевдонима для переменной, если она существует

может быть что-то вроде:

(params[:task][:completed_at] || ()).each { |i| i = Time.parse(i) }

редактирование:

Я вижу, что в Ruby есть ключевое слово alias. Я недостаточно знаком с ним, чтобы привести пример с Ruby, но в Perl вышеприведенное также может быть написано:

local *_ = \$params[$task][$completed_at];

$_ = Time->parse($_) if defined;

, который указывает, что $_ будет псевдонимом для $params[$task][$completed_at]

Я попытался поиграть с этим кратко в Ruby, но не нашел способа присвоить псевдоним идентификатору, только глобальные переменные.

0 голосов
/ 15 января 2010

Полагаю, вы могли бы подумать сделать что-то подобное.

Реализация #to_time в String и NilClass, возможно в extensions.rb (как рекомендуется в Ruby Best Practices , например,

require 'time'
class String
  def to_time
    Time.parse(self) # add error/exception handling to taste
  end
end

class NilClass
  def to_time
    nil
  end
end

Тогда вы можете просто позвонить params[:task][:created_at].to_time и дублирование исчезнет.

Я совсем не уверен, что это обязательно является «наилучшей практикой», но ИМХО это отвечает цели вопроса ...

...