#!/usr/local/bin/perl -w
use strict;
my ($nume,@x,@o,@opts,@sol,$i,$j,$result,$resultant,$ind,$total);

if (@ARGV<2){
print <<EOT;
    El programa calcula que operaciones sobre argv[1] números
      producen como resultado argv[2] o la mejor aproximación.
      Usage: $0 < número de inputs > < número resultante > 
EOT
      exit;
}else{
    $nume = $ARGV[0];
    if ($nume+0 ne $nume) { die "Not numeric argv[1]: $!"; } 
    $total = $ARGV[1];
    if ($total+0 ne $total) { die "Not numeric argv[2]: $!"; } 
}
for (1..$nume){
    print "X$_ = ";
    $x[$_] = <STDIN>;
    chomp($x[$_]);
}
for (0..5){ $opts[$_]=$_; } #or 5
for (1..$nume){ $o[$_]=0; }
$i=1;
$resultant = 99999999;

for (;;){
   $i++;
   if ($i>$nume) {
         $i=1; #2
	 $o[1] = $opts[rand(2)];
   }else{	 
       $o[$i] = $opts[rand(@opts)];
   }

   $j = 1+rand($nume);
   ($x[$i],$x[$j]) = ($x[$j],$x[$i]);
   
   $result = 0;  #$x[1];
   for (1..$nume){
       if ( $o[$_] == 0 ) { 
            $result += $x[$_] ;
	    print "+" ;
       }elsif ( $o[$_] == 1 ) {
            $result -= $x[$_] ;
	    print "-" ;
       }elsif ( $o[$_] == 2 ) {
            $result *= $x[$_] ;
	    print "*" ;
       }elsif ( $o[$_] == 3 ) {
            if ($x[$_]>0){
	           $result /= $x[$_] ;
	    }
	    print "/" ;
       }elsif ( $o[$_] == 4 ) {
            if ($x[$_]>0){
              $result = $result % $x[$_] ;
	     }
             print "%" ;
       }elsif ( $o[$_] == 5 ) {
             $result = $result ** $x[$_] ;
	     print "^" ;
       } 
       print "$x[$_]";
   }
   print " = $result                       ";
   $ind = abs( $result - $total );
   if ($ind <= $resultant ){
       $resultant = $ind;
       print "\n";
       @sol = @o;
   }else { print "\r"; }
}

__END__
