嵌套函数如何在MATLAB中工作?

时间:2014-10-07 14:32:16

标签: matlab nested-function

所以,我是applying for a job,需要弄明白how nested functions work。更具体地说,我想确切知道gnovice发布的以下示例是如何工作的。

问题是:

鉴于以下功能,在命令窗口中输入以下代码时输出是什么?

function fcnHandle = counter
  value = 0;
  function currentValue = increment
    value = value+1;
    currentValue = value;
  end
  fcnHandle = @increment;
end

f1 = counter();
f2 = counter();
output = [f1() f1() f2() f1() f2()];  %# WHAT IS IT?!

我没有申请工作,而且我能够找到问题的答案。我还可以直观地找到the answerMohsenthis question(在不调用内置函数的情况下查找矩阵的大小)。但是,除了听到阿尔伯特爱因斯坦的声音,我无能为力。

enter image description here

我认为documentation有点乱,所以如果有人能够解释它是如何工作的,我会很高兴。

3 个答案:

答案 0 :(得分:5)

嵌套函数的使用与memoization相关(有关其他阅读,请参阅:use nested functions to memoize costly functions),因为它利用parametric function handles存储创建时参数的值。

您需要注意两件事:

  1. counter()直接向嵌套函数

    返回一个函数句柄
    f1 = counter()
    f1 = 
       @counter/increment
    
  2. 嵌套函数将“保存”范围变量。有关详细信息,请参阅functions()

    s = functions(f1)
    s = 
         function: 'counter/increment'
             type: 'nested'
             file: '\\ic.ac.uk\homes\ok1011\MATLAB\counter.m'
        workspace: {[1x1 struct]}
    

    带有作用域工作区:

    s.workspace{1}
    ans = 
        fcnHandle: @counter/increment
            value: 0
    
  3. 基本上,counter()会将value初始化为零,对@counter/increment的连续调用将执行value = value+1;

    最后,@counter/increment已分配给f1,而f1()所有@counter/increment()在之前初始化的value上执行f2 = counter()。正在初始化workspace,会创建另一个计数器,其中包含单独保存的{{1}}。

答案 1 :(得分:4)

让我试试......

每次调用它的函数counter()都会创建一个唯一的函数句柄。此函数句柄是一个名为 increment 的函数的句柄,它接受自己的变量值,并将其递增1。

因此,如果调用两次,就像在代码(f1,f2)中每次都将返回相同的函数(增量)但不同的句柄。你有定义TWICE的功能。而且他们每个人现在都独立工作。由于此特定函数(增量)依赖于其计算的已保存内部值,因此您可以观察如何在代码示例中调用,输出[1 2 1 3 2]。

更好地区分差异的一个好方法是将函数重新定义为:

function fcnHandle = counter(val)
  value = val;
  function currentValue = increment
    value = value+1;
    currentValue = value;
  end
  fcnHandle = @increment;
end

并将其称为:

>> f1 = counter(0);
>> f2 = counter(1000);
>> output = [f1() f1() f2() f1() f2()]  %# WHAT IS IT?

现在,您将看到输出为[1 2 1001 3 1002]

现在更有意义吗?

创建此代码,因此它利用了函数句柄的这个属性(它同样的东西,但它被复制了两次)。

答案 2 :(得分:2)

整洁的运动。我以前从未使用带句柄的嵌套函数,所以这是我的思考过程: 我发现the manual中的这一段很有启发性:

  

嵌套函数可以使用三个来源的变量:

Input arguments

Variables defined within the nested function

Variables defined in a parent function, also called externally scoped variables
     

为嵌套函数创建函数句柄时,该句柄   不仅存储函数的名称,还存储函数的值   外部范围的变量。

因此,在示例中,函数counter将变量value设置为0,然后调用incrementincrement value存储在其句柄中,因此每次调用increment时,value都会递增并覆盖value=0的第一个定义}。

因此,输出为0加上调用increment的次数,即每次调用counter的给定实例时。

当你这样写:

f1 = counter();
f2 = counter();

您创建函数counter的两个单独实例,它们将独立递增。