in reply to Re: Simple add and multiply subroutines
in thread Simple add and multiply subroutines
BTW, if you're really wanting to cut down on duplicated code and don't mind torturing the language a bit, you can do this:
#!/usr/bin/perl -- use strict; use warnings; my $op = shift @ARGV; my $minmax = '$result ? $_[0] : $_[1];'; my $settruth = '$result ? 1 : 0;'; my %ops = ( 'add' => { 'op' => '+' }, 'multiply' => { 'op' => '*' }, 'subtract' => { 'op' => '-' }, 'divide' => { 'op' => '/' }, 'lesser' => { 'op' => '<' }, 'greater' => { 'op' => '>' }, 'power' => { 'op' => '**' }, 'xor' => { 'op' => '&&', 'pre' => '$_[0] = ! $_[0];' }, 'all' => { 'op' => '&&', 'post' => $settruth }, 'none' => { 'op' => '||', 'post' => $settruth, 'last' => '$tot + = ! $tot; $tot += 0;' }, 'any' => { 'op' => '||', 'post' => $settruth }, 'min' => { 'op' => '<', 'post' => $minmax }, 'max' => { 'op' => '>', 'post' => $minmax }, 'mean' => { 'op' => '+', 'last' => '$tot /= scalar (@_ + 1);' + }, 'geomean' => { 'op' => '*', 'last' => '$tot = $tot ** ( 1 / scal +ar (@_ + 1) );' }, 'equal' => { 'op' => '-', 'post' => '$result = $result ? 0 : $ +_[1];', 'last' => 'local $" = "||"; $tot = 1 if 0 == $tot && 0 == eval + "@_";'} ); sub make_op { my $op = shift; my $result = 0; $ops{$op}{'sub'} = sub { ( eval $ops{$op}{'pre'} ) if defined $ops{$op}{'pre'}; $result = ( eval $_[0] . $ops{$op}{'op'} . $_[1] ) + 0; $result = ( eval $ops{$op}{'post'} ) if defined $ops{$op}{'pos +t'}; return $result; }; } sub do_op { my $op = shift; my $tot = shift; make_op( $op ) unless ( exists $ops{$op}{'sub'} && defined $ops{$op}{'sub'} && ref $ops{$op}{'sub'} eq 'CODE' ); foreach ( @_ ) { $tot = $ops{$op}{'sub'}( $tot, $_ ); } if ( exists $ops{$op}{'last'} ) { eval $ops{$op}{'last'}; } return $tot; } printf "%-0.03f\n", do_op( $op, @ARGV );
I know, I know... It's ugly to do from 1 to 3 evals for each iteration and possibly another one or two at the end. The data structures could have clearer names. At least only the op you need gets its sub created. I did say the language would be tortured a bit, didn't I? It's kind of a fun little toy, though.
|
|---|