Should Error Messages be Consistent for Different Implementations of the Same Functionality?

Disclaimer: I don't program with try-catch blocks and so don't know much about how they should be used.
Consider different ways of attempting to evaluate the hypergeometric function with invalid inputs. In all cases, the issue is that the second argument (-1) is greater than the second element of the first argument (-2).
Case 1:
Call hypergeom directly
try
hypergeom([1,-2],sym(-1),-1)
catch ME
ME
string({ME.stack.name}.')
end
ME =
MException with properties: identifier: 'symbolic:specfunc:InvalidArgument' message: 'Invalid arguments.' cause: {} stack: [6×1 struct] Correction: []
ans = 6×1 string array
"symbolicEngine.evalin2sym" "symbolicEngine.feval2sym_Infsingularity" "hypergeom" "LiveEditorEvaluationHelperEeditorId" "fevalMatlab" "fevalJSON"
The message tells us that that the input arguments are invalid (though it would be nice if the message actually said what caused the arguments to be invalid), and we see hypergeom somwhere in the call stack. Note that there are two flavors of hypergeom
which hypergeom -all
/MATLAB/toolbox/symbolic/symbolic/hypergeom.m /MATLAB/toolbox/symbolic/symbolic/@sym/hypergeom.m % sym method
which hypergeom([1,-2],sym(-1),-1)
/MATLAB/toolbox/symbolic/symbolic/@sym/hypergeom.m % sym method
and that we've called the sym method (if that's important, I have no idea).
Case 2:
Define a symbolic expression and subs into that
syms t real
try
subs(hypergeom([1,-2],t,-1),t,-1)
catch ME
ME
string({ME.stack.name}.')
end
ME =
MException with properties: identifier: 'symbolic:kernel:DivisionByZero' message: 'Division by zero.' cause: {} stack: [4×1 struct] Correction: []
ans = 4×1 string array
"subs" "LiveEditorEvaluationHelperEeditorId" "fevalMatlab" "fevalJSON"
Now we get a divide by zero message, and there is no trace of hypergeom in the stack. How is one to figure out where the problem lies?
Case 3:
Define a symbolic function and evaluate at -1
f(t) = hypergeom([1,-2],t,-1);
try
f(-1)
catch ME
ME
string({ME.stack.name}.')
end
ME =
MException with properties: identifier: 'symbolic:kernel:DivisionByZero' message: 'Division by zero.' cause: {} stack: [4×1 struct] Correction: []
ans = 4×1 string array
"symfun.subsref" "LiveEditorEvaluationHelperEeditorId" "fevalMatlab" "fevalJSON"
Same divide by zero, but no indication of hypergeom. subsref is now the culprit, presumably that's an overload to evaluate the symfun with paren indexing.
Case 4:
Define a different symbolic function and evaluate it for an input that should be the same as Case 3
fu(t) = hypergeom([1, -(2*t)/pi], -(2*t - pi)/pi, -1)
fu(t) = 
try
fu(sym(pi))
catch ME
ME
string({ME.stack.name}.')
end
ME =
MException with properties: identifier: 'symbolic:specfunc:InvalidArgument' message: 'Invalid arguments.' cause: {} stack: [4×1 struct] Correction: []
ans = 4×1 string array
"symfun.subsref" "LiveEditorEvaluationHelperEeditorId" "fevalMatlab" "fevalJSON"
Why isn't this result exaclty the same as Case 3?
I started down this path when I ran into the error w/o using try/catch
fu(sym(pi))
Error using indexing (line 213)
Invalid arguments.
I assume the error is shown for "indexing" because it comes from subsref? IDK. On the face of it, I had no idea where indexing would come into play and it took me a while to figure out the real problem was with the inputs to hypergeom.
From a user (at least this user) perspective, I'd expect the error message to be the same in all cases because all four cases are attempting to do the same thing: evaluate hypergeom for (invalid) prescribed inputs. Is that expectation unreasonable? Would it be feasible to make that happen using the multiple try/catch blocks that I assume are in play here?
And why isn't hypergeom shown in the call stack for Cases 2-4? Does that mean those cases never got to a call to hypergeom?

2 comentarios

dpb
dpb el 8 de Nov. de 2026 a las 12:37
Editada: dpb el 8 de Nov. de 2026 a las 17:03
While it would seem ideal for all cases to eventually get down to the base function "invalid arguments" error from the hypergeometric function, once you throw in Symbolic you've entered a wholly different world of evaluation sequencing to process the command syntax to (eventually, hopefully) get down to the root function. I suspect the wish is very unlikely to be possible if/when the parsing and building of the symbolic expressions to evaluate loses its bearings on the way to the forum as happens here.
Your observation that the call stack doesn't ever get to the root function itself pretty-much preculdes it throwing the error identically to the direct function evaluation. Now, whether any of these might be considered bugs in the evaluation engine or not, I've no insight into; certainly, one presumes that if the arguments weren't incorrect they might/should work?
For grins, let's try possible arguments for Case 2 to ensure it is OK...
syms t real
try
subs(hypergeom([1,-2],t,-1),t,-3)
catch ME
ME
string({ME.stack.name}.')
end
ans = 
So, somehow it may have looked ahead internally and error'ed on the way into the function, but it isn't the function itself that was evaluated yet. Probably only MathWorks could delve deeply enough to figure out if there were a way to then report that -- and then it might not be at all generic but only function specific.
I don't suppose it would hurt to file an enhancement request to see if MathWorks might investigate some; particularly I agree adding the "why" info in Case 1 should be relatively easy, for at least some cases. Poking at the symbolic hypergeom function file doesn't uncover just what it does eventually get down to...
S=which('-all','hypergeom')
S = 2×1 cell array
{'/MATLAB/toolbox/symbolic/symbolic/hypergeom.m' } {'/MATLAB/toolbox/symbolic/symbolic/@sym/hypergeom.m'}
dbtype(S{2},'15:15')
15 hSym = feval2sym_Infsingularity(symengine, 'symobj::map', args{1}, 'symobj::hypergeom', args{2}, args{3});
Good luck deciphering that... :>)
On the use of catch blocks, they're nothing truly special; the error is the same only that the use of the try...catch block prevents the calling code from immediately returning to the command line so can inspect the specific error in context and possibly be able to do something about it to continue.
syms t real
subs(hypergeom([1,-2],t,-1),t,-1)
Error using sym/subs (line 138)
Division by zero.
Can't force the online engine to continue after an error, but on local desktop at command line, following the above with
ME=lasterror
will return the identical ME error struct as you obtain in the catch block return variable.
Running locally, I confirmed that hypergeom is called in all four cases, i.e., there is no lookahead.
A little more digging revealed the difference between Cases 1 and 2. In case 1, we have direct call to hypergeom with symbolic number arguments, and so hypergeom attempts an evaluation. But in case 2 what we really have is hypergeom first called with a symbolic variable:
syms t
hypergeom([1,-2],t,-1)
ans = 
For the specified inputs, the returned object is a garden variety symbolic expression. subsing -1 for t in that expression does indeed result in a divide by zero. For some reason, I thought the substitution would go first and then hypergeom would evaluate, but that's not how it works and I don't know how I fooled myself into thinking that it would.
Case 3 is the same as 2, i.e., f(t) is the symbolic expression returned by hypergeom, so no surprise there (I guess this all would have been more obvious if I hadn't used semicolons to suppress output).
Case 4 is differentiated from Case 3 because fu(t) in 4 is NOT the same symbolic expression as f(t) in 3. Instead, fu(t) is an unevaluated call to hypergeom, and that leads down a different call path when evaluating fu(sym(pi)).

Iniciar sesión para comentar.

Respuestas (1)

syms t real
f(t) = hypergeom([1, -2], t, -1);
fu(t) = hypergeom([1, -(2*t)/pi], -(2*t - pi)/pi, -1);
runCase("Case 1", @() hypergeom([1, -2], sym(-1), -1));
Case 1 Hypergeometric evaluation failed: invalid parameters or a singular result. Underlying MATLAB error: Invalid arguments.
runCase("Case 2", @() subs(hypergeom([1, -2], t, -1), t, -1));
Case 2 Hypergeometric evaluation failed: invalid parameters or a singular result. Underlying MATLAB error: Division by zero.
runCase("Case 3", @() f(-1));
Case 3 Hypergeometric evaluation failed: invalid parameters or a singular result. Underlying MATLAB error: Division by zero.
runCase("Case 4", @() fu(sym(pi)));
Case 4 Hypergeometric evaluation failed: invalid parameters or a singular result. Underlying MATLAB error: Invalid arguments.
function runCase(label, operation)
fprintf("\n%s\n", label);
try
result = operation();
disp(result);
catch ME
fprintf(2, "Hypergeometric evaluation failed: invalid parameters or a singular result.\n");
fprintf(2, "Underlying MATLAB error: %s\n", ME.message);
end
end

Productos

Versión

R2026b

Etiquetas

Preguntada:

el 7 de Nov. de 2026 a las 23:33

Respondida:

el 9 de Nov. de 2026 a las 6:53

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by