Python 为什么要使用函数嵌套函数

2017-02-20 17:47:47 +08:00
 SlipStupig

看一些代码会写成函数中嵌套函数,例如:


 def func():
     def new_func():
          return 1
    a = new_func()

这种写法和 lambda 和单独创建一个 function 有什么区别或优势吗?

7514 次点击
所在节点    Python
21 条回复
WangYanjie
2017-02-20 17:52:17 +08:00
clino
2017-02-20 17:54:57 +08:00
对啊,要写闭包的时候很好用的
RadishWind
2017-02-20 18:03:54 +08:00
查看一下柯里化的定义,这样写返回的新函数能够保持当时的状态,而且能够达到惰性求值的效果(用到这个函数的时候再处理传入的参数)
ansheng
2017-02-20 18:07:03 +08:00
例如装饰器传参,就是多层嵌套的函数,
picasso250
2017-02-20 18:18:23 +08:00
因为 lambda 的限制
firstway
2017-02-20 21:07:01 +08:00
你的例子确实 lambda 也可以做到。但是下面的呢?

def func(x):
def new_func(y):
return x+y
return new_func

>>> a = func(10)
>>> a(3)
13
>>> a(5)
15
ic3z
2017-02-20 22:27:16 +08:00
也许是为了方便吧。脚本嘛
Yinz
2017-02-20 22:48:30 +08:00
额,其实我也不是很了解这两种用法的差异的,不过一不小心就写了出来 @firstway

In [1]: def func(x):
...: return lambda y:y+x
...:

In [2]: a = func(10)

In [3]: a(3)
Out[3]: 13

In [4]: a(5)
Out[4]: 15
will0404
2017-02-20 22:57:23 +08:00
@firstway 你的例子不合适啊。

>>> a = lambda x: lambda y: x + y
>>> b = a(10)
>>> b(3)
13
>>> b(5)
15
will0404
2017-02-20 23:08:38 +08:00
因为 lambda 是匿名的,我想区别应该是名字是否有意义,比如递归吧。

>>> def func(x, sum):
... if(x==0):
... return sum
... return func(x-1, sum + x)
...
>>> func(10, 0)
55

lambda 大概写不出上面这个递归?
fwrq41251
2017-02-20 23:35:47 +08:00
能省几个参数,函数的作用域小了
gamexg
2017-02-21 00:08:01 +08:00
一般是返回一个函数指针时用。一般外部固定了函数指针的参数,但是自己又需要传递给函数指针一些数据,这样嵌套函数可以使得内部函数可以访问外部函数的变量。关键字:闭包,需求的例子:装饰器。

不用 lambda 的原因是 lambda 限制太大,不方便。
est
2017-02-21 08:29:38 +08:00
这就是 meta 编程啊
enenaaa
2017-02-21 09:14:42 +08:00
lambda 你能多写几行么
lll9p
2017-02-21 09:44:52 +08:00
Python 里 lambda 只能写一行啊
drlalll
2017-02-21 10:14:32 +08:00
@gamexg
需要做到这个的话直接用指针不行吗?
gamexg
2017-02-21 10:30:52 +08:00
@drlalll 无法实现,像下面的装饰器例子:

https://gist.github.com/GameXG/ed84b114067fb4a7b398cb811a9241ca

需要将 @w(123) 的 123 传递给 fffff 函数,但是 fffff 函数是会被当作 hello3 参数给用户调用的,用户不会帮你把 123 传递进去,只能通过闭包的方式传递进去 123 .
wizardoz
2017-02-21 10:35:18 +08:00
lambda 写复杂的函数很麻烦啊
sadscv
2017-02-21 13:55:52 +08:00
这是一种嵌套函数的写法,有时候它和 lambda 没什么区别,但有些情况下它会实现一个闭包,所以我姑且认为楼主是想知道闭包的特性.
那么这里首先强烈建议楼主了解一下 namespace 与变量作用域的相关知识.
http://python.jobbole.com/81367/
如果只要了解闭包的概念,请参考这篇文章.
http://blog.csdn.net/marty_fu/article/details/7679297
如果想知道闭包的实现原理.那么你必须得明白函数调用过程.因为闭包本身就是调用一个函数反回另一个函数.
这里推荐 UCSB 的教程,提供了一个交互式的函数调用演示程序.共6个课程,每个课程都很短,但看完这些你大概能对函数调用帧栈有初步了解.
https://www.cs.ucsb.edu/~pconrad/cs8/topics.beta/theStack/01/
到现在你已经可以开始探究 python 在函数调用中如何精妙地完成参数传递.
http://www.jianshu.com/p/d00108741a18
如果能坚持到这里,那么你已经停不下来了...函数调用过程中所有涉及到的源码作者都给出了分析,看完之后应该什么都明白了
http://python.jobbole.com/83545/
以下链接可以看看,也许能帮助你理解源码.
http://www.cnblogs.com/hackerl/p/5985102.html
http://eli.thegreenplace.net/2012/03/23/python-internals-how-callables-work/
julyclyde
2017-02-26 14:16:47 +08:00
一种劣习,让函数变成有状态的,或者叫不完全依赖于字面输入,还依赖一个隐藏输入的东西

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/341835

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX