#!/usr/bin/perl

use 5.040;

use Time::HiRes qw( clock_gettime clock_getres CLOCK_REALTIME clock_nanosleep );

my $obj = int (1000+rand()*10_000_000);
my @f;
$f[0] = 1+int rand()*100_000;
for (1 .. 1+int($obj/1000)){
    $f[$_] = 1+int rand()*100_000;
}

### Intento de solución: acercarse a $obj por debajo con aritmética simple

my $err = 8e99;
my $sum;
my $minerr = 9e99;
my $str;
while ($err){
    $sum = 0;
    $str = "";
    for my $t (@f){
	my $i = int rand()*4;

	if ($i == 0 || $i == 1){    
	    if ($obj > $sum){
		$sum += $t;
		$str .= "+$t";
	    }else{          # 0j0 si $sum == $obj no hay opción: se acerca por debajo 
		$sum -= $t;
		$str .= "-$t";
	    }
	}elsif ($i == 2){
	    $sum *= $t;
	    $str .= "*$t";
	}elsif ($i == 3){
	    $sum /= $t;
	    $sum = int $sum;
	    $str .= "/$t";
	}
    }

    $err = $obj-$sum;
    if ($err > 0 && $err < $minerr){
	$minerr = $err;
	say "Problema de alcanzar $obj con ",scalar(@f)," términos:";
	say "                     $sum conseguido";
	say "falta = $err, un ", 100*($obj-$err)/$obj, "% ya logrado";
	say "$str";
	say scalar(localtime()),"\n";
	# Read the POSIX high resolution timer.
#	if ($high != 0) {
#	    $high2 = clock_gettime(CLOCK_REALTIME) - $high;
#	    $high = 0;
#	}elsif ($high2) {
#	    $high = clock_gettime(CLOCK_REALTIME) - $high2;
#	    $high2 = 0;
#	}
#	say "Tiempo de generación:  $high  $high2";
    }
    clock_nanosleep(CLOCK_REALTIME, 1e6);          # 1e6 es el más típico
}

exit 2;

