我有个问题:
cons(a, b)
constructs a pair, andcar(pair)
andcdr(pair)
returns the first and last element of that pair. For example,car(cons(3, 4))
returns3
, andcdr(cons(3, 4))
returns4
.Given this implementation of cons:
def cons(a, b): def pair(f): return f(a, b) return pair
Implement
car
andcdr
.
我不懂这个功能。在
它有一个内部函数,并在返回中调用另一个函数。据我所知,内部函数是,这些函数应该依赖于它们上面的函数。在本例中,cons(..)
。在
但是函数没有使用a
或b
。为什么函数f
在那里?任务是实现car
和cdr
,并且应该给出函数f
。在
有人能解释一下这个功能吗?我该如何开始这项任务呢?在
这就是所谓的闭包。两个基本要素
pair
函数知道a
和{cons
函数返回一个函数,而不是一个值。你必须再次调用结果所以,当你调用
cons(a, b)
时,你得到了一个对a
和b
执行某些操作的函数,只有它还不知道是什么。你必须传递另一个函数。例如这和你的任务有什么关系还不清楚。我只假设对于},您需要元素
^{pr2}$car
,您只需要元素a
(头部),而对于{b
(列表的其余部分)。因此,函数只返回一个参数而忽略另一个参数。例如首先:Python函数对象是一类对象。一条
def
语句将生成一个新的函数对象,您可以使用函数名检索该对象:这意味着您也可以将该对象分配给其他名称,并且可以将它们作为参数传递给函数调用。然后,您可以稍后通过向引用添加
^{pr2}$(...)
来调用函数对象:函数名在当前命名空间中分配给。在模块中,这是全局变量,但在}然后将函数对象{}返回给调用者。在
cons
这样的函数中,名称作为局部名称添加。return pair
函数中的{而函数参数,如}。在
f
和a
和b
也是变量;如果将函数对象作为参数传入,则parameter_name(...)
将调用paramater_name
,并传入...
部分中的任何参数。f(a, b)
调用f
,并传入a
和{下一个要理解的项目是closures;闭包是附加到函数对象的额外名称空间,用于来自周围范围的变量。在
在下面的示例中,
spam
是bar
函数闭包中的一个名称:调用
foo()
返回一个新的函数对象,bar()
函数位于foo()
内。调用返回的函数对象生成'Vikings'
,即foo
函数中spam
变量的值。bar()
是如何获得访问权限的?通过关闭:因此,嵌套函数可以通过闭包访问周围范围内的名称。(旁注:存储在闭包中的不是值,而是变量。变量可以随时间而变化,就像以后访问名称的其他变量一样,将反映新值;如果
spam
稍后被更改,再次调用bar()
将返回新值)。在现在到您的函数:}:
cons()
创建一个内部函数pair()
,并且pair()
可以通过其闭包访问参数a
和{pair()
函数接受一个参数f
,然后调用该参数,传入a
和{print
时会发生什么。在print
也是一个函数,它是一个可以调用的对象,它将参数写入控制台,中间有空格:如果将其传递给
pair()
返回的pair()
函数,则可以看到f(a, b)
的作用:传递给}与{}完全相同。在
print
,被分配给f
,而{我们可以看到,调用了
print()
,因为这些值被写入控制台。但也可以创建一个返回新值的函数。假设有一个函数将两个数字相加并返回该值:我们可以直接调用函数,并返回
123
,也可以让pair_42_81()
为我们执行,并返回相同的结果。简单!在所有这些都是有效的,因为函数是对象,可以像其他变量一样传递,而且},并将使用这两个参数调用给定的对象
pair_42_81
在闭包中存储了a = 42
和{f
。在接下来是}返回{},那么}必须各自创建一个函数来传递给}。在
cdr()
和car()
,它们将返回对中的第一个或最后一个元素。如果cons(a, b)
产生{cdr()
和{pair()
,该函数将提取a
或{因此在每个函数中创建一个嵌套函数,并使用该函数使}调用}的工作,并返回该值。然后将调用结果返回给外部世界:
cdr()
和{pair()
。嵌套函数执行选择a
或{pair(return_first)
调用return_first(a, b)
,a
被返回,car()
可以将其返回给被调用方右侧:这同样适用于}:
pair(return_last)
,现在只返回{您可能对这些操作的背景感兴趣;
car
、cdr
和cons
来自LISP,其中cons a b
构造了一个带有两个指针的单元格(解释了名称),而car
(在IBM 704指令集LISP中,表示寄存器号的地址部分的内容)和cdr
(在704语言中,表示寄存器号的减量部分的内容)取这样一个单元的第一部分和剩余部分。见this Wikipedia article on the names。在cons
是一个接受两个参数a
和{pair
的函数。在函数
pair
接受一个函数f
作为一个参数,它使用两个参数。在f
返回31 = 2**2 + 3**3
注意
cons
的括号是(...)
的两倍,一次用于它自己的调用,另一次用于返回的函数调用。在请注意this answer以便能够调用
car(cons(2, 3))
。您可能还对Why would a program use a closure?感兴趣相关问题 更多 >
编程相关推荐