如何在 ruby 中使基类方法不可重写?
我有一些基类 A ,其方法不可被重写。
class A
def dont_override_me
puts 'class A saying, "Thank you for not overriding me!"'
end
end
另一个类 B 扩展了 A 并尝试重写 dont_override_me 方法。
class B < A
def dont_override_me
puts 'class B saying, "This is my implementation!"'
end
end
如果我实例化 B 并调用 dont_override_me,则将调用类 B 的实例方法。
b = B.new
b.dont_override_me # => class B saying, "This is my implementation!"
这是因为红宝石的特性。 可以理解。
但是,如何强制基类方法 dont_override_me
不可被其派生类覆盖? 我在 ruby 的 java 中找不到像 final
这样的关键字。 在 C++ 中,可以将基类方法设为非虚拟方法,以便派生类无法重写它们。 我如何在红宝石中实现这一目标?
I have some base class A with a method that is not to be overridden.
class A
def dont_override_me
puts 'class A saying, "Thank you for not overriding me!"'
end
end
And another class B that extends A and tries to override the dont_override_me
method.
class B < A
def dont_override_me
puts 'class B saying, "This is my implementation!"'
end
end
If I instantiate B and call dont_override_me
, class B's instance method will be called.
b = B.new
b.dont_override_me # => class B saying, "This is my implementation!"
This is because of ruby's properties. Understandable.
However, how do I force the base class method dont_override_me
to be non-overridable by it's derived classes? I could not find a keyword like final
in java for ruby. In C++, the base class methods can be made non-virtual so that they become non-overridable by the derived classes. How do I achieve this in ruby?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
您可以通过挂钩更改事件并将其改回来来做到这一点,但对我来说似乎有点难闻:
http://scie.nti.st/2008/9/17/making-methods-immutable-in-ruby
这是定义 Ruby 的东西之一,所以在我看来,反对它似乎有点毫无意义。 如果有人重新定义了某些东西,导致它严重损坏..那就是他们的问题;-)
You can do it, by hooking the change event and changing it back, but it seems a bit smelly to me:
http://scie.nti.st/2008/9/17/making-methods-immutable-in-ruby
It's one of those things that sort of defines Ruby, so fighting against it seems a little pointless imo. If someone redefines something so it breaks horribly.. that's their problem ;-)
这是一种方法:
http://www.thesorensens .org/2006/10/06/final-methods-in-ruby-prevent-method-override/
这也被打包到一个名为“finalizer”的 gem 中(gem install Finalizer),
这利用了 method_linked回调并将新方法名称与您希望成为
final
的方法列表进行比较。Here's a way to do it:
http://www.thesorensens.org/2006/10/06/final-methods-in-ruby-prevent-method-override/
This has also been packaged into a gem called "finalizer" (gem install finalizer)
This makes use of the method_added callback and compares the new method name with a list of methods that you wish to make
final
.我建议:
通过将 B 的方法隐藏在 mixin 中,您将得到您想要的。 A 中尚未存在的 B 方法中的任何方法都将可用。 A 中已有的方法不会被覆盖。
I recommend:
By keeping B's methods tucked away in an mixin, you get exactly what you desire. Any method of B's methods that are not already in A will be available. Methods that are already in A will not be overridden.
防止方法被子类覆盖的一种方法(但不推荐):
警告:此示例不完整。 如果您为子类中先前定义的方法添加
frozen_method
,则当该方法在子类中被修改时,它将丢失其实现。One way to prevent a method from being overridden by a subclass (but not recommend) :
Warning: this example is not complete. If you add
frozen_method
for a previously defined method in the subclass, when this method will be modified in the subclass, it will lose its implementation.