You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

223 lines
5.2 KiB

4 years ago
4 years ago
4 years ago
4 years ago
4 years ago
4 years ago
4 years ago
4 years ago
4 years ago
4 years ago
  1. import model.Coord
  2. import model.Customer
  3. import model.HHCEdge
  4. import scala.collection.mutable.ArrayBuffer
  5. import util.Util
  6. import config.Conf
  7. import java.io.File
  8. import scala.io.Source
  9. object Main {
  10. def main(args: Array[String]): Unit = {
  11. val conf = new Conf(args.toIndexedSeq)
  12. val bufferedSource = Source.fromFile(conf.infile())
  13. val customers = Util.getCustomers(bufferedSource)
  14. bufferedSource.close()
  15. val hhc = new HHCSim(epsilonMax = 40, iterations = 10, WLDMax = 10)
  16. val fnl2 = hhc.go(customers)
  17. // customers.map(println(_))
  18. // val edges3 = customers.map(Util.formAdjMatrix)
  19. // val fnl2 = go(customers)
  20. fnl2 match {
  21. case Left(value) => println(value)
  22. case Right(groups) =>
  23. groups.foreach(c => {
  24. print(s"${c._1} -> ")
  25. c._2.foreach(e => {
  26. print(f"(${e._1}%d, ${e._2}%.2f), ")
  27. })
  28. println
  29. })
  30. }
  31. // edges3 match {
  32. // case Right(e) =>
  33. // e.foreach { d =>
  34. // d.foreach(g => print(f"$g%.2f, "))
  35. // println()
  36. // }
  37. // case Left(e) =>
  38. // println(s"Oops, an error occured. The error message was: $e")
  39. // }
  40. val coord1 = Coord(3, 4)
  41. println(s"Distance from origin = ${coord1.distance}")
  42. val cust1 = Customer(coord1, 5)
  43. val cust2 = Customer(Coord(2, 5), 7)
  44. println(s"Customer 1 = ${cust1}")
  45. println(s"Customer 2 = ${cust2}")
  46. val cust3 = Customer(Coord(3, 5), 6)
  47. val cust4 = Customer(Coord(6, 8), 9)
  48. val cust5 = Customer(Coord(5, 4), 6)
  49. val edge1 = HHCEdge(cust1, cust2)
  50. val edge2 = HHCEdge(cust3, cust4)
  51. println(s"Edge 1 = ${edge1}")
  52. println(s"Edge 1 weight = ${edge1.weight}")
  53. val V = Array(cust1, cust2, cust3, cust4, cust5)
  54. val E = Array(edge1, edge2)
  55. V.foreach(println(_))
  56. // prints
  57. // Customer(Coord(3, 4), 5)
  58. // Customer(Coord(2, 5), 7)
  59. // Customer(Coord(3, 5), 6)
  60. // Customer(Coord(6, 8), 9)
  61. // Customer(Coord(5, 4), 6)
  62. E.foreach(println(_))
  63. //prints
  64. // HHCEdge(Customer(Coord(3, 4), 5), Customer(Coord(2, 5), 7))
  65. // HHCEdge(Customer(Coord(3, 5), 6), Customer(Coord(6, 8), 9))
  66. // sample adjacency
  67. // format: off
  68. val edgesSeq = Seq(
  69. Seq(0 , 9 , 75, 0 , 0),
  70. Seq(9 , 0 , 95, 19, 42),
  71. Seq(75, 95, 0 , 51, 66),
  72. Seq(0 , 19, 51, 0 , 31),
  73. Seq(0 , 42, 66, 31, 0)
  74. );
  75. // adjacency list form
  76. // 0 -> 1 -> 2
  77. // 1 -> 0 -> 2 -> 3 -> 4
  78. // 2 -> 0 -> 1 -> 3 -> 4
  79. // 3 -> 1 -> 2 -> 4
  80. // 4 -> 1 -> 2 -> 3
  81. val edges = edgesSeq.map(e => {
  82. e.toArray
  83. }).toArray
  84. val mst = Util.mstUsingPrims(edges)
  85. // mst
  86. // 0, 9 , 0 , 0 , 0
  87. // 9, 0 , 0 , 19, 0
  88. // 0, 0 , 0 , 51, 0
  89. // 0, 19, 51, 0 , 31
  90. // 0, 0 , 0 , 31, 0
  91. // format: on
  92. // Prim's algorithm
  93. // Prim's algorithm result
  94. // Edge selected 0 - 1: 9
  95. // Edge selected 1 - 3: 19
  96. // Edge selected 3 - 4: 31
  97. // Edge selected 3 - 2: 51
  98. // Verify the result with the one at https://www.programiz.com/dsa/prim-algorithm
  99. val edges2: Array[Array[Double]] = Array.ofDim(5, 5)
  100. // create adjacency matrix from given customers
  101. for (i <- 0 to 4) {
  102. for (j <- 0 to 4) {
  103. edges2(i)(j) = Util.getHaversineDistance(V(i).location, V(j).location)
  104. }
  105. }
  106. edges2.foreach { e =>
  107. e.foreach { d =>
  108. print(f"$d%.2f, ")
  109. }
  110. println()
  111. }
  112. // prints
  113. // 0.00 , 159.64, 112.79, 563.55, 225.88
  114. // 159.64, 0.00 , 112.94, 564.16, 357.08
  115. // 112.79, 112.94, 0.00 , 478.40, 252.42
  116. // 563.55, 564.16, 478.40, 0.00 , 463.64
  117. // 225.88, 357.08, 252.42, 463.64, 0.00
  118. println()
  119. println("Initial graph:")
  120. edgesSeq.foreach { e =>
  121. e.foreach { d =>
  122. print(s"$d, ")
  123. }
  124. println()
  125. }
  126. println("MST: ")
  127. mst.foreach { e =>
  128. e.foreach { d =>
  129. print(s"$d, ")
  130. }
  131. println()
  132. }
  133. // 0, 9, 0 , 0 , 0
  134. // 0, 0, 0 , 19, 0
  135. // 0, 0, 0 , 0 , 0
  136. // 0, 0, 51, 0 , 31
  137. // 0, 0, 0 , 0 , 0
  138. val (mst2, centr, removed) = Util.findCentroids(mst)
  139. // val (centr2, eds2) = Util.findCentroids(edges2)
  140. println()
  141. println(s"Centroids: \n$centr")
  142. println(s"Removed: \n$removed")
  143. val (_, clust, _) = Util.findClusters(mst, centr, removed)
  144. val adjList = Util.makeAdjacencyList(edges, centr)
  145. println(s"Clusters:")
  146. clust.foreach(c => {
  147. val (e, d) = c
  148. print(s"$e: ")
  149. d.foreach(f => {
  150. print(s"-> $f ")
  151. })
  152. println()
  153. })
  154. println()
  155. val fnl = Util.groupClusters(centr, clust, removed)
  156. println(s"Final cluster groups: \n$fnl")
  157. // Output
  158. //
  159. // Initial graph:
  160. // 0, 9, 75, 0, 0,
  161. // 9, 0, 95, 19, 42,
  162. // 75, 95, 0, 51, 66,
  163. // 0, 19, 51, 0, 31,
  164. // 0, 42, 66, 31, 0,
  165. // MST:
  166. // 0, 9, 0, 0, 0,
  167. // 9, 0, 0, 19, 0,
  168. // 0, 0, 0, 51, 0,
  169. // 0, 19, 51, 0, 31,
  170. // 0, 0, 0, 31, 0,
  171. // Centroids:
  172. // Vector(2, 3, 4)
  173. // Removed:
  174. // Vector((2,3,51), (3,2,51), (3,4,31), (4,3,31))
  175. // Clusters:
  176. // 2: -> 2
  177. // 3: -> 3 -> 1 -> 0
  178. // 4: -> 4
  179. // Final cluster groups:
  180. // Map(2 -> Vector((3,51)), 3 -> Vector((4,31), (2,51)), 4 -> Vector((3,31)))
  181. }
  182. }