贡献者: addis
我们已经学了一些函数,现在来看如何自定义函数。Matlab 中定义了函数的文件叫做函数文件。函数文件同样以 “.m” 作为后缀名,文件中的第一个命令必须是 function
,用于定义主函数。文件名必须与主函数同名。文件中其他函数都是子函数。主函数可以调用子函数,子函数可以调用同文件中的其他子函数,但不能调用主函数,主函数和子函数都可以调用 Matlab 的内部函数或搜索路径下其他函数文件中的主函数。若函数文件在搜索路径下,其他 m 文件或 Command Window 中可以直接调用它的主函数。注意函数文件中的子函数不能从文件外被调用。
当我们调用某个 Matlab 函数时,若存不同的地方都定义了相同的函数名,那么 Matlab 使用以下优先级:
函数的 workspace 是独立的,即函数在执行的过程中,只能读写输入变量,函数内部定义的定量,以及全局变量(暂不介绍,不建议使用),而不能读取调用该函数的代码中的变量。相比之下,调用脚本相当于把脚本的代码直接插入到调用命令处,所以脚本中可以获取调用脚本的代码中的变量。注意函数只能通过函数文件定义,不能在脚本文件或命令行中定义。
函数句柄(function handle) 是一种特殊的变量类型,可用于定义一个临时的函数,也可传递到其他函数中。首先,对于已经存在的函数(包括函数文件定义的),可直接在函数名前面加 @
生成函数句柄
>> f = @sin; f(pi/2)
ans = 1;
若要将一个含有变量的表达式变为函数句柄,要在 @
后面用小括号指定函数句柄的变量
>> A = 3; w = 5; phi = pi/2;
>> f1 = @(x) A*sin(w*x+phi) + (2*x/pi).^2;
>> f1([0,pi/2])
ans =
3.0000 1.0000;
>> f2 = @(x,phi) A*sin(w*x+phi) + (2*x/pi).^2;
>> f2([0,pi/2],pi/2)
ans =
3.0000 1.0000;
以上的函数句柄在定义时用了逐个元素的幂运算 “.^
”,使函数句柄支持矩阵输入。其中 f1
的变量仅为 x
,f2
的变量为 x
和 phi
。注意如果在函数句柄定义后改变定义表达式中的变量,函数句柄不变。
>> A = 5; f1(0)
ans = 3.0000
有时候一些函数并不支持矢量运算,这时可以通过 arrayfun
函数来进行矢量运算,例如
>> f = @(x) x^2 + 1/x;
>> arrayfun(f, [1,2;3,4])
ans =
2.0000 4.5000
9.3333 16.2500
这样做相当于以下代码
f = @(x) x^2 + 1/x;
x = [1,2; 3,4];
ans = zeros(size(x));
for ii = 1:numel(x)
ans(ii) = f(x(ii));
end
自定义函数的格式为
[输出1, 输出2, ...] = function 函数名(输入1, 输入2, ...)
函数体
end
其中 函数名
是字母,数字和下划线的组合,例如 MyFun_123
,第一个字符不能是数字或下划线。若函数无变量,则小括号可省略。若函数无输出,则等号及方括号可省略,若只有一个输出,方括号也可省略。在一些情况下,如果 函数体
中没有使用某些输入变量,就可以把这些变量用 “~
” 符号代替。
函数的调用格式为
[输出1, 输出2, ...] = 函数名(输入1, 输入2,...);
调用函数时,如果输出变量个数少于函数定义中的输出变量个数,则函数仅输出前几个变量。若调用函数时不需要前面的某几个变量,也可用 “~
” 符号代替。
注意在函数体内部,输入变量是可以直接修改的,但不会影响函数外部的输入变量。这和 python 很不同。如果要把输入变量修改后的结果传出函数,需要在左边将其输出。同一个变量名可以既出现在输入列表中也在输出列表中。
调用函数时,输入变量的个数也可以少于函数定义中的输入变量,但是函数体内部必须要做出相应的措施以防止函数体使用未生成的变量。我们来看下面一个函数
function y = myfun(x, A, phi, y0)
if nargin < 4
y0 = 0;
if nargin < 3
phi = 0;
if nargin < 2
A = 1;
end
end
end
y = A*cos(x + phi) + y0;
end
注意函数体中使用了一个特殊的变量 nargin
,每当函数被调用时,这个变量的值将会等于输入变量的个数(同理,nargout
将等于输出变量的个数)。以上定义的函数允许 1-4 个输入变量,函数体中的 2-10 行根据 nargin
的值对没有输入的几个变量依次赋值。例如在命令行中调用该函数
>> myfun([0, pi/2])
ans = 1.0000 0.0000
>> myfun(0, 1, pi/2)
ans = 0.0000
调用函数时的一种特殊格式是,如果被调用的函数的输入变量是若干个没有空格的字符串,则可以省略括号,逗号和双引号。例如我们之前见过的 format
函数
>> format long;
和将在 “Matlab 画图” 中见到的
>> hold on; axis equal; xlabel x;
与脚本文件相同,若函数文件中执行了 return
命令,该函数的执行将立即终止,程序将执行调用该函数的命令的下一个命令。若该函数是单独被调用的(例如按开始按钮或在命令行被直接调用),则程序结束。