in reply to Re: resetting a foreach loop!
in thread resetting a foreach loop!

Your average specifically checks if no arguments are provided, but doesn't actually handle that situation. Fixed:

sub average { if (@_) { my $sum; for (@_) { $sum += $_; } return $sum/@_; } else { return undef; } }

Same, but shorter:

sub sum { my $sum; $sum += $_ for @_; $sum } sub avg { @_ ? sum(@_)/@_ : undef }

Replies are listed 'Best First'.
Re^3: resetting a foreach loop!
by pryrt (Abbot) on Nov 17, 2017 at 19:36 UTC

    ++Indeed. Technically, the no-explicit-return version of the function returns 0 for an empty argument list, so it implictly handles the empty case. (I infer that the OP did the if(@_) just to prevent divide-by-zero.) But I agree that explicit undef is a better return value than relying on a default 0.

      Technically, the no-explicit-return version of the function returns 0 for an empty argument list

      I am aware of that, but they are relying undefined behaviour to do so[1], and it's a poor value to return.

      I infer that the OP did the if(@_) just to prevent divide-by-zero.

      That would actually have been a far better outcome!


      1. "If no return is found and if the last statement is an expression, its value is returned. If the last statement is a loop control structure like a foreach or a while , the returned value is unspecified. The empty sub returns the empty list."
        "If no return is found [and] the last statement is a loop control structure like a foreach or a while , the returned value is unspecified. ..."

        Does this apply to if-blocks? I don't think of if as a "loop control" structure.


        Give a man a fish:  <%-{-{-{-<