From 7c18a491fd94458ec5e6c0c24b4a3a073a1c80be Mon Sep 17 00:00:00 2001 From: Tyler Wardhaugh Date: Thu, 12 Nov 2020 16:12:31 -0800 Subject: Ch86 (Clojure): improve Task 1's algorithm We now prep the 'source' based on whether the target (A) is zero or non-zero. If zero, we consider any value duplicated in the coll[ection] N. If non-zero, every value in the collection must be considered. --- .../tyler-wardhaugh/clojure/src/tw/weekly/c86/t1.clj | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/challenge-086/tyler-wardhaugh/clojure/src/tw/weekly/c86/t1.clj b/challenge-086/tyler-wardhaugh/clojure/src/tw/weekly/c86/t1.clj index 4a6a873bc7..762e938629 100644 --- a/challenge-086/tyler-wardhaugh/clojure/src/tw/weekly/c86/t1.clj +++ b/challenge-086/tyler-wardhaugh/clojure/src/tw/weekly/c86/t1.clj @@ -8,12 +8,11 @@ (defn pair-difference "Find a pair of coll such that their difference equals the target" [target coll] - (let [freqs (frequencies coll) - s (-> freqs keys set) - repeater (fn [v] (when v (repeat 2 v)))] - (if (zero? target) - (->> freqs (filter (fn [[_ v]] (> v 1))) ffirst repeater) - (->> s (keep (fn [v] (let [k (+ target v)] (when (s k) [v k])))) first)))) + (let [xf (if (zero? target) + (keep (fn [[k v]] (when (> v 1) k))) + (map key)) + s (into #{} xf (frequencies coll))] + (->> s (filter #(s (+ target %))) first))) (defn -main "Run Task 1 with a target A and a list of numbers N, defaulting to the -- cgit From aabd66466e4c75067d7c31d2b38419340f08c62e Mon Sep 17 00:00:00 2001 From: hstejas Date: Sat, 14 Nov 2020 23:20:00 +0530 Subject: The Weekly Challenge - 086 --- challenge-086/hstejas/README | 1 + challenge-086/hstejas/cpp/c1.cpp | 43 ++++++++ challenge-086/hstejas/cpp/c2.cpp | 210 +++++++++++++++++++++++++++++++++++++++ challenge-086/hstejas/perl/c1.pl | 38 +++++++ challenge-086/hstejas/perl/c2.pl | 105 ++++++++++++++++++++ 5 files changed, 397 insertions(+) create mode 100644 challenge-086/hstejas/README create mode 100644 challenge-086/hstejas/cpp/c1.cpp create mode 100644 challenge-086/hstejas/cpp/c2.cpp create mode 100755 challenge-086/hstejas/perl/c1.pl create mode 100755 challenge-086/hstejas/perl/c2.pl diff --git a/challenge-086/hstejas/README b/challenge-086/hstejas/README new file mode 100644 index 0000000000..969c5c0569 --- /dev/null +++ b/challenge-086/hstejas/README @@ -0,0 +1 @@ +Solution by Tejas diff --git a/challenge-086/hstejas/cpp/c1.cpp b/challenge-086/hstejas/cpp/c1.cpp new file mode 100644 index 0000000000..79fa9a55bc --- /dev/null +++ b/challenge-086/hstejas/cpp/c1.cpp @@ -0,0 +1,43 @@ +#include +#include +#include + +// g++ --std=c++17 c1.cpp && ./a.out + +void pair_diff(unsigned int reference, std::vector nums) +{ + std::sort(nums.begin(), nums.end(), std::greater()); + auto start = nums.begin(); + auto curr = start; + while(start != nums.end() && curr != nums.end()) + { + ++curr; + int diff = std::abs(*start - *curr); + if(diff == reference) + { + std::cout << "1 as " << *start << " - " << *curr << " = " << diff << std::endl; + return; + } + else if (diff > reference) + { + ++start; + curr = start; + } + } + std::cout << "0" << std::endl; +} + +int main() +{ + std::vector>> tests { + {7, {50, 8, 12, 15, 5} }, + {6, {1, 5, 2, 9, 7} }, + {15, {10, 30, 20, 50, 40} }, + {15, {-15, -5, -30, 20, 50, 40} } + }; + + for (auto test : tests) + { + pair_diff(test.first, test.second); + } +} \ No newline at end of file diff --git a/challenge-086/hstejas/cpp/c2.cpp b/challenge-086/hstejas/cpp/c2.cpp new file mode 100644 index 0000000000..534a5f036b --- /dev/null +++ b/challenge-086/hstejas/cpp/c2.cpp @@ -0,0 +1,210 @@ +#include +#include +#include +#include +#include + +// https://raw.githubusercontent.com/agauniyal/rang/master/include/rang.hpp +#include "rang.hpp" + +// g++ --std=c++17 c2.cpp -O2 && ./a.out + +namespace std +{ + std::string to_string(bool in) + { + return in ? "true" : "false"; + } +} // namespace std + +class Board +{ +public: + + Board(const std::array, 9>& in) + :mBoard(in) { } + + void fill(int* in) + { + for(size_t row = 0; row < mBoard.size(); row++) + { + for(size_t col = 0; col < mBoard.size(); col++) + { + *(in + (mBoard.size() * row) + col) = mBoard[row][col]; + } + } + } + + void checkPrint(const std::array, 9>& ref) + { + for(size_t row=0; row < mBoard.size(); row++) + { + for(size_t col=0; col < mBoard.size(); col++) + { + if(mBoard[row][col] == ref[row][col]) + { + std::cout << mBoard[row][col] << " "; + } + else + { + std::cout << rang::fg::red << mBoard[row][col] << rang::fg::reset << " "; + } + } + std::cout << std::endl; + } + } + + void print() + { + for(size_t row=0; row < mBoard.size(); row++) + { + for(size_t col=0; col < mBoard.size(); col++) + { + if(mBoard[row][col] != 0) + { + std::cout << mBoard[row][col] << " "; + } + else + { + std::cout << rang::fg::red << mBoard[row][col] << rang::fg::reset << " "; + } + } + std::cout << std::endl; + } + } + + bool solve() + { + bool result = solveNext(0, 0); + std::cout << "Solved? " << std::to_string(result) << std::endl; + return result; + } + +protected: + + bool validRow(int num, size_t row) + { + return std::find(mBoard[row].begin(), mBoard[row].end(), num) == mBoard[row].end(); + } + + bool validCol(int num, size_t col) + { + // entire col + for(size_t irow = 0; irow < mBoard.size(); irow++) + { + if(mBoard[irow][col] == num) + { + return false; + } + } + return true; + } + + bool validBox(int num, size_t row, size_t col) + { + size_t oRow = 3 * (row / 3); + size_t oCol = 3 * (col / 3); + // entire box + for(size_t irow = oRow; irow < oRow+3; irow++) + { + if(std::find(mBoard[irow].begin() + oCol, mBoard[irow].begin() + oCol + 3, num) + != (mBoard[irow].begin() + oCol + 3)) + { + return false; + } + } + return true; + } + + bool isValid(int num, size_t row, size_t col) + { + return validRow(num, row) && validCol(num, col) && validBox(num, row, col); + } + + bool solveNext(size_t row, size_t col) + { + if(mBoard[row][col] == 0) + { + for(int num = 1; num <=9; num++) + { + if(isValid(num, row, col)) + { + mBoard[row][col] = num; + size_t nextCol = col == 8 ? 0 : col+1; + size_t nextRow = col == 8 ? row + 1 : row; + if(nextRow == 9 || solveNext(nextRow, nextCol)) + { + return true; + } + mBoard[row][col] = 0; + } + } + } + else + { + size_t nextCol = col == 8 ? 0 : col + 1; + size_t nextRow = col == 8 ? row + 1 : row; + if(nextRow == 9 || solveNext(nextRow, nextCol)) + { + return true; + } + } + return false; + } + + std::array, 9> mBoard; +}; + +#ifdef BUILD_SHARED +extern "C" { + bool solve(int *data) + { + std::array< std::array, 9> input; + for(size_t row = 0; row < input.size(); row++) + { + for(size_t col = 0; col < input.size(); col++) + { + input[row][col] = *(data + (row * input.size()) + col); + } + } + + Board board(input); + board.print(); + bool ret = board.solve(); + board.print(); + board.fill(data); + return ret; + } +} +#else +int main() +{ + std::array< std::array, 9> solved {{ + { 4, 3, 5, 2, 6, 9, 7, 8, 1 }, + { 6, 8, 2, 5, 7, 1, 4, 9, 3 }, + { 1, 9, 7, 8, 3, 4, 5, 6, 2 }, + { 8, 2, 6, 1, 9, 5, 3, 4, 7 }, + { 3, 7, 4, 6, 8, 2, 9, 1, 5 }, + { 9, 5, 1, 7, 4, 3, 6, 2, 8 }, + { 5, 1, 9, 3, 2, 6, 8, 7, 4 }, + { 2, 4, 8, 9, 5, 7, 1, 3, 6 }, + { 7, 6, 3, 4, 1, 8, 2, 5, 9 }, + }}; + + std::array< std::array, 9> input {{ + { 0, 0, 0, 2, 6, 0, 7, 0, 1 }, + { 6, 8, 0, 0, 7, 0, 0, 9, 0 }, + { 1, 9, 0, 0, 0, 4, 5, 0, 0 }, + { 8, 2, 0, 1, 0, 0, 0, 4, 0 }, + { 0, 0, 4, 6, 0, 2, 9, 0, 0 }, + { 0, 5, 0, 0, 0, 3, 0, 2, 8 }, + { 0, 0, 9, 3, 0, 0, 0, 7, 4 }, + { 0, 4, 0, 0, 5, 0, 0, 3, 6 }, + { 7, 0, 3, 0, 1, 8, 0, 0, 0 }, + }}; + + Board board(input); + board.solve(); + board.print(); +} +#endif // BUILD_SHARED \ No newline at end of file diff --git a/challenge-086/hstejas/perl/c1.pl b/challenge-086/hstejas/perl/c1.pl new file mode 100755 index 0000000000..8c1e81a7ba --- /dev/null +++ b/challenge-086/hstejas/perl/c1.pl @@ -0,0 +1,38 @@ +#!/usr/bin/env perl +use strict; +use warnings; +use v5.30; + +sub pair_diff { + my $ref = abs(shift); + my @nums = sort { $b <=> $a } @{ shift @_ }; + + while(@nums) { + my $num = shift @nums; + foreach(@nums) { + my $diff = abs($num - $_); + if($diff == $ref) { + say "1 as $num - $_ = $ref"; + return; + } + elsif($diff > $ref) { + last; + } + } + } + say '0'; +} + +my $tests = { + 'Test1' => { 'ref' => 7, 'arr' => [10, 8, 12, 15, 5] }, + 'Test2' => { 'ref' => 6, 'arr' => [1, 5, 2, 9, 7] }, + 'Test3' => { 'ref' => 15, 'arr' => [10, 30, 20, 50, 40] }, + 'Test4' => { 'ref' => 15, 'arr' => [-15, -5, -30, 20, 50, 40] }, + 'Test5' => { 'ref' => -15, 'arr' => [-15, -5, -30, 20, 50, 40] }, + 'Test6' => { 'ref' => 1, 'arr' => [9, map { $_ * 10 } 1..900000 ] }, +}; + +foreach(sort keys %{$tests}) { + my $test = $tests->{$_}; + pair_diff($test->{'ref'}, $test->{'arr'}); +} \ No newline at end of file diff --git a/challenge-086/hstejas/perl/c2.pl b/challenge-086/hstejas/perl/c2.pl new file mode 100755 index 0000000000..a72ffa21ea --- /dev/null +++ b/challenge-086/hstejas/perl/c2.pl @@ -0,0 +1,105 @@ +#!/usr/bin/env perl +use strict; +use warnings; +use v5.30; + +# g++ --std=c++17 -DBUILD_SHARED ../cpp/c2.cpp -O2 -fPIC -shared -o sudoku.so +use FFI::Platypus; + +# sudo apt install libgtk3-perl +use Gtk3 -init; + +use Data::Dumper; + + +my $ffi = FFI::Platypus->new( api => 1 ); +$ffi->lib('./sudoku.so'); + +$ffi->attach( 'solve' => ['int[]'] => 'bool' ); + +my @puzzle = ( '', '', '', 2, 6, '', 7, '', 1, + 6, 8, '', '', 7, '', '', 9, '', + 1, 9, '', '', '', 4, 5, '', '', + 8, 2, '', 1, '', '', '', 4, '', + '', '', 4, 6, '', 2, 9, '', '', + '', 5, '', '', '', 3, '', 2, 8, + '', '', 9, 3, '', '', '', 7, 4, + '', 4, '', '', 5, '', '', 3, 6, + 7, '', 3, '', 1, 8, '', '', '',); + +my $window = Gtk3::Window->new ('toplevel'); +$window->signal_connect (delete_event => sub { Gtk3->main_quit }); +$window->set_title("Sudoku Solver"); +$window->set_border_width(5); + +my $provider = Gtk3::CssProvider->new(); +my $screen = Gtk3::Gdk::Screen::get_default; +Gtk3::StyleContext::add_provider_for_screen($screen, $provider, 600); +$provider->load_from_data('#boxsep { margin: 5px;} #boardsep { margin: 8px; }'); + +my @input_boxes; + +my $vbox = Gtk3::Box->new( 'vertical', 5 ); +$window->add($vbox); + +for my $row (0..8) { + if($row == 3 or $row == 6) { + my $sep = Gtk3::HSeparator->new; + $sep->set_name('boxsep'); + $vbox->add($sep); + } + + my $hbox = Gtk3::Box->new( 'horizontal', 5 ); + $vbox->add($hbox); + + for my $col (0..8) { + if($col == 3 or $col == 6) { + my $sep = Gtk3::VSeparator->new(); + $sep->set_name('boxsep'); + $hbox->add($sep); + } + my $cell = new Gtk3::Entry->new; + $cell->set_width_chars(2); + $cell->set_text($puzzle[$row*9 + $col]); + push @input_boxes, $cell; + $hbox->add($cell) + } +} +my $board_sep = Gtk3::HSeparator->new; +$board_sep->set_name('boardsep'); +$vbox->add($board_sep); + +my $solve_btn = Gtk3::Button->new('Solve'); +$solve_btn->signal_connect (clicked => sub { + my @input_nums; + foreach(@input_boxes) { + my $text = $_->get_text(); + push @input_nums, ($text ? $text : 0); + } + my $result = solve(\@input_nums); + if($result) { + for(my $i = 0; $i <= $#input_nums; $i++) { + $input_boxes[$i]->set_text($input_nums[$i]); + } + } + else { + my $error_dialog = Gtk3::MessageDialog->new($window, 'destroy-with-parent', 'error', 'ok', 'Error solving Sudoku'); + $error_dialog->present(); + $error_dialog->signal_connect( response => sub { $error_dialog->destroy() } ); + } + }); + +my $clear_btn = Gtk3::Button->new('Clear'); +$clear_btn->signal_connect (clicked => sub { + for(@input_boxes) { + $_->set_text(''); + } + }); + +my $buttons = Gtk3::HBox->new; +$buttons->add($solve_btn); +$buttons->add($clear_btn); +$vbox->add($buttons); + +$window->show_all; +Gtk3::main; -- cgit From 3b21ccccdc0f04fea1497a1b5302135edf61e34f Mon Sep 17 00:00:00 2001 From: Abigail Date: Sat, 14 Nov 2020 21:24:22 +0100 Subject: Special case naked singles. When we are solving, resolve naked singles without going into recursion. Naked singles are cells which have only one possibility left. For those cells, we cross off the possibility for all other unsolved cells in the same row, column or box, and put the cell in the set of solved cells. We keep resolving naked singles before recursing. --- challenge-086/abigail/perl/ch-2.pl | 152 +++++++++++++++++++++++++++++++------ 1 file changed, 129 insertions(+), 23 deletions(-) diff --git a/challenge-086/abigail/perl/ch-2.pl b/challenge-086/abigail/perl/ch-2.pl index 44646e9087..3ab379a738 100644 --- a/challenge-086/abigail/perl/ch-2.pl +++ b/challenge-086/abigail/perl/ch-2.pl @@ -259,6 +259,8 @@ if ($clue_count < $SIZE) { ################################################################################ sub sees ($x, $y) { + use Carp; + croak unless defined $x && defined $y; state $cache; $$cache {$x, $y} //= do { my $out; @@ -316,16 +318,58 @@ foreach my $x (@INDICES) { } - ################################################################################ # -# Recursively solve the sudoku. +# Two helper functions: +# nr_of_elements: Given a bitfield, return how many elements it represents. +# elements: Given a bitfield, return the elements it represents. +# +################################################################################ + +my sub nr_of_elements ($bitfield) { + sprintf ("%b", $bitfield) =~ y/1/1/; +} + +my sub elements ($bitfield) { + grep {$bitfield & (1 << ($_ - 1))} @ELEMENTS; +} + + + +################################################################################ # -# Given a set of solved and unsolved cells, pick a cell with the least -# number of possibilities left. For each possibility, try this one, and -# recurse. If any leads to a solution, return this. Else, return false, -# so we can backtrack. -# If the set of unsolved cells is empty, we have solved the complete sudoku. +# Recursively solve the sudoku, given a set of solved cells, and a +# set of unsolved cells. +# +# o If the set of unsolved cells is empty, we have solved the complete +# sudoku, and we can return the set of solved cells. +# +# o If we have an unsolved cell with no possibilities left, there is no +# solution possible, and we return 1. +# +# o If we have cells with one possibility left, then create a todo list +# of all cells with one possibility left. Then, for each cell "c" of +# the todo list: +# - for each other unsolved cell "d" which "c" can see, remove "p" +# from its set of possibilities. +# + If, afterwards, "d" has no possibility left, +# there is no solution. +# + If, afterwards, "d" has one possibility left, +# add it to the todo list. +# - add "c" to the set of solved cells, with value "p" +# - remove "c" from the set of unsolved cells, and from the todo list. +# +# o Otherwise, pick an unsolved cell "c" with the least number of possibilities +# left (this will be at least two possibilities). +# - for each of its possibilities "p": +# + for each unsolved cell "d" which "c" can see, remove "p" +# from its set of possibilites +# + add "c" to the set of solved cells, with value "p" +# + remove "c" from the set of unsolved cells. +# + recurse: +# = if there is a solution, return the solution +# = else, try the next possibility +# - if no possibility leads to a solution, there is no solution. # # For larger sudoku's, we can reach the "deep recursion" warning, so we # silence it. @@ -340,27 +384,89 @@ sub solve ($solved, $unsolved) { return $solved unless keys %$unsolved; # - # Find the (a) square which the least possibilities; this - # means finding the set with the least amount of bits set. + # Bucketize the set of unsolved cells, by the number + # of possibilities left. + # + my @buckets; + while (my ($key, $value) = each %$unsolved) { + push @{$buckets [nr_of_elements $value]} => $key; + } + + # + # No solution possible. + # + return if $buckets [0]; + + if (@{$buckets [1] || []}) { + # + # We have unsolved cells with just one possibility left. + # + my %todo = map {$_ => 1} @{$buckets [1]}; + + # + # Make copies of the solved and unsolved structures. + # + my $new_solved = {%$solved}; + my $new_unsolved = {%$unsolved}; + + while (keys %todo) { + my ($cell) = sort keys %todo; + my $mask = $$new_unsolved {$cell}; + my ($x, $y) = split $; => $cell; + + # + # For all unsolved cells which can be seen by this cell + # eliminate the value of this cell from its possibilities. + # If no possibilities are left, return undef. If one possibility + # is left, push onto @todo. + # + # In any case, move this cell from the set of unsolved cells + # to the set of solved cells. + # + foreach my $can_see (sees ($x, $y)) { + my ($x1, $y1) = @$can_see; + if ($$new_unsolved {$x1, $y1} && + $$new_unsolved {$x1, $y1} & $mask) { + $$new_unsolved {$x1, $y1} &= ~ $mask; + my $nr_of_elements = + nr_of_elements $$new_unsolved {$x1, $y1}; + return if $nr_of_elements == 0; + $todo {$x1, $y1} = 1 if $nr_of_elements == 1; + } + } + + # + # Move cell to solved structure, and remove it from %todo. + # + $$new_solved {$cell} = (elements $mask) [0]; + delete $$new_unsolved {$cell}; + delete $todo {$cell}; + } + + # + # Recurse with the new sets + # + return solve ($new_solved, $new_unsolved); + } + + # + # Now, find a cell with the least number of possibilities left. + # That will be a cell in the first non-empty bucket. # - my ($key) = map {$$_ [0]} - sort {$$a [1] <=> $$b [1]} - map {[$_, sprintf ("%b", $$unsolved {$_}) =~ y/1/1/]} - keys %$unsolved; - my ($x, $y) = split $; => $key; - my $possibilities = $$unsolved {$key}; + my ($bucket) = grep {$_} @buckets; + my $cell = $$bucket [0]; + my ($x, $y) = split $; => $cell; # - # Guess each possibility for this key. + # Guess each possibility for this cell. # - foreach my $guess (@ELEMENTS) { + foreach my $guess (elements $$unsolved {$cell}) { my $mask = 1 << ($guess - 1); - next unless $possibilities & $mask; # # Create new solved unsolved structures, as copies from the given ones. # - my $new_solved = {%$solved}; + my $new_solved = {%$solved}; my $new_unsolved = {%$unsolved}; # @@ -371,16 +477,16 @@ sub solve ($solved, $unsolved) { # # Remove the guess from the set of unsolved cells. # - delete $$new_unsolved {$key}; + delete $$new_unsolved {$cell}; # # Delete our guess as possibility for each square # which can be seen. # foreach my $can_see (sees ($x, $y)) { - my ($x, $y) = @$can_see; - if ($$new_unsolved {$x, $y}) { - $$new_unsolved {$x, $y} &= ~ $mask; + my ($x1, $y1) = @$can_see; + if ($$new_unsolved {$x1, $y1}) { + $$new_unsolved {$x1, $y1} &= ~ $mask; } } -- cgit From 7a4afe3f5543d127d5ad2d3127dfc6e0272d0fc5 Mon Sep 17 00:00:00 2001 From: Lubos Kolouch Date: Sat, 14 Nov 2020 22:54:05 +0100 Subject: Solutions task 1 Perl Python LK --- challenge-086/lubos-kolouch/perl/ch-1.pl | 48 ++++++++++++++++++++++++++++++ challenge-086/lubos-kolouch/python/ch-1.py | 39 ++++++++++++++++++++++++ 2 files changed, 87 insertions(+) create mode 100644 challenge-086/lubos-kolouch/perl/ch-1.pl create mode 100644 challenge-086/lubos-kolouch/python/ch-1.py diff --git a/challenge-086/lubos-kolouch/perl/ch-1.pl b/challenge-086/lubos-kolouch/perl/ch-1.pl new file mode 100644 index 0000000000..0603c9b929 --- /dev/null +++ b/challenge-086/lubos-kolouch/perl/ch-1.pl @@ -0,0 +1,48 @@ +#!/usr/bin/perl +#=============================================================================== +# +# FILE: ch-1.pl +# +# USAGE: ./ch-1.pl +# +# DESCRIPTION: Perl Weekly Challenge 086 +# Task 1 +# Pair Difference +# +# AUTHOR: Lubos Kolouch +# CREATED: 11/14/2020 01:27:06 PM +#=============================================================================== + +use strict; +use warnings; +use Data::Dumper; + +sub is_pair_difference { + my $data = shift; + + # to avoid sorting and/or scanning through all pairs in the array + # or double nested loop, + # I will convert the array to a hash, then check if the + # corresponding key exists + + my $arr = $$data{n}; + my %h; + for (@$arr) { + $h{$_} = 1; + } + + for my $x (keys %h) { + return 1 if $h{$x + $$data{a}}; + } + + return 0; +} + +use Test::More; + +is(is_pair_difference( { 'n' => [10, 8, 12, 15, 5], 'a' => 7 }), 1); +is(is_pair_difference( { 'n' => [1, 5, 2, 9, 7], 'a' => 6 }), 1); +is(is_pair_difference( { 'n' => [10, 30, 20, 50, 40], 'a' => 15 }), 0); + +done_testing; + diff --git a/challenge-086/lubos-kolouch/python/ch-1.py b/challenge-086/lubos-kolouch/python/ch-1.py new file mode 100644 index 0000000000..0f284bf4c6 --- /dev/null +++ b/challenge-086/lubos-kolouch/python/ch-1.py @@ -0,0 +1,39 @@ +#!env python +""" +#=============================================================================== +# +# FILE: ch-1.py +# +# USAGE: ./ch-1.py +# +# DESCRIPTION: Perl Weekly Challenge 086 +# Task 1 +# Pair Difference +# +# AUTHOR: Lubos Kolouch +# CREATED: 11/14/2020 01:27:06 PM +#=============================================================================== +""" + + +def is_pair_difference(n: list, a: int): + """ + # to avoid sorting and/or scanning through all pairs in the array + # or double nested loop, + # I will convert the array to a hash, then check if the + # corresponding key exists + """ + + hash_keys = {} + for number in n: + hash_keys[number] = 1 + + for x in hash_keys: + if hash_keys.get(x+a, 0): + return 1 + return 0 + + +assert is_pair_difference(n=[10, 8, 12, 15, 5], a=7) == 1 +assert is_pair_difference(n=[1, 5, 2, 9, 7], a=6) == 1 +assert is_pair_difference(n=[10, 30, 20, 50, 40], a=15) == 0 -- cgit From 3f2837d24dd704e700404e70c7861d216dfc2995 Mon Sep 17 00:00:00 2001 From: Abigail Date: Sat, 14 Nov 2020 23:08:34 +0100 Subject: Improve comment --- challenge-086/abigail/perl/ch-2.pl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/challenge-086/abigail/perl/ch-2.pl b/challenge-086/abigail/perl/ch-2.pl index 3ab379a738..c23e6f273a 100644 --- a/challenge-086/abigail/perl/ch-2.pl +++ b/challenge-086/abigail/perl/ch-2.pl @@ -480,7 +480,7 @@ sub solve ($solved, $unsolved) { delete $$new_unsolved {$cell}; # - # Delete our guess as possibility for each square + # Delete our guess as possibility for each cell # which can be seen. # foreach my $can_see (sees ($x, $y)) { -- cgit From aeb4574faf778bd2202eb7ba7af5ac225a342285 Mon Sep 17 00:00:00 2001 From: Abigail Date: Sat, 14 Nov 2020 23:15:11 +0100 Subject: Blog for part 2. --- challenge-086/abigail/blog1.txt | 1 + 1 file changed, 1 insertion(+) create mode 100644 challenge-086/abigail/blog1.txt diff --git a/challenge-086/abigail/blog1.txt b/challenge-086/abigail/blog1.txt new file mode 100644 index 0000000000..b97c4ee817 --- /dev/null +++ b/challenge-086/abigail/blog1.txt @@ -0,0 +1 @@ +https://wp.me/pcxd30-4C -- cgit From 0250509d3274640c6161d13a75e0b9b68bd3f942 Mon Sep 17 00:00:00 2001 From: Abigail Date: Sat, 14 Nov 2020 23:23:10 +0100 Subject: Trivial updates --- challenge-086/abigail/perl/ch-2.pl | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/challenge-086/abigail/perl/ch-2.pl b/challenge-086/abigail/perl/ch-2.pl index c23e6f273a..ecafa5924c 100644 --- a/challenge-086/abigail/perl/ch-2.pl +++ b/challenge-086/abigail/perl/ch-2.pl @@ -259,8 +259,6 @@ if ($clue_count < $SIZE) { ################################################################################ sub sees ($x, $y) { - use Carp; - croak unless defined $x && defined $y; state $cache; $$cache {$x, $y} //= do { my $out; @@ -525,7 +523,7 @@ if (my $r = solve ($solved, $unsolved)) { } } else { - say "No solution found\n"; + say "No solution found."; } -- cgit From 056d904037e4c3a32913158368fde214b0dde3f0 Mon Sep 17 00:00:00 2001 From: Mohammad S Anwar Date: Sun, 15 Nov 2020 00:55:49 +0000 Subject: - Added solutions by Tejas. --- challenge-086/hstejas/cpp/c1.cpp | 43 -- challenge-086/hstejas/cpp/c2.cpp | 210 ----- challenge-086/hstejas/cpp/ch-1.cpp | 43 ++ challenge-086/hstejas/cpp/ch-2.cpp | 210 +++++ challenge-086/hstejas/perl/c1.pl | 38 - challenge-086/hstejas/perl/c2.pl | 105 --- challenge-086/hstejas/perl/ch-1.pl | 38 + challenge-086/hstejas/perl/ch-2.pl | 105 +++ members.json | 1 + stats/pwc-current.json | 379 ++++----- stats/pwc-language-breakdown-summary.json | 60 +- stats/pwc-language-breakdown.json | 1188 ++++++++++++++--------------- stats/pwc-leaders.json | 738 +++++++++--------- stats/pwc-summary-1-30.json | 110 +-- stats/pwc-summary-121-150.json | 110 +-- stats/pwc-summary-151-180.json | 34 +- stats/pwc-summary-181-210.json | 92 +-- stats/pwc-summary-31-60.json | 98 +-- stats/pwc-summary-61-90.json | 30 +- stats/pwc-summary-91-120.json | 38 +- stats/pwc-summary.json | 56 +- 21 files changed, 1875 insertions(+), 1851 deletions(-) delete mode 100644 challenge-086/hstejas/cpp/c1.cpp delete mode 100644 challenge-086/hstejas/cpp/c2.cpp create mode 100644 challenge-086/hstejas/cpp/ch-1.cpp create mode 100644 challenge-086/hstejas/cpp/ch-2.cpp delete mode 100755 challenge-086/hstejas/perl/c1.pl delete mode 100755 challenge-086/hstejas/perl/c2.pl create mode 100755 challenge-086/hstejas/perl/ch-1.pl create mode 100755 challenge-086/hstejas/perl/ch-2.pl diff --git a/challenge-086/hstejas/cpp/c1.cpp b/challenge-086/hstejas/cpp/c1.cpp deleted file mode 100644 index 79fa9a55bc..0000000000 --- a/challenge-086/hstejas/cpp/c1.cpp +++ /dev/null @@ -1,43 +0,0 @@ -#include -#include -#include - -// g++ --std=c++17 c1.cpp && ./a.out - -void pair_diff(unsigned int reference, std::vector nums) -{ - std::sort(nums.begin(), nums.end(), std::greater()); - auto start = nums.begin(); - auto curr = start; - while(start != nums.end() && curr != nums.end()) - { - ++curr; - int diff = std::abs(*start - *curr); - if(diff == reference) - { - std::cout << "1 as " << *start << " - " << *curr << " = " << diff << std::endl; - return; - } - else if (diff > reference) - { - ++start; - curr = start; - } - } - std::cout << "0" << std::endl; -} - -int main() -{ - std::vector>> tests { - {7, {50, 8, 12, 15, 5} }, - {6, {1, 5, 2, 9, 7} }, - {15, {10, 30, 20, 50, 40} }, - {15, {-15, -5, -30, 20, 50, 40} } - }; - - for (auto test : tests) - { - pair_diff(test.first, test.second); - } -} \ No newline at end of file diff --git a/challenge-086/hstejas/cpp/c2.cpp b/challenge-086/hstejas/cpp/c2.cpp deleted file mode 100644 index 534a5f036b..0000000000 --- a/challenge-086/hstejas/cpp/c2.cpp +++ /dev/null @@ -1,210 +0,0 @@ -#include -#include -#include -#include -#include - -// https://raw.githubusercontent.com/agauniyal/rang/master/include/rang.hpp -#include "rang.hpp" - -// g++ --std=c++17 c2.cpp -O2 && ./a.out - -namespace std -{ - std::string to_string(bool in) - { - return in ? "true" : "false"; - } -} // namespace std - -class Board -{ -public: - - Board(const std::array, 9>& in) - :mBoard(in) { } - - void fill(int* in) - { - for(size_t row = 0; row < mBoard.size(); row++) - { - for(size_t col = 0; col < mBoard.size(); col++) - { - *(in + (mBoard.size() * row) + col) = mBoard[row][col]; - } - } - } - - void checkPrint(const std::array, 9>& ref) - { - for(size_t row=0; row < mBoard.size(); row++) - { - for(size_t col=0; col < mBoard.size(); col++) - { - if(mBoard[row][col] == ref[row][col]) - { - std::cout << mBoard[row][col] << " "; - } - else - { - std::cout << rang::fg::red << mBoard[row][col] << rang::fg::reset << " "; - } - } - std::cout << std::endl; - } - } - - void print() - { - for(size_t row=0; row < mBoard.size(); row++) - { - for(size_t col=0; col < mBoard.size(); col++) - { - if(mBoard[row][col] != 0) - { - std::cout << mBoard[row][col] << " "; - } - else - { - std::cout << rang::fg::red << mBoard[row][col] << rang::fg::reset << " "; - } - } - std::cout << std::endl; - } - } - - bool solve() - { - bool result = solveNext(0, 0); - std::cout << "Solved? " << std::to_string(result) << std::endl; - return result; - } - -protected: - - bool validRow(int num, size_t row) - { - return std::find(mBoard[row].begin(), mBoard[row].end(), num) == mBoard[row].end(); - } - - bool validCol(int num, size_t col) - { - // entire col - for(size_t irow = 0; irow < mBoard.size(); irow++) - { - if(mBoard[irow][col] == num) - { - return false; - } - } - return true; - } - - bool validBox(int num, size_t row, size_t col) - { - size_t oRow = 3 * (row / 3); - size_t oCol = 3 * (col / 3); - // entire box - for(size_t irow = oRow; irow < oRow+3; irow++) - { - if(std::find(mBoard[irow].begin() + oCol, mBoard[irow].begin() + oCol + 3, num) - != (mBoard[irow].begin() + oCol + 3)) - { - return false; - } - } - return true; - } - - bool isValid(int num, size_t row, size_t col) - { - return validRow(num, row) && validCol(num, col) && validBox(num, row, col); - } - - bool solveNext(size_t row, size_t col) - { - if(mBoard[row][col] == 0) - { - for(int num = 1; num <=9; num++) - { - if(isValid(num, row, col)) - { - mBoard[row][col] = num; - size_t nextCol = col == 8 ? 0 : col+1; - size_t nextRow = col == 8 ? row + 1 : row; - if(nextRow == 9 || solveNext(nextRow, nextCol)) - { - return true; - } - mBoard[row][col] = 0; - } - } - } - else - { - size_t nextCol = col == 8 ? 0 : col + 1; - size_t nextRow = col == 8 ? row + 1 : row; - if(nextRow == 9 || solveNext(nextRow, nextCol)) - { - return true; - } - } - return false; - } - - std::array, 9> mBoard; -}; - -#ifdef BUILD_SHARED -extern "C" { - bool solve(int *data) - { - std::array< std::array, 9> input; - for(size_t row = 0; row < input.size(); row++) - { - for(size_t col = 0; col < input.size(); col++) - { - input[row][col] = *(data + (row * input.size()) + col); - } - } - - Board board(input); - board.print(); - bool ret = board.solve(); - board.print(); - board.fill(data); - return ret; - } -} -#else -int main() -{ - std::array< std::array, 9> solved {{ - { 4, 3, 5, 2, 6, 9, 7, 8, 1 }, - { 6, 8, 2, 5, 7, 1, 4, 9, 3 }, - { 1, 9, 7, 8, 3, 4, 5, 6, 2 }, - { 8, 2, 6, 1, 9, 5, 3, 4, 7 }, - { 3, 7, 4, 6, 8, 2, 9, 1, 5 }, - { 9, 5, 1, 7, 4, 3, 6, 2, 8 }, - { 5, 1, 9, 3, 2, 6, 8, 7, 4 }, - { 2, 4, 8, 9, 5, 7, 1, 3, 6 }, - { 7, 6, 3, 4, 1, 8, 2, 5, 9 }, - }}; - - std::array< std::array, 9> input {{ - { 0, 0, 0, 2, 6, 0, 7, 0, 1 }, - { 6, 8, 0, 0, 7, 0, 0, 9, 0 }, - { 1, 9, 0, 0, 0, 4, 5, 0, 0 }, - { 8, 2, 0, 1, 0, 0, 0, 4, 0 }, - { 0, 0, 4, 6, 0, 2, 9, 0, 0 }, - { 0, 5, 0, 0, 0, 3, 0, 2, 8 }, - { 0, 0, 9, 3, 0, 0, 0, 7, 4 }, - { 0, 4, 0, 0, 5, 0, 0, 3, 6 }, - { 7, 0, 3, 0, 1, 8, 0, 0, 0 }, - }}; - - Board board(input); - board.solve(); - board.print(); -} -#endif // BUILD_SHARED \ No newline at end of file diff --git a/challenge-086/hstejas/cpp/ch-1.cpp b/challenge-086/hstejas/cpp/ch-1.cpp new file mode 100644 index 0000000000..79fa9a55bc --- /dev/null +++ b/challenge-086/hstejas/cpp/ch-1.cpp @@ -0,0 +1,43 @@ +#include +#include +#include + +// g++ --std=c++17 c1.cpp && ./a.out + +void pair_diff(unsigned int reference, std::vector nums) +{ + std::sort(nums.begin(), nums.end(), std::greater()); + auto start = nums.begin(); + auto curr = start; + while(start != nums.end() && curr != nums.end()) + { + ++curr; + int diff = std::abs(*start - *curr); + if(diff == reference) + { + std::cout << "1 as " << *start << " - " << *curr << " = " << diff << std::endl; + return; + } + else if (diff > reference) + { + ++start; + curr = start; + } + } + std::cout << "0" << std::endl; +} + +int main() +{ + std::vector>> tests { + {7, {50, 8, 12, 15, 5} }, + {6, {1, 5, 2, 9, 7} }, + {15, {10, 30, 20, 50, 40} }, + {15, {-15, -5, -30, 20, 50, 40} } + }; + + for (auto test : tests) + { + pair_diff(test.first, test.second); + } +} \ No newline at end of file diff --git a/challenge-086/hstejas/cpp/ch-2.cpp b/challenge-086/hstejas/cpp/ch-2.cpp new file mode 100644 index 0000000000..534a5f036b --- /dev/null +++ b/challenge-086/hstejas/cpp/ch-2.cpp @@ -0,0 +1,210 @@ +#include +#include +#include +#include +#include + +// https://raw.githubusercontent.com/agauniyal/rang/master/include/rang.hpp +#include "rang.hpp" + +// g++ --std=c++17 c2.cpp -O2 && ./a.out + +namespace std +{ + std::string to_string(bool in) + { + return in ? "true" : "false"; + } +} // namespace std + +class Board +{ +public: + + Board(const std::array, 9>& in) + :mBoard(in) { } + + void fill(int* in) + { + for(size_t row = 0; row < mBoard.size(); row++) + { + for(size_t col = 0; col < mBoard.size(); col++) + { + *(in + (mBoard.size() * row) + col) = mBoard[row][col]; + } + } + } + + void checkPrint(const std::array, 9>& ref) + { + for(size_t row=0; row < mBoard.size(); row++) + { + for(size_t col=0; col < mBoard.size(); col++) + { + if(mBoard[row][col] == ref[row][col]) + { + std::cout << mBoard[row][col] << " "; + } + else + { + std::cout << rang::fg::red << mBoard[row][col] << rang::fg::reset << " "; + } + } + std::cout << std::endl; + } + } + + void print() + { + for(size_t row=0; row < mBoard.size(); row++) + { + for(size_t col=0; col < mBoard.size(); col++) + { + if(mBoard[row][col] != 0) + { + std::cout << mBoard[row][col] << " "; + } + else + { + std::cout << rang::fg::red << mBoard[row][col] << rang::fg::reset << " "; + } + } + std::cout << std::endl; + } + } + + bool solve() + { + bool result = solveNext(0, 0); + std::cout << "Solved? " << std::to_string(result) << std::endl; + return result; + } + +protected: + + bool validRow(int num, size_t row) + { + return std::find(mBoard[row].begin(), mBoard[row].end(), num) == mBoard[row].end(); + } + + bool validCol(int num, size_t col) + { + // entire col + for(size_t irow = 0; irow < mBoard.size(); irow++) + { + if(mBoard[irow][col] == num) + { + return false; + } + } + return true; + } + + bool validBox(int num, size_t row, size_t col) + { + size_t oRow = 3 * (row / 3); + size_t oCol = 3 * (col / 3); + // entire box + for(size_t irow = oRow; irow < oRow+3; irow++) + { + if(std::find(mBoard[irow].begin() + oCol, mBoard[irow].begin() + oCol + 3, num) + != (mBoard[irow].begin() + oCol + 3)) + { + return false; + } + } + return true; + } + + bool isValid(int num, size_t row, size_t col) + { + return validRow(num, row) && validCol(num, col) && validBox(num, row, col); + } + + bool solveNext(size_t row, size_t col) + { + if(mBoard[row][col] == 0) + { + for(int num = 1; num <=9; num++) + { + if(isValid(num, row, col)) + { + mBoard[row][col] = num; + size_t nextCol = col == 8 ? 0 : col+1; + size_t nextRow = col == 8 ? row + 1 : row; + if(nextRow == 9 || solveNext(nextRow, nextCol)) + { + return true; + } + mBoard[row][col] = 0; + } + } + } + else + { + size_t nextCol = col == 8 ? 0 : col + 1; + size_t nextRow = col == 8 ? row + 1 : row; + if(nextRow == 9 || solveNext(nextRow, nextCol)) + { + return true; + } + } + return false; + } + + std::array, 9> mBoard; +}; + +#ifdef BUILD_SHARED +extern "C" { + bool solve(int *data) + { + std::array< std::array, 9> input; + for(size_t row = 0; row < input.size(); row++) + { + for(size_t col = 0; col < input.size(); col++) + { + input[row][col] = *(data + (row * input.size()) + col); + } + } + + Board board(input); + board.print(); + bool ret = board.solve(); + board.print(); + board.fill(data); + return ret; + } +} +#else +int main() +{ + std::array< std::array, 9> solved {{ + { 4, 3, 5, 2, 6, 9, 7, 8, 1 }, + { 6, 8, 2, 5, 7, 1, 4, 9, 3 }, + { 1, 9, 7, 8, 3, 4, 5, 6, 2 }, + { 8, 2, 6, 1, 9, 5, 3, 4, 7 }, + { 3, 7, 4, 6, 8, 2, 9, 1, 5 }, + { 9, 5, 1, 7, 4, 3, 6, 2, 8 }, + { 5, 1, 9, 3, 2, 6, 8, 7, 4 }, + { 2, 4, 8, 9, 5, 7, 1, 3, 6 }, + { 7, 6, 3, 4, 1, 8, 2, 5, 9 }, + }}; + + std::array< std::array, 9> input {{ + { 0, 0, 0, 2, 6, 0, 7, 0, 1 }, + { 6, 8, 0, 0, 7, 0, 0, 9, 0 }, + { 1, 9, 0, 0, 0, 4, 5, 0, 0 }, + { 8, 2, 0, 1, 0, 0, 0, 4, 0 }, + { 0, 0, 4, 6, 0, 2, 9, 0, 0 }, + { 0, 5, 0, 0, 0, 3, 0, 2, 8 }, + { 0, 0, 9, 3, 0, 0, 0, 7, 4 }, + { 0, 4, 0, 0, 5, 0, 0, 3, 6 }, + { 7, 0, 3, 0, 1, 8, 0, 0, 0 }, + }}; + + Board board(input); + board.solve(); + board.print(); +} +#endif // BUILD_SHARED \ No newline at end of file diff --git a/challenge-086/hstejas/perl/c1.pl b/challenge-086/hstejas/perl/c1.pl deleted file mode 100755 index 8c1e81a7ba..0000000000 --- a/challenge-086/hstejas/perl/c1.pl +++ /dev/null @@ -1,38 +0,0 @@ -#!/usr/bin/env perl -use strict; -use warnings; -use v5.30; - -sub pair_diff { - my $ref = abs(shift); - my @nums = sort { $b <=> $a } @{ shift @_ }; - - while(@nums) { - my $num = shift @nums; - foreach(@nums) { - my $diff = abs($num - $_); - if($diff == $ref) { - say "1 as $num - $_ = $ref"; - return; - } - elsif($diff > $ref) { - last; - } - } - } - say '0'; -} - -my $tests = { - 'Test1' => { 'ref' => 7, 'arr' => [10, 8, 12, 15, 5] }, - 'Test2' => { 'ref' => 6, 'arr' => [1, 5, 2, 9, 7] }, - 'Test3' => { 'ref' => 15, 'arr' => [10, 30, 20, 50, 40] }, - 'Test4' => { 'ref' => 15, 'arr' => [-15, -5, -30, 20, 50, 40] }, - 'Test5' => { 'ref' => -15, 'arr' => [-15, -5, -30, 20, 50, 40] }, - 'Test6' => { 'ref' => 1, 'arr' => [9, map { $_ * 10 } 1..900000 ] }, -}; - -foreach(sort keys %{$tests}) { - my $test = $tests->{$_}; - pair_diff($test->{'ref'}, $test->{'arr'}); -} \ No newline at end of file diff --git a/challenge-086/hstejas/perl/c2.pl b/challenge-086/hstejas/perl/c2.pl deleted file mode 100755 index a72ffa21ea..0000000000 --- a/challenge-086/hstejas/perl/c2.pl +++ /dev/null @@ -1,105 +0,0 @@ -#!/usr/bin/env perl -use strict; -use warnings; -use v5.30; - -# g++ --std=c++17 -DBUILD_SHARED ../cpp/c2.cpp -O2 -fPIC -shared -o sudoku.so -use FFI::Platypus; - -# sudo apt install libgtk3-perl -use Gtk3 -init; - -use Data::Dumper; - - -my $ffi = FFI::Platypus->new( api => 1 ); -$ffi->lib('./sudoku.so'); - -$ffi->attach( 'solve' => ['int[]'] => 'bool' ); - -my @puzzle = ( '', '', '', 2, 6, '', 7, '', 1, - 6, 8, '', '', 7, '', '', 9, '', - 1, 9, '', '', '', 4, 5, '', '', - 8, 2, '', 1, '', '', '', 4, '', - '', '', 4, 6, '', 2, 9, '', '', - '', 5, '', '', '', 3, '', 2, 8, - '', '', 9, 3, '', '', '', 7, 4, - '', 4, '', '', 5, '', '', 3, 6, - 7, '', 3, '', 1, 8, '', '', '',); - -my $window = Gtk3::Window->new ('toplevel'); -$window->signal_connect (delete_event => sub { Gtk3->main_quit }); -$window->set_title("Sudoku Solver"); -$window->set_border_width(5); - -my $provider = Gtk3::CssProvider->new(); -my $screen = Gtk3::Gdk::Screen::get_default; -Gtk3::StyleContext::add_provider_for_screen($screen, $provider, 600); -$provider->load_from_data('#boxsep { margin: 5px;} #boardsep { margin: 8px; }'); - -my @input_boxes; - -my $vbox = Gtk3::Box->new( 'vertical', 5 ); -$window->add($vbox); - -for my $row (0..8) { - if($row == 3 or $row == 6) { - my $sep = Gtk3::HSeparator->new; - $sep->set_name('boxsep'); - $vbox->add($sep); - } - - my $hbox = Gtk3::Box->new( 'horizontal', 5 ); - $vbox->add($hbox); - - for my $col (0..8) { - if($col == 3 or $col == 6) { - my $sep = Gtk3::VSeparator->new(); - $sep->set_name('boxsep'); - $hbox->add($sep); - } - my $cell = new Gtk3::Entry->new; - $cell->set_width_chars(2); - $cell->set_text($puzzle[$row*9 + $col]); - push @input_boxes, $cell; - $hbox->add($cell) - } -} -my $board_sep = Gtk3::HSeparator->new; -$board_sep->set_name('boardsep'); -$vbox->add($board_sep); - -my $solve_btn = Gtk3::Button->new('Solve'); -$solve_btn->signal_connect (clicked => sub { - my @input_nums; - foreach(@input_boxes) { - my $text = $_->get_text(); - push @input_nums, ($text ? $text : 0); - } - my $result = solve(\@input_nums); - if($result) { - for(my $i = 0; $i <= $#input_nums; $i++) { - $input_boxes[$i]->set_text($input_nums[$i]); - } - } - else { - my $error_dialog = Gtk3::MessageDialog->new($window, 'destroy-with-parent', 'error', 'ok', 'Error solving Sudoku'); - $error_dialog->present(); - $error_dialog->signal_connect( response => sub { $error_dialog->destroy() } ); - } - }); - -my $clear_btn = Gtk3::Button->new('Clear'); -$clear_btn->signal_connect (clicked => sub { - for(@input_boxes) { - $_->set_text(''); - } - }); - -my $buttons = Gtk3::HBox->new; -$buttons->add($solve_btn); -$buttons->add($clear_btn); -$vbox->add($buttons); - -$window->show_all; -Gtk3::main; diff --git a/challenge-086/hstejas/perl/ch-1.pl b/challenge-086/hstejas/perl/ch-1.pl new file mode 100755 index 0000000000..8c1e81a7ba --- /dev/null +++ b/challenge-086/hstejas/perl/ch-1.pl @@ -0,0 +1,38 @@ +#!/usr/bin/env perl +use strict; +use warnings; +use v5.30; + +sub pair_diff { + my $ref = abs(shift); + my @nums = sort { $b <=> $a } @{ shift @_ }; + + while(@nums) { + my $num = shift @nums; + foreach(@nums) { + my $diff = abs($num - $_); + if($diff == $ref) { + say "1 as $num - $_ = $ref"; + return; + } + elsif($diff > $ref) { + last; + } + } + } + say '0'; +} + +my $tests = { + 'Test1' => { 'ref' => 7, 'arr' => [10, 8, 12, 15, 5] }, + 'Test2' => { 'ref' => 6, 'arr' => [1, 5, 2, 9, 7] }, + 'Test3' => { 'ref' => 15, 'arr' => [10, 30, 20, 50, 40] }, + 'Test4' => { 'ref' => 15, 'arr' => [-15, -5, -30, 20, 50, 40] }, + 'Test5' => { 'ref' => -15, 'arr' => [-15, -5, -30, 20, 50, 40] }, + 'Test6' => { 'ref' => 1, 'arr' => [9, map { $_ * 10 } 1..900000 ] }, +}; + +foreach(sort keys %{$tests}) { + my $test = $tests->{$_}; + pair_diff($test->{'ref'}, $test->{'arr'}); +} \ No newline at end of file diff --git a/challenge-086/hstejas/perl/ch-2.pl b/challenge-086/hstejas/perl/ch-2.pl new file mode 100755 index 0000000000..a72ffa21ea --- /dev/null +++ b/challenge-086/hstejas/perl/ch-2.pl @@ -0,0 +1,105 @@ +#!/usr/bin/env perl +use strict; +use warnings; +use v5.30; + +# g++ --std=c++17 -DBUILD_SHARED ../cpp/c2.cpp -O2 -fPIC -shared -o sudoku.so +use FFI::Platypus; + +# sudo apt install libgtk3-perl +use Gtk3 -init; + +use Data::Dumper; + + +my $ffi = FFI::Platypus->new( api => 1 ); +$ffi->lib('./sudoku.so'); + +$ffi->attach( 'solve' => ['int[]'] => 'bool' ); + +my @puzzle = ( '', '', '', 2, 6, '', 7, '', 1, + 6, 8, '', '', 7, '', '', 9, '', + 1, 9, '', '', '', 4, 5, '', '', + 8, 2, '', 1, '', '', '', 4, '', + '', '', 4, 6, '', 2, 9, '', '', + '', 5, '', '', '', 3, '', 2, 8, + '', '', 9, 3, '', '', '', 7, 4, + '', 4, '', '', 5, '', '', 3, 6, + 7, '', 3, '', 1, 8, '', '', '',); + +my $window = Gtk3::Window->new ('toplevel'); +$window->signal_connect (delete_event => sub { Gtk3->main_quit }); +$window->set_title("Sudoku Solver"); +$window->set_border_width(5); + +my $provider = Gtk3::CssProvider->new(); +my $screen = Gtk3::Gdk::Screen::get_default; +Gtk3::StyleContext::add_provider_for_screen($screen, $provider, 600); +$provider->load_from_data('#boxsep { margin: 5px;} #boardsep { margin: 8px; }'); + +my @input_boxes; + +my $vbox = Gtk3::Box->new( 'vertical', 5 ); +$window->add($vbox); + +for my $row (0..8) { + if($row == 3 or $row == 6) { + my $sep = Gtk3::HSeparator->new; + $sep->set_name('boxsep'); + $vbox->add($sep); + } + + my $hbox = Gtk3::Box->new( 'horizontal', 5 ); + $vbox->add($hbox); + + for my $col (0..8) { + if($col == 3 or $col == 6) { + my $sep = Gtk3::VSeparator->new(); + $sep->set_name('boxsep'); + $hbox->add($sep); + } + my $cell = new Gtk3::Entry->new; + $cell->set_width_chars(2); + $cell->set_text($puzzle[$row*9 + $col]); + push @input_boxes, $cell; + $hbox->add($cell) + } +} +my $board_sep = Gtk3::HSeparator->new; +$board_sep->set_name('boardsep'); +$vbox->add($board_sep); + +my $solve_btn = Gtk3::Button->new('Solve'); +$solve_btn->signal_connect (clicked => sub { + my @input_nums; + foreach(@input_boxes) { + my $text = $_->get_text(); + push @input_nums, ($text ? $text : 0); + } + my $result = solve(\@input_nums); + if($result) { + for(my $i = 0; $i <= $#input_nums; $i++) { + $input_boxes[$i]->set_text($input_nums[$i]); + } + } + else { + my $error_dialog = Gtk3::MessageDialog->new($window, 'destroy-with-parent', 'error', 'ok', 'Error solving Sudoku'); + $error_dialog->present(); + $error_dialog->signal_connect( response => sub { $error_dialog->destroy() } ); + } + }); + +my $clear_btn = Gtk3::Button->new('Clear'); +$clear_btn->signal_connect (clicked => sub { + for(@input_boxes) { + $_->set_text(''); + } + }); + +my $buttons = Gtk3::HBox->new; +$buttons->add($solve_btn); +$buttons->add($clear_btn); +$vbox->add($buttons); + +$window->show_all; +Gtk3::main; diff --git a/members.json b/members.json index b052d6aebd..31aa95e247 100644 --- a/members.json +++ b/members.json @@ -59,6 +59,7 @@ "guillermo-ramos" : "Guillermo Ramos", "gustavo-chaves" : "Gustavo Chaves", "hauke-d" : "Hauke Dampfling", + "hstejas" : "Tejas", "ianrifkin" : "Ian Rifkin", "izifresh" : "Izifresh", "jacques-guinnebault" : "Jacques Guinnebault", diff --git a/stats/pwc-current.json b/stats/pwc-current.json index 4df59f4879..d64e8f55fb 100644 --- a/stats/pwc-current.json +++ b/stats/pwc-current.json @@ -1,152 +1,8 @@ { - "xAxis" : { - "type" : "category" - }, "tooltip" : { - "pointFormat" : "{point.name}: {point.y:f}
", + "headerFormat" : "{series.name}
", "followPointer" : 1, - "headerFormat" : "{series.name}
" - }, - "plotOptions" : { - "series" : { - "borderWidth" : 0, - "dataLabels" : { - "format" : "{point.y}", - "enabled" : 1 - } - } - }, - "chart" : { - "type" : "column" - }, - "subtitle" : { - "text" : "[Champions: 22] Last updated at 2020-11-14 05:14:14 GMT" - }, - "series" : [ - { - "colorByPoint" : 1, - "name" : "Perl Weekly Challenge - 086", - "data" : [ - { - "name" : "Abigail", - "y" : 3, - "drilldown" : "Abigail" - }, - { - "name" : "Andrew Shitov", - "drilldown" : "Andrew Shitov", - "y" : 1 - }, - { - "name" : "Arne Sommer", - "drilldown" : "Arne Sommer", - "y" : 5 - }, - { - "y" : 1, - "drilldown" : "Cristina Heredia", - "name" : "Cristina Heredia" - }, - { - "drilldown" : "Daniel Bowling", - "y" : 1, - "name" : "Daniel Bowling" - }, - { - "name" : "Dave Jacoby", - "y" : 2, - "drilldown" : "Dave Jacoby" - }, - { - "name" : "E. Choroba", - "y" : 2, - "drilldown" : "E. Choroba" - }, - { - "name" : "Feng Chang", - "y" : 2, - "drilldown" : "Feng Chang" - }, - { - "name" : "Flavio Poletti", - "y" : 4, - "drilldown" : "Flavio Poletti" - }, - { - "name" : "Jorg Sommrey", - "y" : 2, - "drilldown" : "Jorg Sommrey" - }, - { - "name" : "Julio de Castro", - "y" : 4, - "drilldown" : "Julio de Castro" - }, - { - "name" : "Kang-min Liu", - "y" : 2, - "drilldown" : "Kang-min Liu" - }, - { - "y" : 2, - "drilldown" : "Mark Anderson", - "name" : "Mark Anderson" - }, - { - "y" : 1, - "drilldown" : "Myoungjin Jeon", - "name" : "Myoungjin Jeon" - }, - { - "drilldown" : "Nuno Vieira", - "y" : 2, - "name" : "Nuno Vieira" - }, - { - "name" : "Philip Hood", - "drilldown" : "Philip Hood", - "y" : 2 - }, - { - "name" : "Roger Bell_West", - "y" : 4, - "drilldown" : "Roger Bell_West" - }, - { - "name" : "Simon Green", - "drilldown" : "Simon Green", - "y" : 2 - }, - { - "name" : "Simon Proctor", - "y" : 2, - "drilldown" : "Simon Proctor" - }, - { - "name" : "Stuart Little", - "drilldown" : "Stuart Little", - "y" : 2 - }, - { - "name" : "Ulrich Rieke", - "y" : 3, - "drilldown" : "Ulrich Rieke" - }, - { - "y" : 2, - "drilldown" : "Walt Mankowski", - "name" : "Walt Mankowski" - } - ] - } - ], - "yAxis" : { - "title" : { - "text" : "Total Solutions" - } - }, - "legend" : { - "enabled" : 0 + "pointFormat" : "{point.name}: {point.y:f}
" }, "title" : { "text" : "Perl Weekly Challenge - 086" @@ -154,7 +10,7 @@ "drilldown" : { "series" : [ { - "name" : "Abigail", + "id" : "Abigail", "data" : [ [ "Perl", @@ -165,7 +21,7 @@ 1 ] ], - "id" : "Abigail" + "name" : "Abigail" }, { "data" : [ @@ -174,11 +30,10 @@ 1 ] ], - "id" : "Andrew Shitov", - "name" : "Andrew Shitov" + "name" : "Andrew Shitov", + "id" : "Andrew Shitov" }, { - "id" : "Arne Sommer", "data" : [ [ "Perl", @@ -193,60 +48,60 @@ 1 ] ], - "name" : "Arne Sommer" + "name" : "Arne Sommer", + "id" : "Arne Sommer" }, { + "id" : "Cristina Heredia", "data" : [ [ "Perl", 1 ] ], - "id" : "Cristina Heredia", "name" : "Cristina Heredia" }, { - "name" : "Daniel Bowling", "data" : [ [ "Raku", 1 ] ], + "name" : "Daniel Bowling", "id" : "Daniel Bowling" }, { + "id" : "Dave Jacoby", "data" : [ [ "Perl", 2 ] ], - "id" : "Dave Jacoby", "name" : "Dave Jacoby" }, { + "name" : "E. Choroba", "data" : [ [ "Perl", 2 ] ], - "name" : "E. Choroba", "id" : "E. Choroba" }, { + "name" : "Feng Chang", "data" : [ [ "Raku", 2 ] ], - "name" : "Feng Chang", "id" : "Feng Chang" }, { - "id" : "Flavio Poletti", "data" : [ [ "Perl", @@ -257,19 +112,21 @@ 2 ] ], - "name" : "Flavio Poletti" + "name" : "Flavio Poletti", + "id" : "Flavio Poletti" }, { + "id" : "Jorg Sommrey", + "name" : "Jorg Sommrey", "data" : [ [ "Perl", 2 ] - ], - "id" : "Jorg Sommrey", - "name" : "Jorg Sommrey" + ] }, { + "id" : "Julio de Castro", "name" : "Julio de Castro", "data" : [ [ @@ -280,61 +137,60 @@ "Raku", 2 ] - ], - "id" : "Julio de Castro" + ] }, { + "name" : "Kang-min Liu", "data" : [ [ "Raku", 2 ] ], - "id" : "Kang-min Liu", - "name" : "Kang-min Liu" + "id" : "Kang-min Liu" }, { + "id" : "Mark Anderson", + "name" : "Mark Anderson", "data" : [ [ "Raku", 2 ] - ], - "name" : "Mark Anderson", - "id" : "Mark Anderson" + ] }, { + "id" : "Myoungjin Jeon", + "name" : "Myoungjin Jeon", "data" : [ [ "Blog", 1 ] - ], - "name" : "Myoungjin Jeon", - "id" : "Myoungjin Jeon" + ] }, { + "id" : "Nuno Vieira", "data" : [ [ "Perl", 2 ] ], - "id" : "Nuno Vieira", "name" : "Nuno Vieira" }, { + "id" : "Philip Hood", "name" : "Philip Hood", "data" : [ [ "Raku", 2 ] - ], - "id" : "Philip Hood" + ] }, { - "name" : "Roger Bell_West", + "id" : "Roger Bell_West", "data" : [ [ "Perl", @@ -349,10 +205,10 @@ 1 ] ], - "id" : "Roger Bell_West" + "name" : "Roger Bell_West" }, { - "name" : "Simon Green", + "id" : "Simon Green", "data" : [ [ "Perl", @@ -363,29 +219,40 @@ 1 ] ], - "id" : "Simon Green" + "name" : "Simon Green" }, { + "id" : "Simon Proctor", "data" : [ [ "Raku", 2 ] ], - "id" : "Simon Proctor", "name" : "Simon Proctor" }, { + "id" : "Stuart Little", "data" : [ [ "Raku", 2 ] ], - "id" : "Stuart Little", "name" : "Stuart Little" }, { + "id" : "Tejas", + "data" : [ + [ + "Perl", + 2 + ] + ], + "name" : "Tejas" + }, + { + "id" : "Ulrich Rieke", "data" : [ [ "Perl", @@ -396,7 +263,6 @@ 1 ] ], - "id" : "Ulrich Rieke", "name" : "Ulrich Rieke" }, { @@ -410,5 +276,154 @@ "name" : "Walt Mankowski" } ] + }, + "series" : [ + { + "data" : [ + { + "drilldown" : "Abigail", + "y" : 3, + "name" : "Abigail" + }, + { + "name" : "Andrew Shitov", + "y" : 1, + "drilldown" : "Andrew Shitov" + }, + { + "name" : "Arne Sommer", + "drilldown" : "Arne Sommer", + "y" : 5 + }, + { + "name" : "Cristina Heredia", + "drilldown" : "Cristina Heredia", + "y" : 1 + }, + { + "y" : 1, + "drilldown" : "Daniel Bowling", + "name" : "Daniel Bowling" + }, + { + "drilldown