fork download
  1. class Node
  2. attr_accessor :predecessor,:f,:g,:h,:id,:x,:y
  3.  
  4. def initialize(id,x,y)
  5. @id,@x,@y = id,x,y
  6. f = g = h = 0
  7. @predecessor = nil
  8. end
  9. end
  10.  
  11. class Edge
  12. attr_accessor :to,:cost
  13. def initialize(to,cost)
  14. @to,@cost = to, cost
  15. end
  16. end
  17.  
  18. class Graph
  19. def initialize
  20. @nodes = []
  21. @adjacency = {}
  22. end
  23.  
  24. def add_node( id, x, y )
  25. @nodes.push Node.new( id, x, y )
  26. @adjacency[id] = []
  27. end
  28.  
  29. def get_node( id )
  30. @nodes[@nodes.index {|node| node.id == id }]
  31. end
  32.  
  33. def add_edge( from, to, cost )
  34. @adjacency[from] ||= []
  35. @adjacency[from] += [Edge.new( get_node( to ), cost )]
  36. end
  37.  
  38. def get_neighbors( id )
  39. @adjacency[id]
  40. end
  41.  
  42. def heuristic_function( current_node, end_node )
  43. x_distance = (current_node.x - end_node.x).abs
  44. y_distance = (current_node.y - end_node.y).abs
  45.  
  46. if x_distance > y_distance
  47. return 14 * y_distance + 10 * (x_distance - y_distance)
  48. else
  49. return 14 * x_distance + 10 * (y_distance - x_distance)
  50. end
  51. end
  52.  
  53. def lowest_f( set )
  54. lowest = nil
  55. set.each do |node|
  56. if ( !lowest || lowest.f > node.f )
  57. lowest = node
  58. end
  59. end
  60. lowest
  61. end
  62.  
  63. def update_neighbors ( node , end_node)
  64. get_neighbors( node.id ).map! do | neighbor |
  65. neighbor.to.g = node.g + neighbor.cost
  66. neighbor.to.h = heuristic_function( neighbor.to , end_node )
  67. neighbor.to.f = neighbor.to.g + neighbor.to.h
  68. end
  69. end
  70.  
  71. def AStar( id_origin, id_end )
  72. origin_node = get_node id_origin
  73. end_node = get_node id_end
  74. closed_set = []
  75. open_set = []
  76.  
  77. g_value = 0
  78. origin_node.g = 0
  79. origin_node.f = origin_node.g + heuristic_function( origin_node, end_node )
  80.  
  81. open_set.push origin_node
  82. current = nil
  83.  
  84. while open_set.empty? == false
  85. prev_current = current if current != origin_node
  86. current = lowest_f open_set
  87.  
  88. current.predecessor = prev_current
  89. open_set.delete current
  90. closed_set.push current
  91.  
  92. if current == end_node
  93. return reconstruct_path current
  94. end
  95.  
  96. update_neighbors current, end_node
  97.  
  98. get_neighbors( current.id ).each do | neighbor |
  99. open_set.push(neighbor)
  100. end
  101.  
  102. end
  103. end
  104.  
  105.  
  106. def reconstruct_path ( node )
  107. path = []
  108. while ( node )
  109. path.push node
  110. node = node.predecessor
  111. end
  112. path
  113. end
  114. end
  115.  
  116. g = Graph.new
  117. g.add_node( "La asuncion", 15,15 )
  118. g.add_node( "Los robles", 15,10 )
  119. g.add_node( "Manzanillo", 16,17 )
  120. g.add_edge( "Los robles", "Manzanillo", 3 )
  121. g.add_edge( "La asuncion", "Los robles", 2 )
  122.  
  123. p g.AStar("La asuncion", "Manzanillo")
Runtime error #stdin #stdout 0.02s 7476KB
stdin
Standard input is empty
stdout
Standard output is empty