2012-01-12 76 views
1

仅使用object.functionName语法可调用核心Ruby方法吗?是否有可能创建自己的方法可以在点语法中调用?点语法与参数传递语法

对于这种方法:下面

def namechanger (name) 

    nametochange = name 
    puts "This is the name to change: #{nametochange}" 

end 

第一个工程,第二个没有。

namechanger("Steve") 

"Steve".namechanger 

我得到一个错误的"Steve".namechanger

的错误是:

rb:21:in `<main>': private method `namechanger' called for "Steve":String (NoMethodError) 
+0

嗯,这个问题回避*是什么错误*?然后**为什么它有意义**?虽然你可以在Ruby中“打开课程”,但这也会导致很多污染。也许你想遵循一个模式,比如'Person.new(“Steve”)。change_name(“Fred”)'? – 2012-01-12 21:55:45

+0

我添加了错误,谢谢 – holaSenor 2012-01-12 21:57:21

+0

请注意,'obj.m' * always *的意思是“发送消息m'到接收方'obj'”,这意味着在Ruby中,唯一的方法就是使用“x”。工作是为了启用'“x”',或父母,例如'String',回应'm'。 (在某些*其他语言中*可以在不改变接收器或接收器父母的情况下创建过载。) – 2012-01-12 22:01:12

回答

3

是的,你可以添加方法,String类达到你想要的效果;变量“self”是指接收方法调用的对象。

class String 
    def namechanger 
    "This is the name to change: #{self}" 
    end 
end 
"Steve".namechanger # => This is the name to change: Steve 

这种做法被称为monkey patching,应该小心使用。

+1

注意:*应该谨慎使用*或(我的)*可能不在这里* – 2012-01-12 22:38:01

0

你在这里第一种形式是一种采用参数的方法,它与不采用任何参数的方法非常不同。让我说明

ruby namechanger("Steve")

查找名为namechanger方法并传递一个字符串参数给它。直向前。它在一些未知的上下文中查找,可能是另一种方法的本地人,它将在接收该方法的对象上查找它。

ruby "Steve".namechanger

是,它没有参数上存在String的方法。通常,这些方法使用隐含的self参数来操作某些数据。

+0

因此,一种方法需要参数不能在点语法中调用,并且只有在没有参数的情况下使用点语法调用没有参数CAB的方法self用于指向点之前的对象? – holaSenor 2012-01-12 22:02:04

+0

您引用的“点语法”仅仅是调用某个对象的方法的机制。它可以在任何你定义某个对象(类或类的实例)方法的地方使用。 – jer 2012-01-12 22:03:32

+0

这些示例仅仅定义了一个不带参数的方法,因为原始方法只接受一个字符串,并且如果您在字符串本身上定义了该方法,则无需再将其作为参数传递。你当然可以定义诸如'class String; def change_to(name);把“#{self}改为#{name}; end; end' – 2012-01-12 22:09:18

0

如果你想能够调用"Steve".namechanger,你必须做出namechangerString类的这样的方法:

class String 
    def namechanger 
    puts "This is the name to change: #{self}" 
    end 
end 

这通常被称为“猴子补丁”,你可能会想在进入相关考虑和讨论之前,稍微提高一下Ruby的熟练程度。

0

你可以做

class String 
    def namechanger 
    puts "This is the name to change: #{self}" 
    end 
end 

不同的是,你的第一个例子是,这是一个方法(基本)全局定义的,这需要一个字符串,并在其上运行。然而,上面的代码定义了一个名为“namechanger”的方法,它不接受参数,并直接在String类上定义它。因此,您的应用程序中的任何和所有字符串都将具有此方法。

但是,正如pst所说,你应该不要深入了解这种编程风格,直到你对Ruby更熟悉一点,这样你才能更容易地看到做这种monkeypatching的好处和坏处。其中一个考虑因素是你可能有许多字符串不能代表名字,并且这些字符串没有一个名为namechanger的方法。这就是说,如果你的目标只是为了与Ruby有点乐趣,看看你能做什么,去做,但要记住在寿命更长的项目中要更加小心。

1

相反的monkeypatching的,你可以送花儿给人继承,因此:

  1. 准确了解你在想什么对象真的是。
  2. 增益所有的字符串

例如方法:

class PersonName < String 
    def namechanger 
    puts "This is the name to change: #{self}" 
    end 
end 

s = PersonName.new("Iain") 
s.namechanger 

This is the name to change: Iain 
=> nil 
+0

我注意到你通过了'Iain',但是当你在s上调用namechanger时,它仍然打印正确。 'def def namechanger? – holaSenor 2012-01-12 22:24:30

+0

因为它是String的子类,它就像一个字符串(它是一个_enhanced_字符串)。想象一下,当你在String类中引用'self'时,它会返回它所持有的字符串,因此“ Iain“ – iain 2012-01-12 22:30:44

+0

实际上,在我看来,过分简化这种做法是不好的,在任何一个类中'self'都是指它自己,如果你把一个String对象放在一个像”This is the name to change:___“这样的字符串中,所以,在这种情况下,'self'会输出“Iain”。 – iain 2012-01-12 22:32:32