Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Add euler#220 .
  • Loading branch information
shlomif committed Jun 29, 2018
1 parent d658290 commit 87c71ce
Show file tree
Hide file tree
Showing 3 changed files with 228 additions and 2 deletions.
15 changes: 13 additions & 2 deletions perl6-benchmarks/benchmark.pl
Expand Up @@ -19,7 +19,9 @@

sub _bench
{
my ( $DIR, $TESTS ) = @_;
my ( $DIR, $TESTS, $times ) = @_;

$times //= 1;

if ( $DIR !~ /$FILTER/ )
{
Expand All @@ -29,7 +31,7 @@ sub _bench
print "Benchmarking $DIR\n";

chdir($DIR);
timethese( 1, $TESTS, );
timethese( $times, $TESTS, );
chdir($PWD);

return;
Expand All @@ -52,6 +54,15 @@ sub _bench
'p6' => sub { system( "perl6", "euler_189-2.p6" ); },
}
);
_bench(
"./euler220/",
{
'cpy3' => sub { system( "python3", "220-v1.py" ); },
'pypy' => sub { system( "pypy", "220-v1.py" ); },
'p6' => sub { system( "perl6", "220-v1.p6" ); },
},
50
);
_bench(
"./euler287/",
{
Expand Down
104 changes: 104 additions & 0 deletions perl6-benchmarks/euler220/220-v1.p6
@@ -0,0 +1,104 @@
#!/usr/bin/env perl6

# The Expat License
#
# Copyright ($c) 2018, Shlomi Fish
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in the Software without restriction, including without limitation the rights
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
# SOFTWARE.

class XY { has $.x = 0; has $.y = 0; };
multi infix:<+> (XY \a, XY \o) {
a.clone: |([«+»] (a, o.Capture».hash)
};
multi infix:<-> (XY \a, XY \o) {
a.clone: |([«-»] (a, o.Capture».hash)
};
class State {
has $.cur is rw = XY.new;
has $.dir1 is rw = 0;
has $.n is rw = 0;
};
multi infix:<+> (State \a, State \o) {
a.clone: |([«+»] (a, o.Capture».hash)
};
multi infix:<-> (State \a, State \o) {
a.clone: |([«-»] (a, o.Capture».hash)
};

sub master($maxdepth, $mn)
{
my $s1 = State.new;
my %Cache;
my @dirs = [XY.new(x=> 0, y=> 1), XY.new(x=> 1, y=> 0), XY.new(x=> 0, y=> -1), XY.new(x=> -1, y=> 0) ];
my $printed = False;

sub dragon($depth, $seq)
{
my $init = $s1.clone;
my $key = ($depth, $seq, ($s1.dir1 +& 3));
if ( %Cache{$key}:exists ) {
my $val = %Cache{$key};
if $val.n + $s1.n < $mn {
$s1 = $s1 + $val;
return;
}
}
for $seq.comb() -> $c {
if $c eq 'a' {
if $depth < $maxdepth {
dragon($depth+1, 'aRbFR')
}
}
elsif $c eq 'b' {
if $depth < $maxdepth {
dragon($depth+1, 'LFaLb')
}
}
elsif $c eq 'R' {
++$s1.dir1;
}
elsif $c eq 'L' {
--$s1.dir1;
}
elsif $c eq 'F' {
++$s1.n;
$s1.cur = $s1.cur + @dirs[$s1.dir1 +& 3];
}
else {
die $c;
...;
}
if $s1.n >= $mn {
if $s1.n == $mn {
if not $printed {
printf("cur = %d,%d\n", $s1.cur.x, $s1.cur.y);
$printed = True
}
}
return;
}
}
%Cache{$key} = $s1 - $init;
}
dragon(0, 'Fa');
return;
}

master(10, 500);
master(50, 1000000000000);
111 changes: 111 additions & 0 deletions perl6-benchmarks/euler220/220-v1.py
@@ -0,0 +1,111 @@
#!/usr/bin/env python

# The Expat License
#
# Copyright (c) 2018, Shlomi Fish
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in the Software without restriction, including without limitation the rights
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
# SOFTWARE.

from six import print_


class State:
"""docstring for State"""

def __init__(self):
self.cur = [0, 0]
self.dir1 = 0
self.n = 0

def dup(self):
ret = State()
ret.cur = [x for x in self.cur]
ret.dir1 = self.dir1
ret.n = self.n
return ret

def delta(self, o):
ret = self.dup()
ret.cur[0] -= o.cur[0]
ret.cur[1] -= o.cur[1]
ret.dir1 -= o.dir1
ret.n -= o.n
return ret

def apply_delta(self, o):
ret = self.dup()
ret.cur[0] += o.cur[0]
ret.cur[1] += o.cur[1]
ret.dir1 += o.dir1
ret.n += o.n
return ret


s = State()
Cache = {}
dirs = [(0, 1), (1, 0), (0, -1), (-1, 0)]
maxdepth = 10
mn = 500
STEP = 100000000
printed = False


def dragon(depth, seq):
global Cache, maxdepth, s
init = s.dup()
key = (depth, seq, (s.dir1 & 3))
if key in Cache:
val = Cache[key]
if val.n + s.n < mn:
s = s.apply_delta(val)
return
for c in seq:
if c == 'a':
if depth < maxdepth:
dragon(depth+1, 'aRbFR')
elif c == 'b':
if depth < maxdepth:
dragon(depth+1, 'LFaLb')
elif c == 'R':
s.dir1 += 1
elif c == 'L':
s.dir1 -= 1
elif c == 'F':
s.n += 1
s.cur[0] += dirs[s.dir1 & 3][0]
s.cur[1] += dirs[s.dir1 & 3][1]
else:
raise BaseException("unknown")
if s.n >= mn:
if s.n == mn:
global printed
if not printed:
print_("cur = %d,%d" % (s.cur[0], s.cur[1]))
printed = True
return
Cache[key] = s.delta(init)


dragon(0, 'Fa')
maxdepth = 50
mn = 1000000000000
s = State()
Cache = {}
printed = False
dragon(0, 'Fa')

0 comments on commit 87c71ce

Please sign in to comment.