Ruby: Как к evalulate несколько методов на отправляют команду?

Как приложение к ответу вреда, я отметил бы, что, как реестр окон, предпочтения OS X сознательно не удалены, когда приложение удалено, но, в отличие от реестра окон, предпочтения могут мигрировать с машины на машину, поскольку Вы обновляете свой Mac и используете "пользовательское средство" миграции.

Это может привести к неожиданным результатам, таким как установка "NeatoApp 2008" и обнаружив, что это знает все настройки, которые Вы выбрали для "NeatoApp 2003" даже при том, что версия 2003 года никогда не устанавливалась на Вашей текущей машине.

7
задан 28 September 2009 в 01:49
поделиться

4 ответа

В вашем случае лучше использовать instance_eval

"Test".instance_eval{chop!.chop!} #=> "Te"

А для вашего кода:

my_xml_element.instance_eval{parent.next_sibling.next_sibling}
8
ответ дан 6 December 2019 в 09:20
поделиться

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

require 'test/unit'

class Example
  def multi_send(str)
    str.split('.').inject(self){|klass, method| klass.send(method) }
  end
end

class MyTest < Test::Unit::TestCase  
  def test_multi_send
    a = Example.new
    methods = "class.to_s.downcase.chop!"
    assert a.multi_send(methods) == 'exampl'
  end
end
5
ответ дан 6 December 2019 в 09:20
поделиться

Я думаю, что вопрос в том, что у вас есть конкретная серия методов, определенных как строка, и вы хотите вызвать ее на каком-то объекте, верно?

class Object
  def call_method_chain(method_chain)
    return self if method_chain.empty?
    method_chain.split('.').inject(self){|o,m| o.send(m.intern)}
  end
end

>> User.first.profile.address.state.name
=> "Virginia"
>> User.first.call_method_chain("profile.address.state.name")
=> "Virginia"
1
ответ дан 6 December 2019 в 09:20
поделиться

Собственно, Хелл был почти прав. Используйте это:

methods_chain = "parent.next_sibling.next_sibling"
result = my_xml_element.instance_eval( eval methods_chain )

Этот код почти в 20 раз быстрее, чем использование split (), и позволяет передавать методы цепочки с аргументами, например:

methods = "power!(2).div(57).+(12).to_f"
42.instance_eval { eval methods }
6
ответ дан 6 December 2019 в 09:20
поделиться