however, I suspect the answer you are about to provide may be specific to this scenario.
In general, my answer is: Don't return error codes. Either: return undef or an empty string for failure; or better: just die or Carp::croak().
My reasoning comes back to my first question. What are you going to do with the error codes?
There are essentially only 3 things you can do with exceptional circumstances .
If there is nothing that you can do to recover, and so must die, there is no point in converting the error conditions into error codes within the routine, only to have the calling code (at every place the routine is called!) have to convert those error codes back to meaningful error messages in order to report them. (Whether to the terminal or log.)
That is, the program continues to run, but this particular operation is abandoned and the program returns to some previous known-good state.
For the most part, the caller doesn't need to know what went wrong, only that something went wrong. A simple boolean return (undef or '') indicates this just as well and more easily. But even this complicates the calling code more than catching an exception.
In addition, the immediate calling code can choose to ignore the possibility of exceptions and push the resposibility of hadnling them to its caller when that makes sense.
Under some, usually very limited circumstances, recovery may be possible. An example might be an interactive program (CLI or GUI or WUI (web user interface), where the subroutine is validating user input.
Again, the exception model simplifies the calling code, because you can return the error text from the the die to inform the user of the problem, rather than having to convert the error code back to a meaningful message at every call site.
The error code return model made some sense in C and similar languages when exception handling wasn't available. But it imposes clumsy, verbose error handling code at every call site that detracts and distracts from the normal (non-exceptional) flow of operations. It also tends to get "overlooked" when the pressure is on, and is a bitch to debug when it does bite.
The exception handling model (used properly):
By writing your subroutines to die (or better Carp::croak()), when given garbage input, you both simplify the calling code and ensure that exceptional circumstances are either dealt with by the caller, or at least some meaningful error message is reported when the occur and are not handled.
Basically, error codes are just an level of indirection that serves no good purpose.
In reply to Re^5: return from subfunction
by BrowserUk
in thread return from subfunction
by fidesachates
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |