第二周时间过得挺快,学习的内容也比第一周更多更难一些,感觉自己吸收的不是很好,希望通过博客的撰写来进行复习和巩固。首先,对大的框架来进行梳理,再对具体习题代码进行总结分析。
函数
1、为什么使用函数?
答:为了解决重复代码问题!编程大师Martin Fowler曾说过:“代码有很多种坏味道,重复是最坏的一种。”函数的存在就是将代码封装,方便以后遇到相同问题直接调用即可。
2、如何定义函数?
答:使用def name()来定义函数,括号内可以加函数的参数,函数的name命名遵循变量命名的规则。与数学上的函数形式类似,参数相当于自变量,return返回的值相当于因变量。
3、函数参数的使用?
答:当我们给一个函数的参数都设定了默认值,如果调用函数时没有传参,函数使用的默认值。当具体参数个数需要由调用者来决定时,可以使用可变参数,在定义函数时将*args(args随便取名,重要的是*)放入括号内,那么调用该函数时传入的参数个数就可以是0或者多个,如下:
def add(*args): total = 0 for val in args: total += val return total print(add()) print(add(1)) print(add(1, 2)) print(add(1, 2, 3)) print(add(1, 3, 5, 7))
4、函数命名冲突怎么办?
答?由于Python没有函数重载的概念,如果在同一.py文件中定义了2个同名函数,后面的定义会覆盖前面的定义。然而在实际的团队开发中,可能很多程序员都定义了同名函数,这时候可以使用import来导入指定模块调用你真正想使用的函数(每个python文件其实就代表了一个模块modul),如下:
module1.py
def foo(): print('hello, world!')
module2.py
def foo(): print('goodbye, world!')
test.py
from module1 import foo foo() # 输出hello, world! from module2 import foo foo() # 输出goodbye, world!
也可以在调用时对同名函数as命名:
test.py
import module1 as m1 import module2 as m2 m1.foo()# 输出hello, world!
m2.foo()# 输出goodbye, world!
需要说明的是,如果我们导入的模块除了定义函数之外还有可以执行代码,那么Python解释器在导入这个模块时就会执行这些代码,事实上我们可能并不希望如此,因此如果我们在模块中编写了执行代码,最好是将这些执行代码放入如下所示的条件中,这样的话除非直接运行该模块,if
条件下的这些代码是不会执行的,因为只有直接执行的模块的名字才是“__main__”。
modul3.py
def foo(): pass def bar(): pass # __name__是Python中一个隐含的变量它代表了模块的名字 # 只有被Python解释器直接执行的模块的名字才是__main__ if __name__ == '__main__': print('call foo()') foo() print('call bar()') bar()
test.py
import module3
#此时,不会执行模块中if语句里面的代码,因为模块的名字是module3而不是__main__
5、变量作用域
答:记住:Local -> Enclosed -> Global -> built_in顺序,即局部作用域 ->嵌套作用域 ->全局作用域 ->内置作用域,可以通过下面的例子体会:
def foo(): b = 'hello' def bar(): # Python中可以在函数内部再定义函数 c = True print(a) print(b) print(c) bar() # print(c) # NameError: name 'c' is not defined if __name__ == '__main__': a = 100 # print(b) # NameError: name 'b' is not defined foo()
我们可以使用global
关键字来指示foo
函数中的变量a
来自于全局作用域,如果全局作用域中没有a
,那么下面一行的代码就会定义变量a
并将其置于全局作用域。同理,如果我们希望函数内部的函数能够修改嵌套作用域中的变量,可以使用nonlocal
关键字来指示变量来自于嵌套作用域。
def foo(): global a a = 200 print(a) # 200 if __name__ == '__main__': a = 100 foo() print(a) # 200
在实际开发中,我们应该尽量减少对全局变量的使用,因为全局变量的作用域和影响过于广泛,可能会发生意料之外的修改和使用。事实上,减少对全局变量的使用,也是降低代码之间耦合度的一个重要举措,同时也是对迪米特法则的践行。
建议以后定义函数直接如下写法:
def main(): # Todo: Add your code here pass if __name__ == '__main__': main()