How can I create function pointers from a string input in MATLAB?

JP. picture JP. · Nov 30, 2009 · Viewed 10k times · Source

If I use the inline function in MATLAB I can create a single function name that could respond differently depending on previous choices:

if (someCondition)
  p = inline('a - b','a','b');
else
  p = inline('a + b','a','b');
end

c = p(1,2);
d = p(3,4);

But the inline functions I'm creating are becoming quite epic, so I'd like to change them to other types of functions (i.e. m-files, subfunctions, or nested functions).

Let's say I have m-files like Mercator.m, KavrayskiyVII.m, etc. (all taking a value for phi and lambda), and I'd like to assign the chosen function to p in the same way as I have above so that I can call it many times (with variable sized matrices and things that make using eval either impossible or a total mess).

I have a variable, type, that will be one of the names of the functions required (e.g. 'Mercator', 'KavrayskiyVII', etc.). I figure I need to make p into a pointer to the function named inside the type variable. Any ideas how I can do this?

Answer

gnovice picture gnovice · Nov 30, 2009

Option #1:

Use the str2func function (assumes the string in type is the same as the name of the function):

p = str2func(type);  % Create function handle using function name
c = p(phi, lambda);  % Invoke function handle

NOTE: The documentation mentions these limitations:

Function handles created using str2func do not have access to variables outside of their local workspace or to nested functions. If your function handle contains these variables or functions, MATLAB® throws an error when you invoke the handle.

Option #2:

Use a SWITCH statement and function handles:

switch type
  case 'Mercator'
    p = @Mercator;
  case 'KavrayskiyVII'
    p = @KavrayskiyVII;
  ...                    % Add other cases as needed
end
c = p(phi, lambda);      % Invoke function handle

Option #3:

Use EVAL and function handles (suggested by Andrew Janke):

p = eval(['@' type]);  % Concatenate string name with '@' and evaluate
c = p(phi, lambda);    % Invoke function handle

As Andrew points out, this avoids the limitations of str2func and the extra maintenance associated with a switch statement.