将实例保存在全局变量中
save instances in global variable
我需要将一个对象的所有实例保存在一个全局变量中,这样我就可以从另一个对象访问这些实例。不需要像参数一样传递它们。
在我的解决方案中,我有一个 mixin 和一个将实例放入变量的方法,我还使用了开放 class 技术将该 mixin 包含在 Object
中,因此其他对象使用它方法(而且不仅仅是一个 class)。
class Object
include Favourite
end
module Favourite
def favourite_it
#if the variable its not initialized:
@favourites.class == Array.class ? @favourites.push(self) :
@favourites = [].push(self)
end
def get_favourites
@favourites
end
end
#this class is only an example
class Dog
def initialize age
@age = age
end
end
class Dog_T
#all instances of this class will be saved in the variable
def initialize age
@age = age
favourite_it
end
end
class Handler
def do_something
#here I need to access the variable with all the instances of favourites to do something to them
end
end
这是一个简单的测试
handler = Handler.new
d1 = Dog_T.new(10)
d2 = Dog_T.new(12)
all_f = Handler.get_favourites
expect(all_f[0].age).to eq 10
expect(all_f[1].age).to eq 12
d3 = Dog_T.new(15)
all_f = Handler.get_favourites
expect(all_f[3].age).to eq 15
我尝试这样做,但只有每个实例将自己保存在不同的列表中(这是有道理的,因为我还没有使用全局变量)。
我怎样才能只有一个列表,在创建实例时添加实例并能够从 Handler
中清空和操作该列表?
Ruby 支持在模块中使用 class 变量。您还需要 Dog_T 对象的 reader 方法才能访问实例变量。由于 Favorite 对该对象一无所知,因此您需要使用 respond_to?
来防止调用列表中不存在的方法。例如,如果 Dog_R
class 没有方法 age
但确实添加了它自己,那么盲目地对成员调用 age
方法会出现运行时错误Favourite
数组。
module Favourite
@@favourites = [] # you can use a class variable in module
def self.favourite_it(obj) # singleton method of the class
@@favourites.push(obj)
end
def self.get_favourites # singleton method of the class, see below for usage example
@@favourites
end
end
class Object
include Favourite
end
class Dog
def initialize age
@age = age
end
end
class Dog_T
attr_reader :age # you need a reader to able to access it
def initialize age
@age = age
Favourite.favourite_it(self)
end
end
d1 = Dog_T.new(10)
d2 = Dog_T.new(12)
all_f = Favourite.get_favourites
all_f.each do |obj|
puts "#{obj.class}: #{obj.age if obj.respond_to?(:age)}"
end
puts '-' * 20
d3 = Dog_T.new(15)
all_f = Favourite.get_favourites
all_f.each do |obj|
puts "#{obj.class}: #{obj.age if obj.respond_to?(:age)}"
end
这个程序的输出是:
Dog_T: 10
Dog_T: 12
--------------------
Dog_T: 10
Dog_T: 12
Dog_T: 15
我需要将一个对象的所有实例保存在一个全局变量中,这样我就可以从另一个对象访问这些实例。不需要像参数一样传递它们。
在我的解决方案中,我有一个 mixin 和一个将实例放入变量的方法,我还使用了开放 class 技术将该 mixin 包含在 Object
中,因此其他对象使用它方法(而且不仅仅是一个 class)。
class Object
include Favourite
end
module Favourite
def favourite_it
#if the variable its not initialized:
@favourites.class == Array.class ? @favourites.push(self) :
@favourites = [].push(self)
end
def get_favourites
@favourites
end
end
#this class is only an example
class Dog
def initialize age
@age = age
end
end
class Dog_T
#all instances of this class will be saved in the variable
def initialize age
@age = age
favourite_it
end
end
class Handler
def do_something
#here I need to access the variable with all the instances of favourites to do something to them
end
end
这是一个简单的测试
handler = Handler.new
d1 = Dog_T.new(10)
d2 = Dog_T.new(12)
all_f = Handler.get_favourites
expect(all_f[0].age).to eq 10
expect(all_f[1].age).to eq 12
d3 = Dog_T.new(15)
all_f = Handler.get_favourites
expect(all_f[3].age).to eq 15
我尝试这样做,但只有每个实例将自己保存在不同的列表中(这是有道理的,因为我还没有使用全局变量)。
我怎样才能只有一个列表,在创建实例时添加实例并能够从 Handler
中清空和操作该列表?
Ruby 支持在模块中使用 class 变量。您还需要 Dog_T 对象的 reader 方法才能访问实例变量。由于 Favorite 对该对象一无所知,因此您需要使用 respond_to?
来防止调用列表中不存在的方法。例如,如果 Dog_R
class 没有方法 age
但确实添加了它自己,那么盲目地对成员调用 age
方法会出现运行时错误Favourite
数组。
module Favourite
@@favourites = [] # you can use a class variable in module
def self.favourite_it(obj) # singleton method of the class
@@favourites.push(obj)
end
def self.get_favourites # singleton method of the class, see below for usage example
@@favourites
end
end
class Object
include Favourite
end
class Dog
def initialize age
@age = age
end
end
class Dog_T
attr_reader :age # you need a reader to able to access it
def initialize age
@age = age
Favourite.favourite_it(self)
end
end
d1 = Dog_T.new(10)
d2 = Dog_T.new(12)
all_f = Favourite.get_favourites
all_f.each do |obj|
puts "#{obj.class}: #{obj.age if obj.respond_to?(:age)}"
end
puts '-' * 20
d3 = Dog_T.new(15)
all_f = Favourite.get_favourites
all_f.each do |obj|
puts "#{obj.class}: #{obj.age if obj.respond_to?(:age)}"
end
这个程序的输出是:
Dog_T: 10
Dog_T: 12
--------------------
Dog_T: 10
Dog_T: 12
Dog_T: 15