我有一个Skill模型,它有许多先决条件(或我的模型中的prereqs ),我需要创建一个N级深度的技能先决条件地图,因为我需要将此信息传递给Javascript (在我的控制器中带有gon宝石),用于一些疯狂的HTML5/KineticJS操作,显示该技能与其他技能之间关系的鸟瞰视图。
现在,下面的代码可以很好地一致地映射5个级别的深度。
delegate :url_helpers, to: 'Rails.application.routes'
def prereqs_map
prereqs_array = [ self.title.to_s, url_helpers.skill_path(self), Array.new(prereqs) ]
prereqs_array[2] = prereqs_array[2].map do |prereq1|
prereq1 = [ prereq1.title.to_s, url_helpers.skill_path(prereq1), Array.new(prereq1.prereqs).map do |prereq2|
prereq2 = [ prereq2.title.to_s, url_helpers.skill_path(prereq2), Array.new(prereq2.prereqs).map do |prereq3|
prereq3 = [ prereq3.title.to_s, url_helpers.skill_path(prereq3), Array.new(prereq3.prereqs).map do |prereq4|
prereq4 = [ prereq4.title.to_s, url_helpers.skill_path(prereq4), Array.new(prereq4.prereqs).map do |prereq5|
prereq5 = [ prereq5.title.to_s, url_helpers.skill_path(prereq5), [] ]
end ] # prereq depth 5
end ] # prereq depth 4
end ] # prereq depth 3
end ] # prereq depth 2
end # prereq depth 1
return prereqs_array
end正如您所看到的,问题是嵌套的映射非常混乱,而且我无法想出如何传递depth参数并让方法映射到我传递的任何深度。
我想一定有更好的方法来做这件事。有什么想法吗?
发布于 2012-12-31 02:00:51
试试这个:
class Skill
# has many prereqs?
def prereqs_map(depth = 5)
mapping = Proc.new do |node, depth, current_level|
[node.title.to_s, url_helpers.skill_path(node), node.prereqs.map {|prereq| mapping.call(prereq, depth, current_level+1)}] if current_level <= depth
end
mapping.call(self, depth, 0)
end
end
>> skill.prereqs_map(5)发布于 2012-12-31 01:56:30
通过将实例方法"to_tree“添加到您的模型中,您可以递归它。下面的代码随机设置一个依赖关系树,然后以所需的格式给出一个数组数组。
class Skill
attr_accessor :prereqs
attr_accessor :title
def randomly_create_tree depth=0
self.title = ["Coding", "Winning", "Smiling", "Eating"][rand(4)]
if depth < 3
self.prereqs = []
(0..rand(3)).each do
skill = Skill.new
skill.randomly_create_tree(depth + 1)
self.prereqs << skill
end
else
self.prereqs = []
end
self
end
def to_tree
prereqs.collect do |prereq|
[self.title, prereq.to_tree]
end
end然后:
s = Skill.new
s.randomly_create_tree
s.to_tree结果如下:
[["Coding", [["Winning", [["Winning", []], ["Winning", []]]]]]] 其中每个字符串是随机生成的标题。你可能也想添加你的url_helpers.skill_path,但我不确定那是做什么的。
https://stackoverflow.com/questions/14092780
复制相似问题