防止Ruby中的重复对象
这并不完全是单身,但很接近,所以我想这是很普遍的。我有一个类(Foo),其中的实例对应于具有唯一id的外部数据结构。我想确保没有两个Foo实例具有相同的ID-如果使用相同的ID值调用构造函数,则使用该ID的原始Foo实例以及所有其他值都将被简单地更新。换句话说,类似于:防止Ruby中的重复对象,ruby,singleton,Ruby,Singleton,这并不完全是单身,但很接近,所以我想这是很普遍的。我有一个类(Foo),其中的实例对应于具有唯一id的外部数据结构。我想确保没有两个Foo实例具有相同的ID-如果使用相同的ID值调用构造函数,则使用该ID的原始Foo实例以及所有其他值都将被简单地更新。换句话说,类似于: class Foo def initialize(id, var1, var2) if Foo.already_has? id t = Foo.get_object(id) t.var1 =
class Foo
def initialize(id, var1, var2)
if Foo.already_has? id
t = Foo.get_object(id)
t.var1 = var1
t.var2 = var2
return t
else
@var1 = var1
@var2 = var2
end
end
我可以想出两种方法:
您可以覆盖对象中的
Foo.new
,并在其中执行任何操作:
class-Foo
def自我更新(id,var1,var2)
如果instance=self.lookup,则返回instance
实例=self.allocate
instance.send:初始化,var1,var2
返回self.store(实例)
结束
结束
显然,您还可以使用不同的类方法来获取对象;将initialize
方法设置为私有,以帮助阻止意外分配
这样,每个ID只有一个实例,这通常比您建议的模式痛苦得多
您仍然需要实现存储
和查找
位,在类中没有比哈希
或数组
更好的方法来实现这一点
您需要考虑将存储在类中的内容包装到一个实例中,但仍然返回真实对象。这样,该类就可以强制执行唯一性,而不会限制使用过的每个ID始终保留在内存中
这并不适用于你的每一种情况,但肯定适用于某些情况。例如:
#省略了以前的代码。。。
返回存储(实例)
结束
def self.store(实例)
@实例| 124;={}
@实例[instance.id]=WeakRef.new(实例)
实例
结束
def自我查找(id)
@实例| 124;={}
如果weakref=@instances[id]和weakref.weakref_还活着?
返回weakref.uu getobj_u3;包装的实例
其他的
归零
结束
结束
谢谢你介绍我分配-我没有意识到它的存在。但是,对于查找,有没有比手动创建/管理实例数组更好的方法呢?没有。可能是一个散列,但这并没有什么不同。事实上,等等-你几乎肯定想从标准库,在数组中的对象周围-这样它们就不会永远停留:如果删除了一个对象,并且在再次调用构造函数之前没有进行垃圾收集,该怎么办?是否需要在每次调用.new时调用Objectspace.garbage\u collect?我更新了答案,但简言之:不,不要对垃圾收集做任何事情在内部保留一个weakref,但将真实对象返回给调用者,使其保持活动状态。