Skip to Main Content Skip to Search
Home |   Select Country  Choose Country  |  Contact Us  |  Cart Store 
Create Account | Log In
Products & Services Industries Academia Support User Community Company

 

Product Support

1103 - What Is the EVAL Function, When Should I Use It, and How Can I Avoid It?



What is the EVAL function?

The EVAL function is one of the most powerful, flexible, and potentially dangerous functions in MATLAB. EVAL is short for evaluate, which is exactly what the EVAL function does; it evaluates MATLAB expressions. You can use EVAL to execute from an M-file any command you could execute from the command prompt. Some of the more common uses for EVAL are
  • Loading and saving files with variable filenames
  • Executing system commands using the ! command
  • Executing arbitrary commands stored in a string variable

What problems can occur when I use the EVAL function?

Since EVAL is so powerful, it is easy to misuse the function. In a way, the EVAL function is a lot like global variables; both are tools that can be so useful, it is easier to use them than to search for a more elegant solution. There are two major drawbacks to the EVAL function; the former can be avoided if you use EVAL carefully. The drawbacks are:
  • EVAL can be used to alter arbitrary variables. In addition, two related functions which will be described in Section 11, EVALIN and ASSIGNIN, can be used to alter variables in different function workspaces. These functions can create bugs which are difficult to reproduce and nearly impossible to eliminate.
  • Functions which use the EVAL function cannot be translated into C or C++ code using the MATLAB Compiler. The Compiler cannot determine, when it is trying to compile the EVAL call, what will be evaluated.
Below are some basic examples of how to use EVAL, along with examples which avoid using EVAL but perform the same tasks. These examples will provide you with the ability to create just about any expression in MATLAB.

Example 1: Saving data to incrementally numbered ASCII files

EVAL CODE:

rootname = 'file';      % Root filename
        extension = '.dat';     % Extension for the files
        % The following loop concatenates the root filename,
        % an integer value, and the extension to create the 
        % file in which the data is saved.
        for data = 1:10
          filename = [rootname, num2str(data), extension];
          eval(['save ', filename , ' data -ascii'])
        end
      
NON-EVAL CODE:
%Use the functional form of SAVE
        rootname = 'file';      % Root filename
        extension = '.dat';     % Extension for the files
        % The following loop concatenates the root filename,
        % an integer value, and the extension to create the 
        % file in which the data is saved.
        for data = 1:10
          filename = [rootname, int2str(data), extension];
          save(filename,'data','-ascii')
        end
      

Example 2: Load data from the ASCII files generated in Example 1

EVAL CODE:
rootname = 'file';      % Root filename
        extension = '.dat';     % Extension of the files
        % The following loop concatenates the root filename,
        % an integer value, and the extension to create the 
        % file to be loaded.
        for data = 1:10
          variable = [rootname, int2str(data)];
          filename = [variable, extension];
          eval(['load ', filename])
          eval(['data', num2str(data), ' = ', variable, ';'])
          eval(['clear ', variable])
        end
      
NON-EVAL CODE:

While this section of code does not use EVAL it is also not compilable, since it uses the ASSIGNIN function.

%Use ASSIGNIN
        rootname = 'file';      % Root filename
        extension = '.dat';     % Extension of the files
        % The following loop concatenates the root filename,
        % an integer value, and the extension to create the 
        % file to be loaded.
        for data = 1:10
          variable = [rootname, int2str(data)];
          filename = [variable, extension];
          load(filename)
          assignin('base',['data', num2str(data)], variable)
          clear(variable)
        end
NON-EVAL CODE PART 2:

This section of code has slightly different functionality from the previous two sections, but unlike those sections it can be compiled.

rootname = 'file';      % Root filename
        extension = '.dat';     % Extension of the files
        %Here we assign all of the values loaded into the 
        %array called "var".  This allows us to avoid the 
        %EVAL and ASSIGNIN commands.
        for data = 1:10
           filename = [rootname,num2str(data), extension];
           variable = load(filename);
           var(data) = variable;
           clear variable   
        end     
 
 

Example 3:Using EVAL to print to random files

EVAL CODE:
rootname = 'fig';                     % Root filename
        for x = 1:10
          figure(x)
          plot(rand(x))                       % Random plot
          filename = [rootname, int2str(x)];  % Concatenate the
                                              % root filename and
                                              % the integer.
          eval(['print -dps',filename])       % Print to the file
                                              % using EVAL
        end 
      
NON-EVAL CODE:
%Use the functional form of PRINT
        rootname = 'fig';                     % Root filename
        for x = 1:10
          figure(x)
          plot(rand(x))                       % Random plot
          filename = [rootname, int2str(x)];  % Concatenate the
                                              % root filename and
                                              % the integer.
          print(filename,'-dps')              % Print to the file
                                              % w/o using EVAL
        end 
      

Example 4: Reassign the contents of a variable

In this case, you are prompted to enter the name of a variable. In order to use the data inside the M-file, you must assign the contents of the unknown variable to a known variable. This is an instance where the EVAL function is the only sensible way to code this.

Note that this is a very dangerous example. If the user entered the string "clear all" when the INPUT statement asks for a variable name, all the variables in the MATLAB workspace will be cleared. As Example 5 shows below, any MATLAB command can be executed in this manner. Unless you trust your users not to use commands like EXIT, CLEAR ALL", or the like, you may want to use the EXIST function to test that the string you want to evaluate is the name of a variable in the workspace.

var = magic(10);
         
        <-----------------  fun1.m  ----------------->
         
        % Enter 'var' as the variable name.
        variablename = input('Enter the name of the variable:  ','s');
        a = eval(variablename);  % Reassign the contents of
                                 % variablename to a.
        b = 2*a;
        mesh(b)
      

Example 5: Evaluate a MATLAB command

This example generates a Bode plot using a numerator and a denominator you enter.

EVAL CODE:
num = input('Enter the numerator: ');
        den = input('Enter the denominator: ');
        eval(['bode(',mat2str(num),',',mat2str(den),')'])
      
NON-EVAL CODE:
%Use FEVAL
        fun1 = 'bode';
        num = input('Enter the numerator: ');
        den = input('Enter the denominator: ');
        feval(fun1,num,den)

Example 6: Converting a numeric string to its numeric value

Note that there are two versions of STR2NUM. Both do the same thing but are implemented differently. One version of STR2NUM is written in M and is used when you call STR2NUM from M-code. It uses EVAL to handle translating MATLAB expressions into numbers. For example, the following function call executes "eval('1/2')":

str2num('1/2'); 

The other STR2NUM is included in the Math Library and is linked against whenever you generate C-code with the MATLAB Compiler. While the M-code version of STR2NUM uses EVAL, the version of STR2NUM included with the Math Library doesn't. This means that you can compile STR2NUM into C-code as long as it does not accept an expression to be evaluated. The NON-EVAL example below uses the version of STR2NUM written in M-code.


EVAL CODE:
x = '1';
        y = eval(x);
      
NON-EVAL CODE:
%Use STR2NUM
        x = '1';
        y = str2num(x);    

Example 7: Performing error handling

The statement used in the EVAL section of this example:
eval('B = A','disp(''A is undefined'')')

contains two inputs. The underlying concept here is that EVAL will try the first input, and if an error is detected, it will then use the second input. This method is referenced as eval(<try>,<catch>). The first input, B = A is the primary input which EVAL will attempt to evaluate first. If an error is detected then the second input, disp(''A is undefined''), is evaluated.


EVAL CODE:
% CASE 1: A is not defined
        clear all
        eval('B = A','disp(''A is undefined'')')
        % The message "A is undefined" is displayed

        % CASE 2: A is defined
        A = 1;
        eval('B = A','disp(''A is undefined'')')
        % The following is displayed in the command window:
        %
        % B =
        %      1
      
NON-EVAL CODE:
%Use TRY - CATCH
        % CASE 1: A is not defined
        clear all
        try 
           B = A
        catch 
           disp('A is undefined')
        end
        % The message "A is undefined" is displayed

        % CASE 2: A is defined
        A = 1;
        try 
           B = A
        catch 
           disp('A is undefined')
        end
        % The following is displayed in the command window:
        %
        % B =
        %       1
      

Closing remarks on the examples

Examples 1 - 4 use EVAL to concatenate a series of strings together to form a MATLAB expression. EVAL substitutes the value of the variable or variables into the expression, then evaluates the entire expression. This is the most basic use of the EVAL function.
Note that in the examples, the numeric values are converted to strings using the NUM2STR function. This is necessary because EVAL only accepts string inputs. Another reason to convert the numbers to strings is because everything inside the brackets must be of the same type to be concatenated. Matrices in MATLAB are either string or numeric.

Example 6 is useful when using editable text blocks for numeric input. Since an editable text block stores its input in its String property, when you do a get(h,'String'), a string is returned. By using EVAL, it is easy to convert the string to the numeric value.

Another important characteristic of EVAL is the single quote ('). Example 7 illustrates this. When a single quote is nested in a string, it must be defined by using two single quotes, ''. Note that this is not a double quote. Keeping track of quotes is extremely important. EVAL is often used to create very complicated expressions, which have many single quotes in a row. For example,

eval('disp(''''''This is a string'''''')')

displays

    This is a string
in the command window.

There is one trap of which you should be aware, which is using the EVAL statement when it is not necessary. For example:

eval(['title(''Plot #', num2str(1), ''')'])
      
This is the same as the following:
title(['Plot #',num2str(1)])
The latter is much easier to read and write.

Functions similar to EVAL

Other MATLAB functions similar to EVAL are FEVAL, EVALIN, ASSIGNIN, UNIX, and DOS. FEVAL is used to evaluate MATLAB functions. For example, example 5 can be re-written as:
feval('bode',num,den)
The first input is the name of the function to be evaluated, and subsequent inputs are the inputs to the function. As you can see, this is clearer than:
eval(['bode(',mat2str(num),',',mat2str(den),')'])
EVALIN is used in the same manner as EVAL, except that it has an additional argument which allows you to specify in which workspace the expression you pass to it should be evaluated. It can be used to pass results from one function to the workspace of the function which called it or to the base MATLAB workspace, which can be useful if you require information from a subfunction for another function.

ASSIGNIN allocates to a variable whose name you specify a certain value. The variable is created (or overwritten) in either the workspace of the function which called the function containing ASSIGNIN or the base workspace. With ASSIGNIN, as with EVAL and EVALIN, it is easy to create very subtle and hard to eliminate bugs by changing values of variables in an entirely different function from the one in which they were created.

UNIX and DOS are used to open UNIX or DOS shells to execute the given command. For example:
file = input('Enter the file name and extension: ','s');
        unix(['lpr -Pprinter ',file])
        dos(['copy /b ',file', lpt1'])
      
This can be rewritten using eval:
file = input('Enter the filename and extension: ','s');
        eval(['!lpr -Pprinter ',file])
        eval(['!copy /b ',file,' lpt1'])
      
The only difference between using UNIX or DOS and using EVAL is that with EVAL you must use the bang function (!) to execute a shell command. The UNIX and DOS commands do this automatically, so it is best to use these commands when shelling out to the operating system.

Contact support
E-mail this page
Print this page