如何隐式引用变量

时间:2014-08-24 09:04:03

标签: ruby implicit receiver

我的代码包含很多内容:driver.blahblahblah。请考虑以下代码示例,取自http://www.browserstack.com/automate/ruby

require 'rubygems'
require 'selenium-webdriver'    
driver = Selenium::WebDriver.for(:remote,
  :url => "http://USERNAME:ACCESS_KEY@hub.browserstack.com/wd/hub")
driver.navigate.to "http://www.google.com/ncr"
element = driver.find_element(:name, 'q')
element.submit
puts driver.title
driver.quit

如何隐含driver?例如,有一个名为driver.save_screenshot()的方法。我想说save_screenshot("a.png"),因为只有driver变量/对象才有此方法。

2 个答案:

答案 0 :(得分:2)

您可以使用ActiveSupport中的delegate,如下例所示:

require 'active_support/core_ext/module/delegation'

class MyClass
  delegate :find_element, :save_screenshot, to: :driver

  def foo
    find_element
    save_screenshot
  end

  def driver
    @driver ||= Driver.new
  end
end

class Driver
  def find_element
    puts "find_element"
  end

  def save_screenshot
    puts "save_screenshot"
  end
end

MyClass.new.foo

或使用SimpleDelegator装饰司机(但我不推荐)。

答案 1 :(得分:0)

如果你有很多接收器为driver的方法,那么隐藏接收器的方法是:

driver.instance_eval do
  method_1...
  method_2...
  ...
end

但请注意,这会慢下来。如果你只是想找到一种懒惰的方法,那么最好的方法是将局部变量简化为单个字母,并且不要把它隐藏起来。

d = .... # instead of `drive`
d.method_1...
d.method_2...
...