Для чего нужен «end.new» в Ruby?Почему бы просто не использовать «конец» сам по себе - PullRequest
1 голос
/ 09 мая 2019

Я сталкивался с этим вопросом , а ответ @Kris имеет следующую строку:

end.new

здесь:

  subject do
    Class.new do
      include ActiveModel::Validations    
      attr_accessor :email
      validates :email, email: true
    end.new
  end

Я не видел этого раньшеи не может найти других примеров или объяснений.

Почему бы просто не закончить само по себе, как это:

  subject do
    Class.new do
      include ActiveModel::Validations    
      attr_accessor :email
      validates :email, email: true
    end
  end

В чем разница?

1 Ответ

3 голосов
/ 09 мая 2019

Прежде всего вам необходимо понять, что вы можете связывать операторы на end, например

[1,2,3,4,5].select do |num|
  i % 2 == 0
end.map do |num|
  "#{num} is even"
end.each do |str|
  puts str
end

Далее, чтобы понять ваш пример, вам нужно понять, что такое «анонимный» класс.

Вместо этого вы можете определить этот класс как обычно:

class MyClass
  include ActiveModel::Validations    
  attr_accessor :email
  validates :email, email: true
end

и вы определите global MyClass переменную, которая ссылается на class . Конечно, вы можете позвонить MyClass.new, чтобы получить экземпляр.

Блок аномального класса Class.new do - это то же самое, но он не определяет глобальный идентификатор для класса. Вместо этого, чтобы получить дескриптор класса, необходимо присвоить переменную результату выражения Class.new do .. end.

Итак, если вы понимаете, что Class.new do ... end возвращает класс, и вы можете вызвать .new для любого класса, тогда вы можете сделать что-то вроде кода в вашем вопросе:

klass = Class.new { def foo; "bar"; end }
klass.new.foo # => "bar"

# or ...
Class.new { def foo; "bar"; end }.new.foo # => "bar"

do ... end - многострочная версия {} для определения блока

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...