From 600578803fb2cf7e6e09a01ebaa3c368d13dec10 Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 20:59:10 +0530 Subject: [PATCH 01/10] Optimized NQueens implementation using hashing --- .../thealgorithms/backtracking/NQueens.java | 72 +++++++++++-------- 1 file changed, 44 insertions(+), 28 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index 1a8e453e34cb..1ae354a2e0cc 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -2,6 +2,8 @@ import java.util.ArrayList; import java.util.List; +import java.util.HashSet; +import java.util.Set; /** * Problem statement: Given a N x N chess board. Return all arrangements in @@ -32,7 +34,22 @@ * queen is not placed safely. If there is no such way then return an empty list * as solution */ + +/* + * Time Complexity: O(N!) + * space Complexity: O(N) + */ public final class NQueens { + + // Store occupied rows for constant time safety check + private static final Set occupiedRows = new HashSet<>(); + + // Store occupied main diagonals (row - column) + private static final Set occupiedDiagonals = new HashSet<>(); + + // Store occupied anti-diagonals (row + columns) + private static final Set occupiedAntiDiagonals = new HashSet<>(); + private NQueens() { } @@ -43,10 +60,11 @@ public static List> getNQueensArrangements(int queens) { } public static void placeQueens(final int queens) { - List> arrangements = new ArrayList>(); + List> arrangements = new ArrayList<>(); getSolution(queens, arrangements, new int[queens], 0); if (arrangements.isEmpty()) { - System.out.println("There is no way to place " + queens + " queens on board of size " + queens + "x" + queens); + System.out.println( + "There is no way to place " + queens + " queens on board of size " + queens + "x" + queens); } else { System.out.println("Arrangement for placing " + queens + " queens"); } @@ -59,15 +77,15 @@ public static void placeQueens(final int queens) { /** * This is backtracking function which tries to place queen recursively * - * @param boardSize: size of chess board - * @param solutions: this holds all possible arrangements - * @param columns: columns[i] = rowId where queen is placed in ith column. + * @param boardSize: size of chess board + * @param solutions: this holds all possible arrangements + * @param columns: columns[i] = rowId where queen is placed in ith column. * @param columnIndex: This is the column in which queen is being placed */ private static void getSolution(int boardSize, List> solutions, int[] columns, int columnIndex) { if (columnIndex == boardSize) { // this means that all queens have been placed - List sol = new ArrayList(); + List sol = new ArrayList<>(); for (int i = 0; i < boardSize; i++) { StringBuilder sb = new StringBuilder(); for (int j = 0; j < boardSize; j++) { @@ -82,30 +100,28 @@ private static void getSolution(int boardSize, List> solutions, int // This loop tries to place queen in a row one by one for (int rowIndex = 0; rowIndex < boardSize; rowIndex++) { columns[columnIndex] = rowIndex; - if (isPlacedCorrectly(columns, rowIndex, columnIndex)) { - // If queen is placed successfully at rowIndex in column=columnIndex then try - // placing queen in next column - getSolution(boardSize, solutions, columns, columnIndex + 1); - } - } - } - /** - * This function checks if queen can be placed at row = rowIndex in column = - * columnIndex safely - * - * @param columns: columns[i] = rowId where queen is placed in ith column. - * @param rowIndex: row in which queen has to be placed - * @param columnIndex: column in which queen is being placed - * @return true: if queen can be placed safely false: otherwise - */ - private static boolean isPlacedCorrectly(int[] columns, int rowIndex, int columnIndex) { - for (int i = 0; i < columnIndex; i++) { - int diff = Math.abs(columns[i] - rowIndex); - if (diff == 0 || columnIndex - i == diff) { - return false; + // Skip current position if row or diagonal is already occupied + if (occupiedRows.contains(rowIndex) + || occupiedDiagonals.contains(rowIndex - columnIndex) + || occupiedAntiDiagonals.contains(rowIndex + columnIndex)) { + continue; } + + // Mark current row and diagonal as occupied + occupiedRows.add(rowIndex); + occupiedDiagonals.add(rowIndex - columnIndex); + occupiedAntiDiagonals.add(rowIndex + columnIndex); + + // Move to the next column after placing current queen + getSolution(boardSize, solutions, columns, columnIndex + 1); + + // Backtrack by removing current queen + + occupiedRows.remove(rowIndex); + occupiedDiagonals.remove(rowIndex - columnIndex); + occupiedAntiDiagonals.remove(rowIndex + columnIndex); } - return true; } + } From 5f30250b9d72f1ac927276eb3fe5b8b8f77a1143 Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 21:24:37 +0530 Subject: [PATCH 02/10] Fixed checkstyle naming issues --- .../thealgorithms/backtracking/NQueens.java | 25 ++++++++++--------- 1 file changed, 13 insertions(+), 12 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index 1ae354a2e0cc..8020e1900db1 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -42,13 +42,13 @@ public final class NQueens { // Store occupied rows for constant time safety check - private static final Set occupiedRows = new HashSet<>(); + private static final Set OCCUPIED_ROWS = new HashSet<>(); // Store occupied main diagonals (row - column) - private static final Set occupiedDiagonals = new HashSet<>(); + private static final Set OCCUPIED_DIAGONALS = new HashSet<>(); // Store occupied anti-diagonals (row + columns) - private static final Set occupiedAntiDiagonals = new HashSet<>(); + private static final Set OCCUPIED_ANTI_DIAGONALS = new HashSet<>(); private NQueens() { } @@ -102,25 +102,26 @@ private static void getSolution(int boardSize, List> solutions, int columns[columnIndex] = rowIndex; // Skip current position if row or diagonal is already occupied - if (occupiedRows.contains(rowIndex) - || occupiedDiagonals.contains(rowIndex - columnIndex) - || occupiedAntiDiagonals.contains(rowIndex + columnIndex)) { + if (OCCUPIED_ROWS + .contains(rowIndex) + || OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) + || OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { continue; } // Mark current row and diagonal as occupied - occupiedRows.add(rowIndex); - occupiedDiagonals.add(rowIndex - columnIndex); - occupiedAntiDiagonals.add(rowIndex + columnIndex); + OCCUPIED_ROWS.add(rowIndex); + OCCUPIED_DIAGONALS.add(rowIndex - columnIndex); + OCCUPIED_ANTI_DIAGONALS.add(rowIndex + columnIndex); // Move to the next column after placing current queen getSolution(boardSize, solutions, columns, columnIndex + 1); // Backtrack by removing current queen - occupiedRows.remove(rowIndex); - occupiedDiagonals.remove(rowIndex - columnIndex); - occupiedAntiDiagonals.remove(rowIndex + columnIndex); + OCCUPIED_ROWS.remove(rowIndex); + OCCUPIED_DIAGONALS.remove(rowIndex - columnIndex); + OCCUPIED_ANTI_DIAGONALS.remove(rowIndex + columnIndex); } } From d6fea9b552fdba2942a75b3974af8ff9f8ffac62 Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 21:43:32 +0530 Subject: [PATCH 03/10] Fixed formatting issues --- .../com/thealgorithms/backtracking/NQueens.java | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index 8020e1900db1..7942313e1904 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -1,8 +1,8 @@ package com.thealgorithms.backtracking; import java.util.ArrayList; -import java.util.List; import java.util.HashSet; +import java.util.List; import java.util.Set; /** @@ -63,8 +63,8 @@ public static void placeQueens(final int queens) { List> arrangements = new ArrayList<>(); getSolution(queens, arrangements, new int[queens], 0); if (arrangements.isEmpty()) { - System.out.println( - "There is no way to place " + queens + " queens on board of size " + queens + "x" + queens); + System.out.println("There is no way to place " + queens + " queens on board of size " + + queens + "x" + queens); } else { System.out.println("Arrangement for placing " + queens + " queens"); } @@ -102,10 +102,9 @@ private static void getSolution(int boardSize, List> solutions, int columns[columnIndex] = rowIndex; // Skip current position if row or diagonal is already occupied - if (OCCUPIED_ROWS - .contains(rowIndex) - || OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) - || OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { + if (OCCUPIED_ROWS.contains(rowIndex) || + OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) || + OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { continue; } From 0761aa5452b46c88d38ef93e0adc150a7bb3a3f3 Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 21:48:20 +0530 Subject: [PATCH 04/10] Fixed operator wrap formatting --- src/main/java/com/thealgorithms/backtracking/NQueens.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index 7942313e1904..289b8f5def19 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -102,9 +102,9 @@ private static void getSolution(int boardSize, List> solutions, int columns[columnIndex] = rowIndex; // Skip current position if row or diagonal is already occupied - if (OCCUPIED_ROWS.contains(rowIndex) || - OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) || - OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { + if (OCCUPIED_ROWS.contains(rowIndex) + || OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) + || OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { continue; } From 0fc3e091db518dbce42fb1f6d64635eb75111409 Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 21:52:35 +0530 Subject: [PATCH 05/10] Fixed formatting issues --- .../java/com/thealgorithms/backtracking/NQueens.java | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index 289b8f5def19..0bb682826b6d 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -63,8 +63,8 @@ public static void placeQueens(final int queens) { List> arrangements = new ArrayList<>(); getSolution(queens, arrangements, new int[queens], 0); if (arrangements.isEmpty()) { - System.out.println("There is no way to place " + queens + " queens on board of size " - + queens + "x" + queens); + System.out.println( + "There is no way to place " + queens + " queens on board of size " + queens + "x" + queens); } else { System.out.println("Arrangement for placing " + queens + " queens"); } @@ -102,9 +102,9 @@ private static void getSolution(int boardSize, List> solutions, int columns[columnIndex] = rowIndex; // Skip current position if row or diagonal is already occupied - if (OCCUPIED_ROWS.contains(rowIndex) - || OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) - || OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { + if (OCCUPIED_ROWS.contains(rowIndex) || + OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) || + OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { continue; } From aaad158e499bf9dbb2a6147314d30f852a6c256a Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 21:57:14 +0530 Subject: [PATCH 06/10] Fixed operator wrapping style --- src/main/java/com/thealgorithms/backtracking/NQueens.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index 0bb682826b6d..dbe6ef008504 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -102,9 +102,9 @@ private static void getSolution(int boardSize, List> solutions, int columns[columnIndex] = rowIndex; // Skip current position if row or diagonal is already occupied - if (OCCUPIED_ROWS.contains(rowIndex) || - OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) || - OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { + if (OCCUPIED_ROWS.contains(rowIndex) + || OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) + || OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { continue; } From e085d1015b82e22a767174fb9c0905bf45c12bd5 Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 22:14:18 +0530 Subject: [PATCH 07/10] Fixed print formatting --- src/main/java/com/thealgorithms/backtracking/NQueens.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index dbe6ef008504..0578ab847892 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -63,8 +63,7 @@ public static void placeQueens(final int queens) { List> arrangements = new ArrayList<>(); getSolution(queens, arrangements, new int[queens], 0); if (arrangements.isEmpty()) { - System.out.println( - "There is no way to place " + queens + " queens on board of size " + queens + "x" + queens); + System.out.println(" no way to place " + queens + " queens on board of size " + queens + "x" + queens); } else { System.out.println("Arrangement for placing " + queens + " queens"); } From 3c5d1bdedfebb79a8f7cae2294021558c7a23b95 Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 22:18:08 +0530 Subject: [PATCH 08/10] Fixed print formatting --- src/main/java/com/thealgorithms/backtracking/NQueens.java | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index 0578ab847892..b6385959bbce 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -101,9 +101,8 @@ private static void getSolution(int boardSize, List> solutions, int columns[columnIndex] = rowIndex; // Skip current position if row or diagonal is already occupied - if (OCCUPIED_ROWS.contains(rowIndex) - || OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) - || OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { + if (OCCUPIED_ROWS.contains(rowIndex) || OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) || + OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { continue; } From db9980d18b124e3b08f0396417297c4ca9cbe129 Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 22:31:59 +0530 Subject: [PATCH 09/10] Fixed operator formatting --- .../thealgorithms/backtracking/NQueens.java | 25 +++++++++++-------- 1 file changed, 14 insertions(+), 11 deletions(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index b6385959bbce..3243f6f4752c 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -42,13 +42,13 @@ public final class NQueens { // Store occupied rows for constant time safety check - private static final Set OCCUPIED_ROWS = new HashSet<>(); + private static final Set OCROWS = new HashSet<>(); // Store occupied main diagonals (row - column) - private static final Set OCCUPIED_DIAGONALS = new HashSet<>(); + private static final Set OCDIAG = new HashSet<>(); // Store occupied anti-diagonals (row + columns) - private static final Set OCCUPIED_ANTI_DIAGONALS = new HashSet<>(); + private static final Set OCANTIDIAG = new HashSet<>(); private NQueens() { } @@ -101,24 +101,27 @@ private static void getSolution(int boardSize, List> solutions, int columns[columnIndex] = rowIndex; // Skip current position if row or diagonal is already occupied - if (OCCUPIED_ROWS.contains(rowIndex) || OCCUPIED_DIAGONALS.contains(rowIndex - columnIndex) || - OCCUPIED_ANTI_DIAGONALS.contains(rowIndex + columnIndex)) { + boolean isROp = OCROWS.contains(rowIndex); + + boolean isDOp = OCDIAG.contains(rowIndex - columnIndex) || OCANTIDIAG.contains(rowIndex + columnIndex); + + if (isROp || isDOp) { continue; } // Mark current row and diagonal as occupied - OCCUPIED_ROWS.add(rowIndex); - OCCUPIED_DIAGONALS.add(rowIndex - columnIndex); - OCCUPIED_ANTI_DIAGONALS.add(rowIndex + columnIndex); + OCROWS.add(rowIndex); + OCDIAG.add(rowIndex - columnIndex); + OCANTIDIAG.add(rowIndex + columnIndex); // Move to the next column after placing current queen getSolution(boardSize, solutions, columns, columnIndex + 1); // Backtrack by removing current queen - OCCUPIED_ROWS.remove(rowIndex); - OCCUPIED_DIAGONALS.remove(rowIndex - columnIndex); - OCCUPIED_ANTI_DIAGONALS.remove(rowIndex + columnIndex); + OCROWS.remove(rowIndex); + OCDIAG.remove(rowIndex - columnIndex); + OCANTIDIAG.remove(rowIndex + columnIndex); } } From 0b0ce0e5a9b7f8ddb434bc92ac172a4abda3911a Mon Sep 17 00:00:00 2001 From: bhanu1012 Date: Fri, 8 May 2026 23:06:14 +0530 Subject: [PATCH 10/10] Removed extra brace --- src/main/java/com/thealgorithms/backtracking/NQueens.java | 1 - 1 file changed, 1 deletion(-) diff --git a/src/main/java/com/thealgorithms/backtracking/NQueens.java b/src/main/java/com/thealgorithms/backtracking/NQueens.java index 3243f6f4752c..404f677738a0 100644 --- a/src/main/java/com/thealgorithms/backtracking/NQueens.java +++ b/src/main/java/com/thealgorithms/backtracking/NQueens.java @@ -124,5 +124,4 @@ private static void getSolution(int boardSize, List> solutions, int OCANTIDIAG.remove(rowIndex + columnIndex); } } - }