From b59c082a2f6c23f76597d9cd3053807da28ea177 Mon Sep 17 00:00:00 2001 From: "E. Choroba" Date: Wed, 10 Nov 2021 00:17:48 +0100 Subject: Add solutions to 138: Workdays & Split Number by E. Choroba --- challenge-138/e-choroba/perl/ch-1.pl | 47 ++++++++++++++++++++++++++++++++++++ challenge-138/e-choroba/perl/ch-2.pl | 26 ++++++++++++++++++++ 2 files changed, 73 insertions(+) create mode 100755 challenge-138/e-choroba/perl/ch-1.pl create mode 100755 challenge-138/e-choroba/perl/ch-2.pl diff --git a/challenge-138/e-choroba/perl/ch-1.pl b/challenge-138/e-choroba/perl/ch-1.pl new file mode 100755 index 0000000000..f17e160f7f --- /dev/null +++ b/challenge-138/e-choroba/perl/ch-1.pl @@ -0,0 +1,47 @@ +#!/usr/bin/perl +use warnings; +use strict; +use feature qw{ say }; + +use Time::Piece; +use Time::Seconds qw{ ONE_DAY }; + +sub workdays_slow { + my ($year) = @_; + my $d = 'Time::Piece'->strptime("$year-0101", '%Y-%m%d'); + my $count = 0; + while ($d->year == $year) { + my $wday = $d->wday; + ++$count if $wday > 1 && $wday < 7; + $d += ONE_DAY; + } + return $count +} + +sub workdays_fast { + my ($year) = @_; + my $tp = 'Time::Piece'->strptime("$year-0101", '%Y-%m%d'); + my $wday = $tp->wday; + my $leap = $tp->is_leap_year; + + return 260 if $wday == 7 || $wday == 1 && ! $leap; + return 262 if $leap && $wday > 1 && $wday < 6; + return 261 +} + +use Test2::V0; + +is workdays_fast(2021), 261, 'Example 1'; +is workdays_fast(2020), 262, 'Example 2'; + + +for my $year (1900 .. 2100) { + is workdays_slow($year), workdays_fast($year), "same $year"; +} +done_testing(); + +use Benchmark qw{ cmpthese }; +cmpthese(-3, { + slow => 'workdays_slow(1900 + int rand 1000)', + fast => 'workdays_fast(1900 + int rand 1000)', +}); diff --git a/challenge-138/e-choroba/perl/ch-2.pl b/challenge-138/e-choroba/perl/ch-2.pl new file mode 100755 index 0000000000..c48f2fde1d --- /dev/null +++ b/challenge-138/e-choroba/perl/ch-2.pl @@ -0,0 +1,26 @@ +#!/usr/bin/perl +use warnings; +use strict; + +sub _split { + my ($sum, $part) = @_; + return 1 if $sum == $part; + + for my $length (1 .. length($part) - 1) { + my $prefix = substr $part, 0, $length; + return 1 if _split($sum - $prefix, substr $part, $length) + } + return 0 +} + +sub split_number { + my ($square) = @_; + return _split(sqrt $square, $square) +} + +use Test2::V0; +plan 3; + +is split_number(81), 1, 'Example 1'; +is split_number(9801), 1, 'Example 2'; +is split_number(36), 0, 'Example 3'; -- cgit