rendered paste body#!/usr/bin/perl -w
use strict;
my %seen;
my $limit = shift or die;
my $count = 0;
my $num = 1;
my $cache_limit = 9**2*log($limit)/log(10);
$|++;
while ($num <= $limit) {
$count += &chain($num) == 89;
$num++;
#print "$num\r" if $num % 1000 == 0;
}
print "\n\n$count\n";
sub chain {
my $start = shift;
my $num = $start;
my @chain;
push @chain, $num;
while (1) {
my $s = 0;
$s += $_**2 for split "", $num;
$num = $s;
push @chain, $num;
return $seen{$num} if $start > $cache_limit;
last if $seen{$num} or $num == 1 or $num == 89;
}
if ($seen{$num}) { $num = $seen{$num} };
foreach (@chain) {
next if $_ > $cache_limit or $seen{$_};
$seen{$_} = $num;
}
#print "$start => ", ($seen{$num}||$num), "\n";
return $seen{$num} || $num;
}