From a6edadf1cb77d6b881963bab15124e85b86cee2b Mon Sep 17 00:00:00 2001 From: vedas-dixit Date: Sun, 22 Oct 2023 13:19:23 +0530 Subject: [PATCH 1/5] Implemented M Coloring Problem --- Backtracking/MColoringProblem.js | 65 +++++++++++++++++++++ Backtracking/tests/MColoringProblem.test.js | 25 ++++++++ 2 files changed, 90 insertions(+) create mode 100644 Backtracking/MColoringProblem.js create mode 100644 Backtracking/tests/MColoringProblem.test.js diff --git a/Backtracking/MColoringProblem.js b/Backtracking/MColoringProblem.js new file mode 100644 index 0000000000..2ad2102a90 --- /dev/null +++ b/Backtracking/MColoringProblem.js @@ -0,0 +1,65 @@ +/* + Problem: M Coloring Problem + Given a graph represented as an adjacency matrix and a number M (number of colors), + determine if the graph can be colored with up to M colors such that no two adjacent + vertices share the same color. + + What is the M Coloring Problem? + - This problem is about coloring a graph's vertices with at most M different colors + such that no two adjacent vertices have the same color. + + Example: + - Consider a triangle (3 nodes connected cyclically). We'd need 3 colors to color each vertex + without adjacent vertices having the same color. + + Solution: + - We will be using backtracking to solve this question. + - Color a vertex, then move to an adjacent vertex and try all colors. If a color is valid, + continue to the next vertex, else backtrack. +*/ + +class MColoring { + constructor(graph, m) { + this.graph = graph; // adjacency matrix representation + this.m = m; + this.colors = new Array(graph.length).fill(0); + } + + isSafe(vertex, color) { + for (let i = 0; i < this.graph.length; i++) { + if (this.graph[vertex][i] && this.colors[i] === color) { + return false; + } + } + return true; + } + + solveColoring(vertex = 0) { + if (vertex === this.graph.length) { + return true; + } + + for (let color = 1; color <= this.m; color++) { + if (this.isSafe(vertex, color)) { + this.colors[vertex] = color; + + if (this.solveColoring(vertex + 1)) { + return true; + } + + this.colors[vertex] = 0; // backtrack + } + } + return false; + } + + getSolution() { + if (this.solveColoring()) { + return this.colors; + } + return []; + } + } + + export { MColoring } + \ No newline at end of file diff --git a/Backtracking/tests/MColoringProblem.test.js b/Backtracking/tests/MColoringProblem.test.js new file mode 100644 index 0000000000..7e8d82fa78 --- /dev/null +++ b/Backtracking/tests/MColoringProblem.test.js @@ -0,0 +1,25 @@ +import { MColoring } from '../MColoringProblem'; + +describe('MColoringProblem', () => { + it('should color a triangle with 3 colors', () => { + const graph = [ + [0, 1, 1], + [1, 0, 1], + [1, 1, 0] + ]; + const test1 = new MColoring(graph, 3); + const solution = test1.getSolution(); + expect(solution).not.toEqual([]); + }); + + it('should not color a triangle with 2 colors', () => { + const graph = [ + [0, 1, 1], + [1, 0, 1], + [1, 1, 0] + ]; + const test2 = new MColoring(graph, 2); + const solution = test2.getSolution(); + expect(solution).toEqual([]); + }); +}); From f945eb1c79903d0b597a7c12cce6a7823fc404bb Mon Sep 17 00:00:00 2001 From: vedas-dixit Date: Sun, 22 Oct 2023 13:19:23 +0530 Subject: [PATCH 2/5] Implemented M Coloring Problem --- Backtracking/MColoringProblem.js | 65 +++++++++++++++++++++ Backtracking/tests/MColoringProblem.test.js | 25 ++++++++ 2 files changed, 90 insertions(+) create mode 100644 Backtracking/MColoringProblem.js create mode 100644 Backtracking/tests/MColoringProblem.test.js diff --git a/Backtracking/MColoringProblem.js b/Backtracking/MColoringProblem.js new file mode 100644 index 0000000000..2ad2102a90 --- /dev/null +++ b/Backtracking/MColoringProblem.js @@ -0,0 +1,65 @@ +/* + Problem: M Coloring Problem + Given a graph represented as an adjacency matrix and a number M (number of colors), + determine if the graph can be colored with up to M colors such that no two adjacent + vertices share the same color. + + What is the M Coloring Problem? + - This problem is about coloring a graph's vertices with at most M different colors + such that no two adjacent vertices have the same color. + + Example: + - Consider a triangle (3 nodes connected cyclically). We'd need 3 colors to color each vertex + without adjacent vertices having the same color. + + Solution: + - We will be using backtracking to solve this question. + - Color a vertex, then move to an adjacent vertex and try all colors. If a color is valid, + continue to the next vertex, else backtrack. +*/ + +class MColoring { + constructor(graph, m) { + this.graph = graph; // adjacency matrix representation + this.m = m; + this.colors = new Array(graph.length).fill(0); + } + + isSafe(vertex, color) { + for (let i = 0; i < this.graph.length; i++) { + if (this.graph[vertex][i] && this.colors[i] === color) { + return false; + } + } + return true; + } + + solveColoring(vertex = 0) { + if (vertex === this.graph.length) { + return true; + } + + for (let color = 1; color <= this.m; color++) { + if (this.isSafe(vertex, color)) { + this.colors[vertex] = color; + + if (this.solveColoring(vertex + 1)) { + return true; + } + + this.colors[vertex] = 0; // backtrack + } + } + return false; + } + + getSolution() { + if (this.solveColoring()) { + return this.colors; + } + return []; + } + } + + export { MColoring } + \ No newline at end of file diff --git a/Backtracking/tests/MColoringProblem.test.js b/Backtracking/tests/MColoringProblem.test.js new file mode 100644 index 0000000000..7e8d82fa78 --- /dev/null +++ b/Backtracking/tests/MColoringProblem.test.js @@ -0,0 +1,25 @@ +import { MColoring } from '../MColoringProblem'; + +describe('MColoringProblem', () => { + it('should color a triangle with 3 colors', () => { + const graph = [ + [0, 1, 1], + [1, 0, 1], + [1, 1, 0] + ]; + const test1 = new MColoring(graph, 3); + const solution = test1.getSolution(); + expect(solution).not.toEqual([]); + }); + + it('should not color a triangle with 2 colors', () => { + const graph = [ + [0, 1, 1], + [1, 0, 1], + [1, 1, 0] + ]; + const test2 = new MColoring(graph, 2); + const solution = test2.getSolution(); + expect(solution).toEqual([]); + }); +}); From 95cab089ab04c7adb62a49180666666b0a43f8ab Mon Sep 17 00:00:00 2001 From: vedas-dixit Date: Mon, 23 Oct 2023 10:38:29 +0530 Subject: [PATCH 3/5] Switch to a functional approach instead of class-based. Use proper JSDoc comments. Refine the comments and remove redundancies. --- Backtracking/MColoringProblem.js | 94 +++++++++------------ Backtracking/tests/MColoringProblem.test.js | 14 ++- 2 files changed, 45 insertions(+), 63 deletions(-) diff --git a/Backtracking/MColoringProblem.js b/Backtracking/MColoringProblem.js index 2ad2102a90..751fb3e9f2 100644 --- a/Backtracking/MColoringProblem.js +++ b/Backtracking/MColoringProblem.js @@ -1,65 +1,49 @@ -/* - Problem: M Coloring Problem - Given a graph represented as an adjacency matrix and a number M (number of colors), - determine if the graph can be colored with up to M colors such that no two adjacent - vertices share the same color. +//https://en.wikipedia.org/wiki/Edge_coloring - What is the M Coloring Problem? - - This problem is about coloring a graph's vertices with at most M different colors - such that no two adjacent vertices have the same color. +// M Coloring Problem +// Given an adjacency matrix representation of a graph and a number M, +// determine if the graph can be colored with up to M colors such that +// no two adjacent vertices share the same color. - Example: - - Consider a triangle (3 nodes connected cyclically). We'd need 3 colors to color each vertex - without adjacent vertices having the same color. +function mColoring(graph, m) { + const colors = new Array(graph.length).fill(0); - Solution: - - We will be using backtracking to solve this question. - - Color a vertex, then move to an adjacent vertex and try all colors. If a color is valid, - continue to the next vertex, else backtrack. -*/ - -class MColoring { - constructor(graph, m) { - this.graph = graph; // adjacency matrix representation - this.m = m; - this.colors = new Array(graph.length).fill(0); - } - - isSafe(vertex, color) { - for (let i = 0; i < this.graph.length; i++) { - if (this.graph[vertex][i] && this.colors[i] === color) { - return false; - } + // Check if it's safe to color a vertex with a given color. + function isSafe(vertex, color) { + for (let i = 0; i < graph.length; i++) { + if (graph[vertex][i] && colors[i] === color) { + return false; } + } + return true; + } + + // Use backtracking to try and color the graph. + function solveColoring(vertex = 0) { + if (vertex === graph.length) { return true; } - - solveColoring(vertex = 0) { - if (vertex === this.graph.length) { - return true; - } - - for (let color = 1; color <= this.m; color++) { - if (this.isSafe(vertex, color)) { - this.colors[vertex] = color; - - if (this.solveColoring(vertex + 1)) { - return true; - } - - this.colors[vertex] = 0; // backtrack + + for (let color = 1; color <= m; color++) { + if (isSafe(vertex, color)) { + colors[vertex] = color; + + if (solveColoring(vertex + 1)) { + return true; } + + // If no solution, backtrack. + colors[vertex] = 0; } - return false; - } - - getSolution() { - if (this.solveColoring()) { - return this.colors; - } - return []; } + return false; } - - export { MColoring } - \ No newline at end of file + + // If coloring is possible, return the colors. + if (solveColoring()) { + return colors; + } + return null; +} + +export { mColoring }; \ No newline at end of file diff --git a/Backtracking/tests/MColoringProblem.test.js b/Backtracking/tests/MColoringProblem.test.js index 7e8d82fa78..7ef08493d6 100644 --- a/Backtracking/tests/MColoringProblem.test.js +++ b/Backtracking/tests/MColoringProblem.test.js @@ -1,4 +1,4 @@ -import { MColoring } from '../MColoringProblem'; +import { mColoring } from '../MColoringProblem'; describe('MColoringProblem', () => { it('should color a triangle with 3 colors', () => { @@ -7,9 +7,8 @@ describe('MColoringProblem', () => { [1, 0, 1], [1, 1, 0] ]; - const test1 = new MColoring(graph, 3); - const solution = test1.getSolution(); - expect(solution).not.toEqual([]); + const solution = mColoring(graph, 3); + expect(solution).not.toBeNull(); }); it('should not color a triangle with 2 colors', () => { @@ -18,8 +17,7 @@ describe('MColoringProblem', () => { [1, 0, 1], [1, 1, 0] ]; - const test2 = new MColoring(graph, 2); - const solution = test2.getSolution(); - expect(solution).toEqual([]); + const solution = mColoring(graph, 2); + expect(solution).toBeNull(); }); -}); +}); \ No newline at end of file From eafd7fb08efbe4210eb00a78296f6fc74be608ec Mon Sep 17 00:00:00 2001 From: github-actions <${GITHUB_ACTOR}@users.noreply.github.com> Date: Mon, 23 Oct 2023 05:14:21 +0000 Subject: [PATCH 4/5] Updated Documentation in README.md --- DIRECTORY.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/DIRECTORY.md b/DIRECTORY.md index aea7b1548f..61fa501119 100644 --- a/DIRECTORY.md +++ b/DIRECTORY.md @@ -3,6 +3,7 @@ * [generateParentheses](Backtracking/generateParentheses.js) * [GeneratePermutations](Backtracking/GeneratePermutations.js) * [KnightTour](Backtracking/KnightTour.js) + * [MColoringProblem](Backtracking/MColoringProblem.js) * [NQueens](Backtracking/NQueens.js) * [RatInAMaze](Backtracking/RatInAMaze.js) * [Sudoku](Backtracking/Sudoku.js) @@ -166,6 +167,7 @@ * [Area](Maths/Area.js) * [ArithmeticGeometricMean](Maths/ArithmeticGeometricMean.js) * [ArmstrongNumber](Maths/ArmstrongNumber.js) + * [AutomorphicNumber](Maths/AutomorphicNumber.js) * [AverageMean](Maths/AverageMean.js) * [AverageMedian](Maths/AverageMedian.js) * [BinaryConvert](Maths/BinaryConvert.js) From 9300adc1d33870ce4ac554e2bb95f402edf90b35 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lars=20M=C3=BCller?= <34514239+appgurueu@users.noreply.github.com> Date: Mon, 23 Oct 2023 18:39:25 +0200 Subject: [PATCH 5/5] Proper JSDoc comment --- Backtracking/MColoringProblem.js | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/Backtracking/MColoringProblem.js b/Backtracking/MColoringProblem.js index 0424d0408f..c89f30e043 100644 --- a/Backtracking/MColoringProblem.js +++ b/Backtracking/MColoringProblem.js @@ -1,10 +1,10 @@ -//https://en.wikipedia.org/wiki/Edge_coloring - -// M Coloring Problem -// Given an adjacency matrix representation of a graph and a number M, -// determine if the graph can be colored with up to M colors such that -// no two adjacent vertices share the same color. - +/** + * Colors a graph using up to m colors such that no two adjacent vertices share the same color. + * @param {number[][]} graph - Adjacency matrix of the graph, using 0 for no edge. + * @param {number} m - The number of colors to use. + * @returns {?Array.} A valid M-coloring of the graph using colors 1 to m, or null if none exists. + * @see https://en.wikipedia.org/wiki/Graph_coloring + */ function mColoring(graph, m) { const colors = new Array(graph.length).fill(0);