如何在此示例中设置对节点的引用

时间:2018-03-05 21:11:22

标签: ruby hashmap graph-theory

当我尝试设置我的图形时,它会创建一个近乎无限的循环,其中每个节点都保存每个其他节点的关系。但我只想让`nodes.film_actor_hash'拥有节点名称和对节点的引用。我如何得到一个参考而不是节点本身?

如果您只是将我的代码复制并粘贴到irb或pry中,我应该添加,你会看到我的意思。

class Node
  attr_accessor :name
  attr_accessor :film_actor_hash

  def initialize(name)
    self.name = name
    self.film_actor_hash = {}
  end
end

require_relative 'nodes'
class Graph
  attr_accessor :actors
  attr_accessor :films
  def initialize
    @actors = []
    @films = []
  end
end

graph = Graph.new()

a= Node.new("a")
b= Node.new("b")
c= Node.new("c")
d= Node.new("d")
e= Node.new("e")
f= Node.new("f")
g= Node.new("g")
h= Node.new("h")
i= Node.new("i")
j= Node.new("j")
kevin_bacon= Node.new("kevin_bacon")
l= Node.new("l")
m= Node.new("m")
n= Node.new("n")
o= Node.new("o")
p= Node.new("p")
q= Node.new("q")
r= Node.new("r")
s= Node.new("s")

one = Node.new("one")
two = Node.new("two")
three = Node.new("three")
four = Node.new("four")
five = Node.new("five")
six = Node.new("six")
seven = Node.new("seven")
eight = Node.new("eight")
nine = Node.new("nine")
ten = Node.new("ten")
eleven = Node.new("eleven")
twelve = Node.new("twelve")
thirteen = Node.new("thirteen")
fourteen = Node.new("fourteen")
fifteen = Node.new("fifteen")
sixteen = Node.new("sixteen")
seventeen = Node.new("seventeen")
eighteen = Node.new("eighteen")
nineteen = Node.new("nineteen")

a.film_actor_hash['sixteen'] = sixteen
a.film_actor_hash['one'] = one
b.film_actor_hash['one'] = one
b.film_actor_hash['two'] = two
c.film_actor_hash['two'] = two
c.film_actor_hash['three'] = three
d.film_actor_hash['three'] = three
d.film_actor_hash['four'] = four
e.film_actor_hash['four'] = four
e.film_actor_hash['five'] = five
f.film_actor_hash['five'] = five
f.film_actor_hash['six'] = six
g.film_actor_hash['six'] = six
g.film_actor_hash['seven'] = seven
h.film_actor_hash['seven'] = seven
h.film_actor_hash['eight'] = eight
i.film_actor_hash['eight'] = eight
i.film_actor_hash['nine'] = nine
j.film_actor_hash['nine'] = nine
j.film_actor_hash['ten'] = ten
l.film_actor_hash['ten'] = ten
l.film_actor_hash['eleven'] = eleven
m.film_actor_hash['eleven'] = eleven
m.film_actor_hash['twelve'] = twelve
n.film_actor_hash['twelve'] = twelve
n.film_actor_hash['thirteen'] = thirteen
o.film_actor_hash['thirteen'] = thirteen
o.film_actor_hash['fourteen'] = fourteen
p.film_actor_hash['fourteen'] = fourteen
p.film_actor_hash['fifteen'] = fifteen
kevin_bacon.film_actor_hash['fifteen'] = fifteen
kevin_bacon.film_actor_hash['sixteen'] = sixteen

one.film_actor_hash['kevin_bacon'] = kevin_bacon
one.film_actor_hash['a'] = a
two.film_actor_hash['a'] = a
two.film_actor_hash['b'] = b
three.film_actor_hash['b'] = b
three.film_actor_hash['c'] = c
four.film_actor_hash['c'] = c
four.film_actor_hash['d'] = d
five.film_actor_hash['d'] = d
five.film_actor_hash['e'] = e
six.film_actor_hash['e'] = e
six.film_actor_hash['f'] = f
seven.film_actor_hash['f'] = f
seven.film_actor_hash['g'] = g
eight.film_actor_hash['g'] = g
eight.film_actor_hash['h'] = h
nine.film_actor_hash['h'] = h
nine.film_actor_hash['i'] = i
ten.film_actor_hash['i'] = i
ten.film_actor_hash['j'] = j
eleven.film_actor_hash['j'] = j
eleven.film_actor_hash['l'] = l
twelve.film_actor_hash['l'] = l
twelve.film_actor_hash['m'] = m
thirteen.film_actor_hash['m'] = m
thirteen.film_actor_hash['n'] = n
fourteen.film_actor_hash['n'] = n
fourteen.film_actor_hash['o'] = o
fifteen.film_actor_hash['o'] = o
fifteen.film_actor_hash['p'] = p
sixteen.film_actor_hash['p'] = p
sixteen.film_actor_hash['kevin_bacon'] = kevin_bacon

1 个答案:

答案 0 :(得分:1)

您的代码实际上正常运行。在Ruby中,"节点本身" 的参考。没有办法直接访问底层对象,所以你的代码只是传递指针。

问题在于:

  

如果您只是将我的代码复制并粘贴到irb或pry中,我应该添加,你会看到我的意思。

在irb / pry中计算表达式时,Ruby会在结果上调用inspect并将其打印到控制台。问题是inspect是递归的,即当您检查自定义类或散列时,它还inspect是类/散列的内容。由于所有对象都通过实例变量相互引用,因此最终会进入无限递归循环。我猜测inspect最终会达到堆栈限制并放弃。

观察差异:

sixteen.film_actor_hash.size # 2 elements in the hash
sixteen.film_actor_hash.inspect.size # 18743520 characters in its string representation!

从技术上讲,只要你不需要inspect你的物品,你就无需修理任何东西。但为了理智,你可以重新定义inspect不是递归的:

class Node
  def inspect
    "#<#{self.class}:0x%x #{self.name}>" % object_id
  end
end