Ruby在没有显式包含声明的子类上执行self.included(base)方法?
发布时间:2020-12-16 19:20:33 所属栏目:百科 来源:网络整理
导读:我有一些从一个超类继承的类. 超类作为模块定义.模块内部是一个self.included(base)方法,用于设置一些实例变量. 所以这样的事情: module MyModule def self.included(base) base.instance_variable_set("@my_instance_variable",{}) endendclass MySuperCla
我有一些从一个超类继承的类.
超类作为模块定义.模块内部是一个self.included(base)方法,用于设置一些实例变量. 所以这样的事情: module MyModule def self.included(base) base.instance_variable_set("@my_instance_variable",{}) end end class MySuperClass include MyModule end class ClassA < MySuperClass end class ClassB < MySuperClass end 除非我在ClassA和ClassB中明确包含MyModule,否则我的实例变量将不会在这两个类中设置. 有没有办法确保模块self.included(base)方法在每个子类中执行而无需显式包含模块?因为它已经包含在超类中. 解决方法
类实例变量是类的私有.继承的类无法直接访问它们.这里有几种方法.
1.定义访问者 module MyModule def self.included(base) base.instance_variable_set :@my_instance_variable,{} base.extend ClassMethods end module ClassMethods def my_instance_variable # self is ClassA here,so we need to call superclass superclass.instance_variable_get :@my_instance_variable # => {} end end end class MySuperClass include MyModule end class ClassA < MySuperClass; end ClassA.my_instance_variable # => {} 2.更多元编程 但是每次从你继承一个类时都会调用一个钩子.您可以在此处设置变量.看一下这个. module MyModule def self.included(base) base.extend ClassMethods end module ClassMethods # make it a class method. It will be called on target classes later. def enhance klass klass.instance_variable_set("@my_instance_variable",{}) end end end class MySuperClass include MyModule # this hook will get called on 'class ClassA < MySuperClass` def self.inherited klass # set class instance var on child class enhance klass end end class ClassA < MySuperClass; end ClassA.instance_variable_get '@my_instance_variable' # => {} 注意:在此示例中,每个继承的类都获得自己的类实例var(并且基类不会获得一个).这可能更适合您的情况,可能不适合. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |