{"id":19280301,"url":"https://github.com/sraaphorst/sudoku-stochastic","last_synced_at":"2025-06-24T20:12:04.133Z","repository":{"id":84878105,"uuid":"157450512","full_name":"sraaphorst/sudoku-stochastic","owner":"sraaphorst","description":"Solving Sudoku boards using stochastic methods and genetic algorithms","archived":false,"fork":false,"pushed_at":"2022-12-04T09:37:45.000Z","size":206,"stargazers_count":2,"open_issues_count":4,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-02-23T21:44:46.016Z","etag":null,"topics":["beta-hill-climbing","cpp14","cpp17","genetic-algorithm","genetic-optimization-algorithm","great-deluge","hill-climbing","simulated-annealing","stochastic-optimization","sudoku","sudoku-board","sudoku-solver","tabu-search"],"latest_commit_sha":null,"homepage":"","language":"C++","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/sraaphorst.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2018-11-13T21:38:26.000Z","updated_at":"2024-11-14T08:02:23.000Z","dependencies_parsed_at":"2023-03-02T18:16:15.291Z","dependency_job_id":null,"html_url":"https://github.com/sraaphorst/sudoku-stochastic","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/sraaphorst/sudoku-stochastic","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sraaphorst%2Fsudoku-stochastic","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sraaphorst%2Fsudoku-stochastic/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sraaphorst%2Fsudoku-stochastic/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sraaphorst%2Fsudoku-stochastic/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/sraaphorst","download_url":"https://codeload.github.com/sraaphorst/sudoku-stochastic/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sraaphorst%2Fsudoku-stochastic/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":261749259,"owners_count":23203998,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["beta-hill-climbing","cpp14","cpp17","genetic-algorithm","genetic-optimization-algorithm","great-deluge","hill-climbing","simulated-annealing","stochastic-optimization","sudoku","sudoku-board","sudoku-solver","tabu-search"],"created_at":"2024-11-09T21:17:44.316Z","updated_at":"2025-06-24T20:12:04.101Z","avatar_url":"https://github.com/sraaphorst.png","language":"C++","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Stochastic Sudoku\n\n**Current status:** In progress.\n\nThis is another technique to attempt to solve Sudoku boards using stochastic algorithms. Note that we do not limit to 3^2 x 3^2 = 9 x 9 boards, but allow for any positive integer n and n^2 x n^2 boards. (The command-line apps, however, limit to standard Sudoku boards.)\n\nThe current implementation offers the current types of algorithms to find solutions to Sudoku puzzles:\n1. Genetic algorithm\n2. Hill climbing\n3. β-Hill climbing\n4. Great deluge algorithm\n5. Tabu search algorithm\n6. Simulated annealing algorithm\n\nMy primary goals in this project were to:\n\n1. Implement a genetic algorithm and other reusable heuristic algorithms in C++;\n2. Compare the efficiency with brute-force backtracking, exact cover, and constraint programming;\n3. Gain more experience with `std::unique_ptr` and its necessary move semantics, since I had seldom worked with them in the past; and\n4. Experiment with OpenMP for parallelization.\n\n## Formulation ##\n\n- Every row of a Sudoku board is one of the `9! = 36,2880` permutations in `S_9`. (The same is true for columns and grids.)\n\n- The idea behind generating a random board is to take the partialy filled board, and randomly complete the row permutation.\n\n- Crossover breeding occurs with a fixed probability using a pre-chosen selection algorithm (k-tournament, roulette, and random are currently offered). Two children are produced row-by-row, each with one or the other corresponding row from one of the parents with fixed probability.\n\n- Mutation occurs with a fixed probability on the children, and consists of choosing a row, and then swapping a new row permtutation (that reflects the fixed cells) in place.\n\n- Every generation, we euthanize candidates that are weak and replace them with new random candidates. If the board with the best fitness found has not changed for a large number of rounds, we kill and replace the entire generation and then reset the counter.\n\n- **Fitness:** We measure the fitness of a Sudoku board by the sum of the number of distinct digits per row, column, and subgrid. Note that rows are unimportant, as being permutations, every candidate has perfect row fitness.\n\n## Experimental Results ##\n\nGenetic algorithms are a very poor tool to use to solve Sudoku of any substantial difficulty. While exact cover and constraint programming can (and will) solve any Sudoku board - regardless of difficulty - in a fraction of a millisecond, the genetic algorithm - even if it does find a solution - finds one slowly.\n\nOut of the provided heuristics, however, the genetic algorithm is the only one who can reliably solve not only the `easy_board` candidate, but the `medium_board` as well: the other heuristics can solve the `very_easy` board, but struggle with the `easy_board`.\n\nThis is largely due to the search space for Sudoku. For a given Sudoku board search space with many empty cells, there are many local maximums; this, it is very easy for a heuristic algorithm to get stuck and have trouble escaping local maximums to find the single (assuming the board is legitimate) global maximum.\n\nHeuristic algorithms also tend to have many parameters, and tweaking them is difficult: sometimes they seem board-dependent.\n\n## Example ##\n\nWe represent a Sudoku board as a string of length 81 where 0 indicates an empty cell.\n\nAll of the heuristics are able to solve this benchmark board, as provided in:\n\nhttps://www.researchgate.net/publication/319886025_b-Hill_Climbing_Algorithm_for_Sudoku_Game\n\n`050306007000085024098420603901003206030000010507260908405090380010570002800104070`\n\nFurthermore, I failed to see any advantage of β-hill climbing over heuristics other than vanilla hill climbing.\n\nHowever, this board is incredibly simple. As the difficulty increases, the probability of solving drops off sharply. The algorithms struggled to solve this Sudoku board, classified as easy:\n\n`870090230000003010004281000040809603090060040308704090000527100010900000027040085`\n\nThe notoriously difficult Sudoku board, as provided in:\n\nhttps://www.telegraph.co.uk/news/science/science-news/9359579/Worlds-hardest-sudoku-can-you-crack-it.html\n\n`800000000003600000070090200050007000000045700000100030001000068008500010090000400`\n\ncould not be solved by any of the heuristics, whereas exact cover and constraint methods solve it with ease.\n\n\n## Conclusion ##\n\nDespite the artifact with regards to Sudoku solving being far from ideal, the following goals have been accomplished:\n\n1. Generate a generic C++ genetic algorithm that can be used for any genetic algorithm purposes.\n2. Generate another simple library of heuristic methods related to hill climbing that can easily be repurposed.\n3. Learn substantially more about `std::unique_ptr`, move semantics, and OpenMP.\n\nThus, in that sense, the project was a success.\n\n## TODO ##\n\nAt the moment, only the genetic algorithm offers command-line execution. This should be extended to the other heuristics as well.\n\nAdditionally, statistics and proper logging need to be added.\n\nFinally, I would like to add other generic C++ heuristic algorithms to the list that can be used to solve Sudoku and compare them.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsraaphorst%2Fsudoku-stochastic","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsraaphorst%2Fsudoku-stochastic","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsraaphorst%2Fsudoku-stochastic/lists"}