1、函数
1.1 自定义函数
函数的定义用def语句,def是可执行语句,在被调用之前是不存在的,只需要保证调用时,所需函数已经声明定义即可。
示例:
def my_func(message):
print('Got a message: {}'.format(message))
# 调用函数
my_func('Hell World')
# 输出
Got a message: Hello World
其中:
——def是函数的声明;
——my_func是函数的名称;
——括号里的message是函数的参数(形参),可以传递多个参数,而且可以设置默认值,比如message=‘hi’,如果实参没有传递参数,那么参数默认为hi。同时,参数的传递可以接受任意数据类型;
——调用函数时传递的是实参,与形参一一对应,可以传递列表
1.2 函数的嵌套
即函数里面又有函数
示例:
def f1():
print('hello')
def f2():
print('world')
f2()
# 调用
f1()
# 输出
hello
world
这样做的好处:
1.函数嵌套可以保证内部函数的隐私。内部函数只能被外部函数所调用和访问,不会暴露在全局作用域,因此,如果函数内部有一些隐私数据,就可以使用函数嵌套,将其封装在内部函数中,只通过外部函数来访问;
2.合理的使用函数嵌套可以提高程序的运行效率。
1.3 函数变量作用域
(1)如果变量是在函数内部定义的,就称为局部变量,一旦函数执行完毕,就会被收回,无法访问;全局变量是定义在整个文件层次上的,即函数外部。
(2)python解释器会默认函数内部的变量为局部变量,可以使用global 全局变量名
使其当做局部变量使用
类似的,对于嵌套函数来说,内部函数可以访问外部函数定义的变量,需要变为nonlocal 变量名
1.4 闭包
——闭包和嵌套函数类似,区别就在于闭包的玩不函数返回的是一个函数,而不是具体的值,返回的函数通常赋予一个变量,这个变量可以在后面继续执行调用
示例:
def nth_power(exponent):
def exponent_of(base):
return base ** exponent
# 返回值是exponent_of函数
return exponent_of
square = nth_power(2)
cube = nth_power(3)
# 计算2的平方
print(square(2))
# 计算2的立方
print(cube(2))
# 输出
4
8
1.5 匿名函数
1.5.1 lambda函数
lambda argument1, argument2...argumentN: expression
——其中lambda本身是一个表达式,类似于一系列的公式,可以当做函数的参数,argument表示参数,expression表示含参数的表达式
示例:
square = lambda: x**2
square(3)
输出:
9
1.5.2 与其他函数的结合使用
(1)map()函数
——此函数直接由C语言编写,运行时不需要通过python解释器间接调用,并且内部做了很多优化,所以运行速度很快
squared = map(lambda x: x**2, [1, 2, 3, 4, 5])
——map(function, iterable)的第一个参数是函数对象,第二个是一个可以遍历的集合,表示对iterable中的每个元素都运用function这个函数。
(2)filter()函数
——与map()函数类似,filter(function,iterable),表示对iterable中的每个元素,都是用function判断,并返回True或者False,最后将返回True的元素组成一个新的可遍历的集合。
示例:
l = [1, 2, 3, 4, 5]
# 返回一个列表中所有的偶数
new_list = filter(lambda x: x%2==0,1)
(3)reduce(function, iterable)
——此函数通常用来对一个集合做一些累积操作,function也是一个函数对象,规定它有两个参数,表示对iterable中的每个元素以及上一次调用后的结果运用function计算,最后返回的是一个单独的数值。
示例:
l = [1, 2, 3, 4, 5]
# 计算列表元素的乘积
product = reduce(lambda x,y: x*y, l)
2、面向对象
2.1基本属性
class Document():
def __init__(self, title, author, context):
print('init function called')
self.title = title
self.author = author
self.__context = context # __ 开头的属性是私有属性
def get_context_length(self):
return len(self.__context)
def intercept_context(self, length):
self.__context = self.__context[:length]
harry_potter_book = Document('Harry Potter', 'J. K. Rowling', '... Forever Do not believe any thing is capable of thinking independently ...')
print(harry_potter_book.title)
print(harry_potter_book.author)
print(harry_potter_book.get_context_length())
harry_potter_book.intercept_context(10)
print(harry_potter_book.get_context_length())
print(harry_potter_book.__context)
########## 输出 ##########
init function called
Harry Potter
J. K. Rowling
77
10
——Document为类名,一般类名首字母大写,类中函数称为方法。
——方法__init__()为构造函数,每次实例化对象时就会自动执行,方法中有四个形参,self, title, author, context,称为类的属性,其中self自动传递且必不可少,是一个指向实例本身的引用,让实例能够访问类中的属性和方法,必须放在所有形参前面;
——函数中以self为前缀的变量都可供类中的所有方法使用,还可以通过类的任何实例来访问这些变量。self.title = title获取存储在形参name中的值,并将其存储在变量name中,然后该变量被关联到当前创建的实例。
——以__开头的属性为私有属性,只能在类的函数中进行访问和修改。
——全大写表示类中的常量,在类中用self.常量名
调用,在类外使用类名.常量名
调用。
2.2 继承
class Entity():
def __init__(self, object_type):
print('parent class init called')
self.object_type = object_type
def get_context_length(self):
raise Exception('get_context_length not implemented')
def print_title(self):
print(self.title)
class Document(Entity):
def __init__(self, title, author, context):
print('Document class init called')
Entity.__init__(self, 'document')
self.title = title
self.author = author
self.__context = context
def get_context_length(self):
return len(self.__context)
class Video(Entity):
def __init__(self, title, author, video_length):
print('Video class init called')
Entity.__init__(self, 'video')
self.title = title
self.author = author
self.__video_length = video_length
def get_context_length(self):
return self.__video_length
harry_potter_book = Document('Harry Potter(Book)', 'J. K. Rowling', '... Forever Do not believe any thing is capable of thinking independently ...')
harry_potter_movie = Video('Harry Potter(Movie)', 'J. K. Rowling', 120)
print(harry_potter_book.object_type)
print(harry_potter_movie.object_type)
harry_potter_book.print_title()
harry_potter_movie.print_title()
print(harry_potter_book.get_context_length())
print(harry_potter_movie.get_context_length())
########## 输出 ##########
Document class init called
parent class init called
Video class init called
parent class init called
document
video
Harry Potter(Book)
Harry Potter(Movie)
77
120
——子类继承父类时,它将自动获得另一个类的所有属性,同时还可以定义自己的属性和方法,其中子类括号里必须传入父类的名称。
——在子类中显式地调用父类的构造函数才能在生成对象时执行父类的构造函数,执行顺序是先子类后父类。
——子类中与父类中的方法同名,可以覆盖掉父类中的函数,即可进行父类重写。
——子类的对象可以任意调用父类的方法。
2.3 抽象类与抽象函数
from abc import ABCMeta, abstractmethod
class Entity(metaclass=ABCMeta):
@abstractmethod
def get_title(self):
pass
@abstractmethod
def set_title(self, title):
pass
class Document(Entity):
def get_title(self):
return self.title
def set_title(self, title):
self.title = title
document = Document()
document.set_title('Harry Potter')
print(document.get_title())
entity = Entity()
########## 输出 ##########
Harry Potter
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
<ipython-input-7-266b2aa47bad> in <module>()
21 print(document.get_title())
22
---> 23 entity = Entity()
24 entity.set_title('Test')
TypeError: Can't instantiate abstract class Entity with abstract methods get_title, set_title
抽象类其实就是用来定义接口的,其本身作为父类存在,抽象函数定义在抽象类中,必须在子类中进行重写才能使用,只有通过子类继承,父类才能使用