From af7f33f046605e7c66464dbae7cd1c87099b4012 Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar Date: Wed, 29 Oct 2025 19:49:22 +0530 Subject: [PATCH 01/13] Add A* Search algorithm for shortest path --- .../com/thealgorithms/graph/AStarSearch.java | 122 ++++++++++++++++++ 1 file changed, 122 insertions(+) create mode 100644 src/main/java/com/thealgorithms/graph/AStarSearch.java diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java new file mode 100644 index 000000000000..5d1953c6d3d3 --- /dev/null +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -0,0 +1,122 @@ +package Astar; + +import java.util.*; + +/** + * A* Search Algorithm for shortest pathfinding. + * + *

Commonly used in games, navigation, and robotics. Combines Dijkstra’s Algorithm and heuristic estimation.

+ * + * + */ +public class AStarSearch { + + static class Node implements Comparable { + int id; + double g; // Cost from start + double h; // Heuristic to goal + double f; // Total cost = g + h + Node parent; + + Node(int id, double g, double h, Node parent) { + this.id = id; + this.g = g; + this.h = h; + this.f = g + h; + this.parent = parent; + } + + @Override + public int compareTo(Node o) { + return Double.compare(this.f, o.f); + } + } + + private final Map> graph; + + public AStarSearch() { + graph = new HashMap<>(); + } + + public void addEdge(int u, int v, int weight) { + graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); + graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); // if undirected + } + + private double heuristic(int node, int goal) { + return Math.abs(goal - node); // Simplified heuristic + } + + public List findPath(int start, int goal) { + PriorityQueue openSet = new PriorityQueue<>(); + Map gScore = new HashMap<>(); + Set closedSet = new HashSet<>(); + + openSet.add(new Node(start, 0, heuristic(start, goal), null)); + gScore.put(start, 0.0); + + while (!openSet.isEmpty()) { + Node current = openSet.poll(); + + if (current.id == goal) { + return reconstructPath(current); + } + + closedSet.add(current.id); + + for (int[] edge : graph.getOrDefault(current.id, new ArrayList<>())) { + int neighbor = edge[0]; + double tentativeG = current.g + edge[1]; + + if (closedSet.contains(neighbor)) continue; + + if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { + gScore.put(neighbor, tentativeG); + Node next = new Node(neighbor, tentativeG, heuristic(neighbor, goal), current); + openSet.add(next); + } + } + } + return Collections.emptyList(); + } + + private List reconstructPath(Node node) { + List path = new ArrayList<>(); + while (node != null) { + path.add(node.id); + node = node.parent; + } + Collections.reverse(path); + return path; + } + + public static void main(String[] args) { + Scanner sc = new Scanner(System.in); + AStarSearch aStar = new AStarSearch(); + + System.out.print("Enter number of edges: "); + int edges = sc.nextInt(); + + System.out.println("Enter edges in format: u v weight"); + for (int i = 0; i < edges; i++) { + int u = sc.nextInt(); + int v = sc.nextInt(); + int w = sc.nextInt(); + aStar.addEdge(u, v, w); + } + + System.out.print("Enter start node: "); + int start = sc.nextInt(); + + System.out.print("Enter goal node: "); + int goal = sc.nextInt(); + + List path = aStar.findPath(start, goal); + if (path.isEmpty()) { + System.out.println("No path found from " + start + " → " + goal); + } else { + System.out.println("Shortest path from " + start + " → " + goal + ": " + path); + } + sc.close(); + } +} \ No newline at end of file From 9a05c56fab79f8e855f518caaf3ea8ecd521037c Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar Date: Wed, 29 Oct 2025 20:03:18 +0530 Subject: [PATCH 02/13] Update A* Search: dynamic input, TheAlgorithms style --- .../com/thealgorithms/graph/AStarSearch.java | 242 ++++++++++-------- 1 file changed, 130 insertions(+), 112 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index 5d1953c6d3d3..da515a9737bd 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -1,122 +1,140 @@ -package Astar; +package com.thealgorithms.graph; import java.util.*; /** * A* Search Algorithm for shortest pathfinding. * - *

Commonly used in games, navigation, and robotics. Combines Dijkstra’s Algorithm and heuristic estimation.

+ *

Commonly used in games, navigation, and robotics. + * Combines Dijkstra’s Algorithm and heuristic estimation.

* - * + *

Reference: https://en.wikipedia.org/wiki/A*_search_algorithm

*/ public class AStarSearch { - static class Node implements Comparable { - int id; - double g; // Cost from start - double h; // Heuristic to goal - double f; // Total cost = g + h - Node parent; - - Node(int id, double g, double h, Node parent) { - this.id = id; - this.g = g; - this.h = h; - this.f = g + h; - this.parent = parent; - } - - @Override - public int compareTo(Node o) { - return Double.compare(this.f, o.f); - } - } - - private final Map> graph; - - public AStarSearch() { - graph = new HashMap<>(); - } - - public void addEdge(int u, int v, int weight) { - graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); - graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); // if undirected - } - - private double heuristic(int node, int goal) { - return Math.abs(goal - node); // Simplified heuristic - } - - public List findPath(int start, int goal) { - PriorityQueue openSet = new PriorityQueue<>(); - Map gScore = new HashMap<>(); - Set closedSet = new HashSet<>(); - - openSet.add(new Node(start, 0, heuristic(start, goal), null)); - gScore.put(start, 0.0); - - while (!openSet.isEmpty()) { - Node current = openSet.poll(); - - if (current.id == goal) { - return reconstructPath(current); - } - - closedSet.add(current.id); - - for (int[] edge : graph.getOrDefault(current.id, new ArrayList<>())) { - int neighbor = edge[0]; - double tentativeG = current.g + edge[1]; - - if (closedSet.contains(neighbor)) continue; - - if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { - gScore.put(neighbor, tentativeG); - Node next = new Node(neighbor, tentativeG, heuristic(neighbor, goal), current); - openSet.add(next); - } - } - } - return Collections.emptyList(); - } - - private List reconstructPath(Node node) { - List path = new ArrayList<>(); - while (node != null) { - path.add(node.id); - node = node.parent; - } - Collections.reverse(path); - return path; - } - - public static void main(String[] args) { - Scanner sc = new Scanner(System.in); - AStarSearch aStar = new AStarSearch(); - - System.out.print("Enter number of edges: "); - int edges = sc.nextInt(); - - System.out.println("Enter edges in format: u v weight"); - for (int i = 0; i < edges; i++) { - int u = sc.nextInt(); - int v = sc.nextInt(); - int w = sc.nextInt(); - aStar.addEdge(u, v, w); - } - - System.out.print("Enter start node: "); - int start = sc.nextInt(); - - System.out.print("Enter goal node: "); - int goal = sc.nextInt(); - - List path = aStar.findPath(start, goal); - if (path.isEmpty()) { - System.out.println("No path found from " + start + " → " + goal); - } else { - System.out.println("Shortest path from " + start + " → " + goal + ": " + path); - } - sc.close(); - } -} \ No newline at end of file + static class Node implements Comparable { + int id; + double g; // Cost from start + double h; // Heuristic to goal + double f; // Total cost = g + h + Node parent; + + Node(int id, double g, double h, Node parent) { + this.id = id; + this.g = g; + this.h = h; + this.f = g + h; + this.parent = parent; + } + + @Override + public int compareTo(Node o) { + return Double.compare(this.f, o.f); + } + } + + private final Map> graph; + + public AStarSearch() { + graph = new HashMap<>(); + } + + /** + * Adds an undirected edge between nodes u and v with the given weight. + */ + public void addEdge(int u, int v, int weight) { + graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); + graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); + } + + /** + * Heuristic function (simplified for numeric nodes). + */ + private double heuristic(int node, int goal) { + return Math.abs(goal - node); + } + + /** + * Finds the shortest path from start to goal using A* algorithm. + * + * @param start starting node + * @param goal goal node + * @return list of nodes representing the shortest path + */ + public List findPath(int start, int goal) { + PriorityQueue openSet = new PriorityQueue<>(); + Map gScore = new HashMap<>(); + Set closedSet = new HashSet<>(); + + openSet.add(new Node(start, 0, heuristic(start, goal), null)); + gScore.put(start, 0.0); + + while (!openSet.isEmpty()) { + Node current = openSet.poll(); + + if (current.id == goal) { + return reconstructPath(current); + } + + closedSet.add(current.id); + + for (int[] edge : graph.getOrDefault(current.id, new ArrayList<>())) { + int neighbor = edge[0]; + double tentativeG = current.g + edge[1]; + + if (closedSet.contains(neighbor)) continue; + + if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { + gScore.put(neighbor, tentativeG); + Node next = new Node(neighbor, tentativeG, heuristic(neighbor, goal), current); + openSet.add(next); + } + } + } + return Collections.emptyList(); + } + + /** + * Reconstructs path by following parent nodes. + */ + private List reconstructPath(Node node) { + List path = new ArrayList<>(); + while (node != null) { + path.add(node.id); + node = node.parent; + } + Collections.reverse(path); + return path; + } + + /** Dynamic usage: reads graph and start/goal from input */ + public static void main(String[] args) { + Scanner sc = new Scanner(System.in); + AStarSearch aStar = new AStarSearch(); + + System.out.print("Enter number of edges: "); + int edges = sc.nextInt(); + + System.out.println("Enter edges in format: u v weight"); + for (int i = 0; i < edges; i++) { + int u = sc.nextInt(); + int v = sc.nextInt(); + int w = sc.nextInt(); + aStar.addEdge(u, v, w); + } + + System.out.print("Enter start node: "); + int start = sc.nextInt(); + + System.out.print("Enter goal node: "); + int goal = sc.nextInt(); + + List path = aStar.findPath(start, goal); + if (path.isEmpty()) { + System.out.println("No path found from " + start + " → " + goal); + } else { + System.out.println("Shortest path from " + start + " → " + goal + ": " + path); + } + sc.close(); + } +} From 1bd62d66c2aaf595b0b65fb134a489f5a3fbf25f Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 20:10:14 +0530 Subject: [PATCH 03/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 241 +++++++++--------- 1 file changed, 116 insertions(+), 125 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index da515a9737bd..0ddcceec0888 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -12,129 +12,120 @@ */ public class AStarSearch { - static class Node implements Comparable { - int id; - double g; // Cost from start - double h; // Heuristic to goal - double f; // Total cost = g + h - Node parent; - - Node(int id, double g, double h, Node parent) { - this.id = id; - this.g = g; - this.h = h; - this.f = g + h; - this.parent = parent; - } - - @Override - public int compareTo(Node o) { - return Double.compare(this.f, o.f); - } - } - - private final Map> graph; - - public AStarSearch() { - graph = new HashMap<>(); - } - - /** - * Adds an undirected edge between nodes u and v with the given weight. - */ - public void addEdge(int u, int v, int weight) { - graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); - graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); - } - - /** - * Heuristic function (simplified for numeric nodes). - */ - private double heuristic(int node, int goal) { - return Math.abs(goal - node); - } - - /** - * Finds the shortest path from start to goal using A* algorithm. - * - * @param start starting node - * @param goal goal node - * @return list of nodes representing the shortest path - */ - public List findPath(int start, int goal) { - PriorityQueue openSet = new PriorityQueue<>(); - Map gScore = new HashMap<>(); - Set closedSet = new HashSet<>(); - - openSet.add(new Node(start, 0, heuristic(start, goal), null)); - gScore.put(start, 0.0); - - while (!openSet.isEmpty()) { - Node current = openSet.poll(); - - if (current.id == goal) { - return reconstructPath(current); - } - - closedSet.add(current.id); - - for (int[] edge : graph.getOrDefault(current.id, new ArrayList<>())) { - int neighbor = edge[0]; - double tentativeG = current.g + edge[1]; - - if (closedSet.contains(neighbor)) continue; - - if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { - gScore.put(neighbor, tentativeG); - Node next = new Node(neighbor, tentativeG, heuristic(neighbor, goal), current); - openSet.add(next); - } - } - } - return Collections.emptyList(); - } - - /** - * Reconstructs path by following parent nodes. - */ - private List reconstructPath(Node node) { - List path = new ArrayList<>(); - while (node != null) { - path.add(node.id); - node = node.parent; - } - Collections.reverse(path); - return path; - } - - /** Dynamic usage: reads graph and start/goal from input */ - public static void main(String[] args) { - Scanner sc = new Scanner(System.in); - AStarSearch aStar = new AStarSearch(); - - System.out.print("Enter number of edges: "); - int edges = sc.nextInt(); - - System.out.println("Enter edges in format: u v weight"); - for (int i = 0; i < edges; i++) { - int u = sc.nextInt(); - int v = sc.nextInt(); - int w = sc.nextInt(); - aStar.addEdge(u, v, w); - } - - System.out.print("Enter start node: "); - int start = sc.nextInt(); - - System.out.print("Enter goal node: "); - int goal = sc.nextInt(); - - List path = aStar.findPath(start, goal); - if (path.isEmpty()) { - System.out.println("No path found from " + start + " → " + goal); - } else { - System.out.println("Shortest path from " + start + " → " + goal + ": " + path); - } - sc.close(); - } + @FunctionalInterface + public interface Heuristic { + double estimate(int node, int goal); + } + + static class Node implements Comparable { + int id; + double g; // Cost from start + double h; // Heuristic to goal + double f; // Total cost = g + h + Node parent; + + Node(int id, double g, double h, Node parent) { + this.id = id; + this.g = g; + this.h = h; + this.f = g + h; + this.parent = parent; + } + + @Override + public int compareTo(Node o) { + return Double.compare(this.f, o.f); + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (!(o instanceof Node)) return false; + Node node = (Node) o; + return id == node.id; + } + + @Override + public int hashCode() { + return Objects.hash(id); + } + } + + private final Map> graph; + private final Heuristic heuristic; + + /** + * Constructor with default heuristic (|goal - node|). + */ + public AStarSearch() { + this.graph = new HashMap<>(); + this.heuristic = (node, goal) -> Math.abs(goal - node); + } + + /** + * Constructor with custom heuristic. + */ + public AStarSearch(Heuristic heuristic) { + this.graph = new HashMap<>(); + this.heuristic = heuristic; + } + + /** + * Adds an undirected edge between nodes u and v with the given weight. + */ + public void addEdge(int u, int v, int weight) { + graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); + graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); + } + + /** + * Finds the shortest path from start to goal using A* algorithm. + * + * @param start starting node + * @param goal goal node + * @return list of nodes representing the shortest path + */ + public List findPath(int start, int goal) { + PriorityQueue openSet = new PriorityQueue<>(); + Map gScore = new HashMap<>(); + Set closedSet = new HashSet<>(); + + openSet.add(new Node(start, 0, heuristic.estimate(start, goal), null)); + gScore.put(start, 0.0); + + while (!openSet.isEmpty()) { + Node current = openSet.poll(); + + if (current.id == goal) return reconstructPath(current); + + closedSet.add(current.id); + + for (int[] edge : graph.getOrDefault(current.id, new ArrayList<>())) { + int neighbor = edge[0]; + double tentativeG = current.g + edge[1]; + + if (closedSet.contains(neighbor)) continue; + + if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { + gScore.put(neighbor, tentativeG); + Node next = new Node(neighbor, tentativeG, heuristic.estimate(neighbor, goal), current); + openSet.add(next); + } + } + } + return Collections.emptyList(); + } + + /** + * Reconstructs path by following parent nodes. + */ + private List reconstructPath(Node node) { + List path = new ArrayList<>(); + while (node != null) { + path.add(node.id); + node = node.parent; + } + Collections.reverse(path); + return path; + } } From c2b5bda65305d44b277098115e431e1054a44f5f Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 20:18:03 +0530 Subject: [PATCH 04/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 59 ++++++------------- 1 file changed, 17 insertions(+), 42 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index 0ddcceec0888..a4a38d9a99c2 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -12,11 +12,6 @@ */ public class AStarSearch { - @FunctionalInterface - public interface Heuristic { - double estimate(int node, int goal); - } - static class Node implements Comparable { int id; double g; // Cost from start @@ -36,48 +31,25 @@ static class Node implements Comparable { public int compareTo(Node o) { return Double.compare(this.f, o.f); } - - @Override - public boolean equals(Object o) { - if (this == o) return true; - if (!(o instanceof Node)) return false; - Node node = (Node) o; - return id == node.id; - } - - @Override - public int hashCode() { - return Objects.hash(id); - } } private final Map> graph; - private final Heuristic heuristic; - /** - * Constructor with default heuristic (|goal - node|). - */ public AStarSearch() { - this.graph = new HashMap<>(); - this.heuristic = (node, goal) -> Math.abs(goal - node); + graph = new HashMap<>(); } - /** - * Constructor with custom heuristic. - */ - public AStarSearch(Heuristic heuristic) { - this.graph = new HashMap<>(); - this.heuristic = heuristic; - } - - /** - * Adds an undirected edge between nodes u and v with the given weight. - */ + /** Adds an undirected edge between nodes u and v with the given weight. */ public void addEdge(int u, int v, int weight) { graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); } + /** Heuristic function (simplified for numeric nodes). */ + private double heuristic(int node, int goal) { + return Math.abs(goal - node); + } + /** * Finds the shortest path from start to goal using A* algorithm. * @@ -90,13 +62,15 @@ public List findPath(int start, int goal) { Map gScore = new HashMap<>(); Set closedSet = new HashSet<>(); - openSet.add(new Node(start, 0, heuristic.estimate(start, goal), null)); + openSet.add(new Node(start, 0, heuristic(start, goal), null)); gScore.put(start, 0.0); while (!openSet.isEmpty()) { Node current = openSet.poll(); - if (current.id == goal) return reconstructPath(current); + if (current.id == goal) { + return reconstructPath(current); + } closedSet.add(current.id); @@ -104,21 +78,22 @@ public List findPath(int start, int goal) { int neighbor = edge[0]; double tentativeG = current.g + edge[1]; - if (closedSet.contains(neighbor)) continue; + if (closedSet.contains(neighbor)) { + continue; + } if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { gScore.put(neighbor, tentativeG); - Node next = new Node(neighbor, tentativeG, heuristic.estimate(neighbor, goal), current); + Node next = new Node(neighbor, tentativeG, heuristic(neighbor, goal), current); openSet.add(next); } } } + return Collections.emptyList(); } - /** - * Reconstructs path by following parent nodes. - */ + /** Reconstructs path by following parent nodes. */ private List reconstructPath(Node node) { List path = new ArrayList<>(); while (node != null) { From d1f5c2168c12953658719d910d28d9a6914ec755 Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 20:21:06 +0530 Subject: [PATCH 05/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 33 +++++++++++-------- 1 file changed, 19 insertions(+), 14 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index a4a38d9a99c2..24febc2ab1f7 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -6,7 +6,7 @@ * A* Search Algorithm for shortest pathfinding. * *

Commonly used in games, navigation, and robotics. - * Combines Dijkstra’s Algorithm and heuristic estimation.

+ * Combines Dijkstra's Algorithm and heuristic estimation.

* *

Reference: https://en.wikipedia.org/wiki/A*_search_algorithm

*/ @@ -14,9 +14,9 @@ public class AStarSearch { static class Node implements Comparable { int id; - double g; // Cost from start - double h; // Heuristic to goal - double f; // Total cost = g + h + double g; // cost from start + double h; // heuristic to goal + double f; // total cost = g + h Node parent; Node(int id, double g, double h, Node parent) { @@ -28,8 +28,8 @@ static class Node implements Comparable { } @Override - public int compareTo(Node o) { - return Double.compare(this.f, o.f); + public int compareTo(Node other) { + return Double.compare(this.f, other.f); } } @@ -39,13 +39,17 @@ public AStarSearch() { graph = new HashMap<>(); } - /** Adds an undirected edge between nodes u and v with the given weight. */ + /** + * Adds an undirected edge between nodes u and v with the given weight. + */ public void addEdge(int u, int v, int weight) { - graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); - graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); + graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[] {v, weight}); + graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[] {u, weight}); } - /** Heuristic function (simplified for numeric nodes). */ + /** + * Heuristic function (simplified for numeric nodes). + */ private double heuristic(int node, int goal) { return Math.abs(goal - node); } @@ -54,7 +58,7 @@ private double heuristic(int node, int goal) { * Finds the shortest path from start to goal using A* algorithm. * * @param start starting node - * @param goal goal node + * @param goal goal node * @return list of nodes representing the shortest path */ public List findPath(int start, int goal) { @@ -74,7 +78,7 @@ public List findPath(int start, int goal) { closedSet.add(current.id); - for (int[] edge : graph.getOrDefault(current.id, new ArrayList<>())) { + for (int[] edge : graph.getOrDefault(current.id, Collections.emptyList())) { int neighbor = edge[0]; double tentativeG = current.g + edge[1]; @@ -89,11 +93,12 @@ public List findPath(int start, int goal) { } } } - return Collections.emptyList(); } - /** Reconstructs path by following parent nodes. */ + /** + * Reconstructs path by following parent nodes. + */ private List reconstructPath(Node node) { List path = new ArrayList<>(); while (node != null) { From 6f2a51071e371078ff9eefa9c341a8f17b832c90 Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 20:25:41 +0530 Subject: [PATCH 06/13] Update AStarSearch.java --- src/main/java/com/thealgorithms/graph/AStarSearch.java | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index 24febc2ab1f7..fa63706e990a 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -2,6 +2,15 @@ import java.util.*; +import java.util.ArrayList; +import java.util.Collections; +import java.util.HashMap; +import java.util.HashSet; +import java.util.List; +import java.util.Map; +import java.util.PriorityQueue; +import java.util.Set; + /** * A* Search Algorithm for shortest pathfinding. * From e813c12fd92b1eba07c4701d1915b4126a214b5f Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 20:29:47 +0530 Subject: [PATCH 07/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 54 +++++++++++++++---- 1 file changed, 43 insertions(+), 11 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index fa63706e990a..59b5fc50b2c8 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -1,7 +1,5 @@ package com.thealgorithms.graph; -import java.util.*; - import java.util.ArrayList; import java.util.Collections; import java.util.HashMap; @@ -9,13 +7,14 @@ import java.util.List; import java.util.Map; import java.util.PriorityQueue; +import java.util.Scanner; import java.util.Set; /** * A* Search Algorithm for shortest pathfinding. * *

Commonly used in games, navigation, and robotics. - * Combines Dijkstra's Algorithm and heuristic estimation.

+ * Combines Dijkstra’s Algorithm and heuristic estimation.

* *

Reference: https://en.wikipedia.org/wiki/A*_search_algorithm

*/ @@ -23,9 +22,9 @@ public class AStarSearch { static class Node implements Comparable { int id; - double g; // cost from start - double h; // heuristic to goal - double f; // total cost = g + h + double g; // Cost from start + double h; // Heuristic to goal + double f; // Total cost = g + h Node parent; Node(int id, double g, double h, Node parent) { @@ -37,8 +36,8 @@ static class Node implements Comparable { } @Override - public int compareTo(Node other) { - return Double.compare(this.f, other.f); + public int compareTo(Node o) { + return Double.compare(this.f, o.f); } } @@ -52,8 +51,8 @@ public AStarSearch() { * Adds an undirected edge between nodes u and v with the given weight. */ public void addEdge(int u, int v, int weight) { - graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[] {v, weight}); - graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[] {u, weight}); + graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); + graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); } /** @@ -67,7 +66,7 @@ private double heuristic(int node, int goal) { * Finds the shortest path from start to goal using A* algorithm. * * @param start starting node - * @param goal goal node + * @param goal goal node * @return list of nodes representing the shortest path */ public List findPath(int start, int goal) { @@ -117,4 +116,37 @@ private List reconstructPath(Node node) { Collections.reverse(path); return path; } + + /** + * Dynamic usage: reads graph and start/goal from input. + */ + public static void main(String[] args) { + Scanner sc = new Scanner(System.in); + AStarSearch aStar = new AStarSearch(); + + System.out.print("Enter number of edges: "); + int edges = sc.nextInt(); + + System.out.println("Enter edges in format: u v weight"); + for (int i = 0; i < edges; i++) { + int u = sc.nextInt(); + int v = sc.nextInt(); + int w = sc.nextInt(); + aStar.addEdge(u, v, w); + } + + System.out.print("Enter start node: "); + int start = sc.nextInt(); + + System.out.print("Enter goal node: "); + int goal = sc.nextInt(); + + List path = aStar.findPath(start, goal); + if (path.isEmpty()) { + System.out.println("No path found from " + start + " → " + goal); + } else { + System.out.println("Shortest path from " + start + " → " + goal + ": " + path); + } + sc.close(); + } } From 8aec567ee4e975f1d1c38ea1f84aecb082660e78 Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 20:36:29 +0530 Subject: [PATCH 08/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 172 ++++++++++-------- 1 file changed, 101 insertions(+), 71 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index 59b5fc50b2c8..c349f1ee8f30 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -1,31 +1,92 @@ package com.thealgorithms.graph; import java.util.ArrayList; -import java.util.Collections; import java.util.HashMap; -import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.PriorityQueue; -import java.util.Scanner; import java.util.Set; +import java.util.HashSet; +import java.util.Collections; /** - * A* Search Algorithm for shortest pathfinding. + * Implementation of the A* Search Algorithm for shortest pathfinding. + * + *

+ * A* combines Dijkstra’s algorithm with a heuristic to efficiently find the + * shortest path in weighted graphs. + *

+ * + *

+ * Reference: https://en.wikipedia.org/wiki/A*_search_algorithm + *

* - *

Commonly used in games, navigation, and robotics. - * Combines Dijkstra’s Algorithm and heuristic estimation.

+ *

+ * Time Complexity: O(E + V log V) with a binary heap priority queue.
+ * Space Complexity: O(V + E). + *

* - *

Reference: https://en.wikipedia.org/wiki/A*_search_algorithm

+ *

+ * Usage is intended programmatically via the {@link Graph} and {@link #findPath} + * method; interactive input should be handled externally or via tests. + *

*/ public class AStarSearch { - static class Node implements Comparable { - int id; - double g; // Cost from start - double h; // Heuristic to goal - double f; // Total cost = g + h - Node parent; + /** + * Represents a weighted directed graph using adjacency lists. + */ + public static class Graph { + private final Map> adjacencyList; + + /** + * Constructs an empty graph. + */ + public Graph() { + adjacencyList = new HashMap<>(); + } + + /** + * Adds an undirected edge between nodes {@code u} and {@code v} with a weight. + * + * @param u first node + * @param v second node + * @param weight weight of the edge + */ + public void addEdge(int u, int v, int weight) { + adjacencyList.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[] { v, weight }); + adjacencyList.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[] { u, weight }); + } + + /** + * Returns the adjacency list for a node. + * + * @param node node index + * @return list of int[] {neighbor, weight} + */ + public List getEdges(int node) { + return adjacencyList.getOrDefault(node, Collections.emptyList()); + } + + /** + * Returns all nodes in the graph. + * + * @return set of node indices + */ + public Set getNodes() { + return adjacencyList.keySet(); + } + } + + /** + * Node used in the priority queue for A*. + */ + private static class Node implements Comparable { + final int id; + final double g; // cost from start + final double h; // heuristic + final double f; // total = g + h + final Node parent; Node(int id, double g, double h, Node parent) { this.id = id; @@ -41,33 +102,23 @@ public int compareTo(Node o) { } } - private final Map> graph; - - public AStarSearch() { - graph = new HashMap<>(); - } + private final Graph graph; /** - * Adds an undirected edge between nodes u and v with the given weight. - */ - public void addEdge(int u, int v, int weight) { - graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); - graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); - } - - /** - * Heuristic function (simplified for numeric nodes). + * Constructs an A* solver for a given graph. + * + * @param graph weighted graph */ - private double heuristic(int node, int goal) { - return Math.abs(goal - node); + public AStarSearch(Graph graph) { + this.graph = graph; } /** - * Finds the shortest path from start to goal using A* algorithm. + * Finds the shortest path from {@code start} to {@code goal} using A* search. * * @param start starting node * @param goal goal node - * @return list of nodes representing the shortest path + * @return list of nodes representing the shortest path, empty if none */ public List findPath(int start, int goal) { PriorityQueue openSet = new PriorityQueue<>(); @@ -86,26 +137,38 @@ public List findPath(int start, int goal) { closedSet.add(current.id); - for (int[] edge : graph.getOrDefault(current.id, Collections.emptyList())) { + for (int[] edge : graph.getEdges(current.id)) { int neighbor = edge[0]; double tentativeG = current.g + edge[1]; - if (closedSet.contains(neighbor)) { - continue; - } + if (closedSet.contains(neighbor)) continue; if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { gScore.put(neighbor, tentativeG); - Node next = new Node(neighbor, tentativeG, heuristic(neighbor, goal), current); - openSet.add(next); + openSet.add(new Node(neighbor, tentativeG, heuristic(neighbor, goal), current)); } } } + return Collections.emptyList(); } /** - * Reconstructs path by following parent nodes. + * Simple heuristic: absolute difference between node indices. + * + * @param node current node + * @param goal goal node + * @return heuristic value + */ + private double heuristic(int node, int goal) { + return Math.abs(goal - node); + } + + /** + * Reconstructs the path from goal to start following parent links. + * + * @param node end node + * @return list of node indices from start to goal */ private List reconstructPath(Node node) { List path = new ArrayList<>(); @@ -116,37 +179,4 @@ private List reconstructPath(Node node) { Collections.reverse(path); return path; } - - /** - * Dynamic usage: reads graph and start/goal from input. - */ - public static void main(String[] args) { - Scanner sc = new Scanner(System.in); - AStarSearch aStar = new AStarSearch(); - - System.out.print("Enter number of edges: "); - int edges = sc.nextInt(); - - System.out.println("Enter edges in format: u v weight"); - for (int i = 0; i < edges; i++) { - int u = sc.nextInt(); - int v = sc.nextInt(); - int w = sc.nextInt(); - aStar.addEdge(u, v, w); - } - - System.out.print("Enter start node: "); - int start = sc.nextInt(); - - System.out.print("Enter goal node: "); - int goal = sc.nextInt(); - - List path = aStar.findPath(start, goal); - if (path.isEmpty()) { - System.out.println("No path found from " + start + " → " + goal); - } else { - System.out.println("Shortest path from " + start + " → " + goal + ": " + path); - } - sc.close(); - } } From e400522f46c9a1c35179bd40c80fb459dbc6d1fd Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 20:41:49 +0530 Subject: [PATCH 09/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 165 ++++++++---------- 1 file changed, 74 insertions(+), 91 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index c349f1ee8f30..6f09286e1a90 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -1,13 +1,14 @@ package com.thealgorithms.graph; import java.util.ArrayList; +import java.util.Collections; import java.util.HashMap; +import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.PriorityQueue; import java.util.Set; -import java.util.HashSet; -import java.util.Collections; +import java.util.Scanner; /** * Implementation of the A* Search Algorithm for shortest pathfinding. @@ -23,70 +24,17 @@ * *

* Time Complexity: O(E + V log V) with a binary heap priority queue.
- * Space Complexity: O(V + E). - *

- * - *

- * Usage is intended programmatically via the {@link Graph} and {@link #findPath} - * method; interactive input should be handled externally or via tests. + * Space Complexity: O(V + E) *

*/ public class AStarSearch { - /** - * Represents a weighted directed graph using adjacency lists. - */ - public static class Graph { - private final Map> adjacencyList; - - /** - * Constructs an empty graph. - */ - public Graph() { - adjacencyList = new HashMap<>(); - } - - /** - * Adds an undirected edge between nodes {@code u} and {@code v} with a weight. - * - * @param u first node - * @param v second node - * @param weight weight of the edge - */ - public void addEdge(int u, int v, int weight) { - adjacencyList.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[] { v, weight }); - adjacencyList.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[] { u, weight }); - } - - /** - * Returns the adjacency list for a node. - * - * @param node node index - * @return list of int[] {neighbor, weight} - */ - public List getEdges(int node) { - return adjacencyList.getOrDefault(node, Collections.emptyList()); - } - - /** - * Returns all nodes in the graph. - * - * @return set of node indices - */ - public Set getNodes() { - return adjacencyList.keySet(); - } - } - - /** - * Node used in the priority queue for A*. - */ private static class Node implements Comparable { - final int id; - final double g; // cost from start - final double h; // heuristic - final double f; // total = g + h - final Node parent; + int id; + double g; // cost from start + double h; // heuristic to goal + double f; // total cost = g + h + Node parent; Node(int id, double g, double h, Node parent) { this.id = id; @@ -97,28 +45,47 @@ private static class Node implements Comparable { } @Override - public int compareTo(Node o) { - return Double.compare(this.f, o.f); + public int compareTo(Node other) { + return Double.compare(this.f, other.f); } } - private final Graph graph; + private final Map> graph; + + /** Constructs an empty graph. */ + public AStarSearch() { + graph = new HashMap<>(); + } + + /** + * Adds an undirected edge between nodes u and v with the given weight. + * + * @param u first node + * @param v second node + * @param weight edge weight + */ + public void addEdge(int u, int v, int weight) { + graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); + graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); + } /** - * Constructs an A* solver for a given graph. + * Heuristic function for A* (simplified as absolute difference). * - * @param graph weighted graph + * @param node current node + * @param goal goal node + * @return heuristic estimate */ - public AStarSearch(Graph graph) { - this.graph = graph; + private double heuristic(int node, int goal) { + return Math.abs(goal - node); } /** - * Finds the shortest path from {@code start} to {@code goal} using A* search. + * Finds the shortest path from start to goal using A* algorithm. * - * @param start starting node - * @param goal goal node - * @return list of nodes representing the shortest path, empty if none + * @param start start node + * @param goal goal node + * @return list of nodes representing the shortest path */ public List findPath(int start, int goal) { PriorityQueue openSet = new PriorityQueue<>(); @@ -130,18 +97,17 @@ public List findPath(int start, int goal) { while (!openSet.isEmpty()) { Node current = openSet.poll(); - if (current.id == goal) { return reconstructPath(current); } closedSet.add(current.id); - - for (int[] edge : graph.getEdges(current.id)) { + for (int[] edge : graph.getOrDefault(current.id, new ArrayList<>())) { int neighbor = edge[0]; double tentativeG = current.g + edge[1]; - - if (closedSet.contains(neighbor)) continue; + if (closedSet.contains(neighbor)) { + continue; + } if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { gScore.put(neighbor, tentativeG); @@ -149,26 +115,14 @@ public List findPath(int start, int goal) { } } } - return Collections.emptyList(); } /** - * Simple heuristic: absolute difference between node indices. - * - * @param node current node - * @param goal goal node - * @return heuristic value - */ - private double heuristic(int node, int goal) { - return Math.abs(goal - node); - } - - /** - * Reconstructs the path from goal to start following parent links. + * Reconstructs the path by following parent nodes. * * @param node end node - * @return list of node indices from start to goal + * @return path from start to end */ private List reconstructPath(Node node) { List path = new ArrayList<>(); @@ -179,4 +133,33 @@ private List reconstructPath(Node node) { Collections.reverse(path); return path; } + + /** Reads input dynamically and runs A* algorithm. */ + public static void main(String[] args) { + Scanner sc = new Scanner(System.in); + AStarSearch aStar = new AStarSearch(); + + System.out.print("Enter number of edges: "); + int edges = sc.nextInt(); + System.out.println("Enter edges in format: u v weight"); + for (int i = 0; i < edges; i++) { + int u = sc.nextInt(); + int v = sc.nextInt(); + int w = sc.nextInt(); + aStar.addEdge(u, v, w); + } + + System.out.print("Enter start node: "); + int start = sc.nextInt(); + System.out.print("Enter goal node: "); + int goal = sc.nextInt(); + + List path = aStar.findPath(start, goal); + if (path.isEmpty()) { + System.out.println("No path found from " + start + " → " + goal); + } else { + System.out.println("Shortest path from " + start + " → " + goal + ": " + path); + } + sc.close(); + } } From 1190b987f7d07314dd66ec64df62765cf311a0bf Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 20:48:42 +0530 Subject: [PATCH 10/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 24 +++++++++---------- 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index 6f09286e1a90..d26728f18666 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -1,4 +1,4 @@ -package com.thealgorithms.graph; +package com.thealgorithms.graphs; import java.util.ArrayList; import java.util.Collections; @@ -7,14 +7,14 @@ import java.util.List; import java.util.Map; import java.util.PriorityQueue; -import java.util.Set; import java.util.Scanner; +import java.util.Set; /** - * Implementation of the A* Search Algorithm for shortest pathfinding. + * Implementation of the A* Search Algorithm for shortest path finding. * *

- * A* combines Dijkstra’s algorithm with a heuristic to efficiently find the + * A* combines Dijkstra's algorithm with a heuristic to efficiently find the * shortest path in weighted graphs. *

* @@ -23,18 +23,18 @@ *

* *

- * Time Complexity: O(E + V log V) with a binary heap priority queue.
+ * Time Complexity: O(E + V log V) with a binary heap priority queue. * Space Complexity: O(V + E) *

*/ public class AStarSearch { private static class Node implements Comparable { - int id; - double g; // cost from start - double h; // heuristic to goal - double f; // total cost = g + h - Node parent; + private final int id; + private final double g; // cost from start + private final double h; // heuristic to goal + private final double f; // total cost = g + h + private final Node parent; Node(int id, double g, double h, Node parent) { this.id = id; @@ -65,8 +65,8 @@ public AStarSearch() { * @param weight edge weight */ public void addEdge(int u, int v, int weight) { - graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[]{v, weight}); - graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[]{u, weight}); + graph.computeIfAbsent(u, k -> new ArrayList<>()).add(new int[] {v, weight}); + graph.computeIfAbsent(v, k -> new ArrayList<>()).add(new int[] {u, weight}); } /** From 6a307fa9df85adf2b2178f5eccf6da42f48f37bb Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 21:19:43 +0530 Subject: [PATCH 11/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 55 +++++++++++-------- 1 file changed, 33 insertions(+), 22 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index d26728f18666..cdd55848bd8e 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -27,26 +27,26 @@ * Space Complexity: O(V + E) *

*/ -public class AStarSearch { +public final class AStarSearch { - private static class Node implements Comparable { + private static final class Node implements Comparable { private final int id; - private final double g; // cost from start - private final double h; // heuristic to goal - private final double f; // total cost = g + h + private final double costFromStart; + private final double heuristicCost; + private final double totalCost; private final Node parent; - Node(int id, double g, double h, Node parent) { + Node(int id, double costFromStart, double heuristicCost, Node parent) { this.id = id; - this.g = g; - this.h = h; - this.f = g + h; + this.costFromStart = costFromStart; + this.heuristicCost = heuristicCost; + this.totalCost = costFromStart + heuristicCost; this.parent = parent; } @Override public int compareTo(Node other) { - return Double.compare(this.f, other.f); + return Double.compare(this.totalCost, other.totalCost); } } @@ -72,12 +72,12 @@ public void addEdge(int u, int v, int weight) { /** * Heuristic function for A* (simplified as absolute difference). * - * @param node current node - * @param goal goal node + * @param currentNode current node + * @param goalNode goal node * @return heuristic estimate */ - private double heuristic(int node, int goal) { - return Math.abs(goal - node); + private double heuristic(int currentNode, int goalNode) { + return Math.abs(goalNode - currentNode); } /** @@ -102,16 +102,22 @@ public List findPath(int start, int goal) { } closedSet.add(current.id); - for (int[] edge : graph.getOrDefault(current.id, new ArrayList<>())) { + + List edges = graph.getOrDefault(current.id, Collections.emptyList()); + for (int[] edge : edges) { int neighbor = edge[0]; - double tentativeG = current.g + edge[1]; + double edgeWeight = edge[1]; + double tentativeG = current.costFromStart + edgeWeight; + if (closedSet.contains(neighbor)) { continue; } - if (tentativeG < gScore.getOrDefault(neighbor, Double.MAX_VALUE)) { + double currentGScore = gScore.getOrDefault(neighbor, Double.MAX_VALUE); + if (tentativeG < currentGScore) { gScore.put(neighbor, tentativeG); - openSet.add(new Node(neighbor, tentativeG, heuristic(neighbor, goal), current)); + double neighborHeuristic = heuristic(neighbor, goal); + openSet.add(new Node(neighbor, tentativeG, neighborHeuristic, current)); } } } @@ -126,15 +132,20 @@ public List findPath(int start, int goal) { */ private List reconstructPath(Node node) { List path = new ArrayList<>(); - while (node != null) { - path.add(node.id); - node = node.parent; + Node current = node; + while (current != null) { + path.add(current.id); + current = current.parent; } Collections.reverse(path); return path; } - /** Reads input dynamically and runs A* algorithm. */ + /** + * Main method to demonstrate A* algorithm with user input. + * + * @param args command line arguments + */ public static void main(String[] args) { Scanner sc = new Scanner(System.in); AStarSearch aStar = new AStarSearch(); From 2da1d4fbe2419b604a3343cfe13db3ee1fdf3c4b Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 21:31:00 +0530 Subject: [PATCH 12/13] Update AStarSearch.java --- .../com/thealgorithms/graph/AStarSearch.java | 78 ++++++------------- 1 file changed, 25 insertions(+), 53 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index cdd55848bd8e..88fe4268b7c1 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -7,28 +7,19 @@ import java.util.List; import java.util.Map; import java.util.PriorityQueue; -import java.util.Scanner; import java.util.Set; /** * Implementation of the A* Search Algorithm for shortest path finding. * - *

- * A* combines Dijkstra's algorithm with a heuristic to efficiently find the - * shortest path in weighted graphs. - *

- * - *

- * Reference: https://en.wikipedia.org/wiki/A*_search_algorithm - *

- * - *

- * Time Complexity: O(E + V log V) with a binary heap priority queue. - * Space Complexity: O(V + E) - *

+ * @author Your Name + * @version 1.0 */ -public final class AStarSearch { +public final class AStar { + /** + * Represents a node in the graph for A* algorithm. + */ private static final class Node implements Comparable { private final int id; private final double costFromStart; @@ -36,6 +27,14 @@ private static final class Node implements Comparable { private final double totalCost; private final Node parent; + /** + * Constructs a new Node. + * + * @param id the node identifier + * @param costFromStart the cost from start node to this node + * @param heuristicCost the heuristic cost from this node to goal + * @param parent the parent node + */ Node(int id, double costFromStart, double heuristicCost, Node parent) { this.id = id; this.costFromStart = costFromStart; @@ -52,8 +51,10 @@ public int compareTo(Node other) { private final Map> graph; - /** Constructs an empty graph. */ - public AStarSearch() { + /** + * Constructs an empty graph. + */ + public AStar() { graph = new HashMap<>(); } @@ -88,11 +89,15 @@ private double heuristic(int currentNode, int goalNode) { * @return list of nodes representing the shortest path */ public List findPath(int start, int goal) { + if (start == goal) { + return List.of(start); + } + PriorityQueue openSet = new PriorityQueue<>(); Map gScore = new HashMap<>(); Set closedSet = new HashSet<>(); - openSet.add(new Node(start, 0, heuristic(start, goal), null)); + openSet.add(new Node(start, 0.0, heuristic(start, goal), null)); gScore.put(start, 0.0); while (!openSet.isEmpty()) { @@ -102,13 +107,13 @@ public List findPath(int start, int goal) { } closedSet.add(current.id); - + List edges = graph.getOrDefault(current.id, Collections.emptyList()); for (int[] edge : edges) { int neighbor = edge[0]; double edgeWeight = edge[1]; double tentativeG = current.costFromStart + edgeWeight; - + if (closedSet.contains(neighbor)) { continue; } @@ -140,37 +145,4 @@ private List reconstructPath(Node node) { Collections.reverse(path); return path; } - - /** - * Main method to demonstrate A* algorithm with user input. - * - * @param args command line arguments - */ - public static void main(String[] args) { - Scanner sc = new Scanner(System.in); - AStarSearch aStar = new AStarSearch(); - - System.out.print("Enter number of edges: "); - int edges = sc.nextInt(); - System.out.println("Enter edges in format: u v weight"); - for (int i = 0; i < edges; i++) { - int u = sc.nextInt(); - int v = sc.nextInt(); - int w = sc.nextInt(); - aStar.addEdge(u, v, w); - } - - System.out.print("Enter start node: "); - int start = sc.nextInt(); - System.out.print("Enter goal node: "); - int goal = sc.nextInt(); - - List path = aStar.findPath(start, goal); - if (path.isEmpty()) { - System.out.println("No path found from " + start + " → " + goal); - } else { - System.out.println("Shortest path from " + start + " → " + goal + ": " + path); - } - sc.close(); - } } From dcf16aca0d7b9b52fd4b9af0e54855a2fb8d0c50 Mon Sep 17 00:00:00 2001 From: Bhoomika Marigoudar <148475967+bhoomika1714@users.noreply.github.com> Date: Wed, 29 Oct 2025 21:43:20 +0530 Subject: [PATCH 13/13] Update AStarSearch.java --- src/main/java/com/thealgorithms/graph/AStarSearch.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/com/thealgorithms/graph/AStarSearch.java b/src/main/java/com/thealgorithms/graph/AStarSearch.java index 88fe4268b7c1..52c0b822bec7 100644 --- a/src/main/java/com/thealgorithms/graph/AStarSearch.java +++ b/src/main/java/com/thealgorithms/graph/AStarSearch.java @@ -15,7 +15,7 @@ * @author Your Name * @version 1.0 */ -public final class AStar { +public final class AStarSearch { /** * Represents a node in the graph for A* algorithm. @@ -54,7 +54,7 @@ public int compareTo(Node other) { /** * Constructs an empty graph. */ - public AStar() { + public AStarSearch() { graph = new HashMap<>(); }