文章目录
面向对象编程
嵌套函数
一般在什么情况下使用嵌套函数:
- 封装——数据隐藏:外部无法访问嵌套函数
- 降低重复代码
- 闭包
def outer():
print("running outer")
def f2():
print("inner")
f2() # f2()要缩进到和定义f2()一样的位置
outer()
# isChinese可作为条件判断语句的一部分,内部的函数定义打印,外部的函数提供顺序和条件判断
def f01(isChinese, last_name, name):
def f02(a,b):
print("{0}{1}".format(a, b))
# if在这里属于f01()
if isChinese:
f02(last_name, name)
else:
f02(name, last_name)
f01(True, "蔡", "朝晖")
f01(False,"cai","grace")
nonlocal:用来声明外部函数的局部变量
global:用来声明全局变量
def f01():
b = 10
def f02():
nonlocal b # nonlocal必须在print之前使用,这样内部函数才能打印在外部被定义的的b
print("inner:",b)
b = 20 # 对b进行修改
global a # a 在函数内声明global,才可以在外部使用
a =1000
f02()
print("outer:",b)
f01()
print(a)
LEGB规则:
local(内部函数)→enclosed(外部函数)→global(全局变量)→built in(内置)
面向对象编程
面向过程(procedure oriented)和面向对象(object oriented)区别
解决简单问题用面向过程,解决复杂问题用面向对象。
对象的进化
简单数据到数组,再到结构体,再到对象(对象不光有数据,还有处理数据的方法)
类
类名首字母大写,多个单词采用驼峰原则
类名()指的是构造的方法:def__init__():
self表示的是类对象本身
self.name代表的是刚刚传进来的name值
class Student: # 类名一般蚕蛹首字母大写
def __init__(self,name,score): # self必须为第一个参数
self.name = name
self.score = score
def say_score(self): # 第一个参数必须是self
print("{0},{1}".format(self.name, self.score))
s1 = Student("gaoqi",100) # 定义参数的值,并将她赋值给s1
s1.say_score() # 引用函数(注意函数形式
构造函数__init__()
__init__方法:初始化创建好的对象,初始化指的是:给实例属性赋值
__new__方法 :用于创建对象,但我们一般无需重新定义该方法。
一个python对象包含如下部分:
- id码
- type(对象类型)
- value(对象的值):属性(attribute),方法(method)
init()规则:
-
名称固定
-
参数固定,第一个必须为self
-
构造函数通常用来初始化实例对象的实例属性,如下代码就是初始化实例属性:name和score
-
通过类名(参数列表)来调用构造函数,调用后,将创建好的对象返回给相应的变量。
实例属性
实例属性是从属于实例对象的属性,也称为实例变量。它的使用有以下几个要点:
- 实例属性一般在__init__()方法中通过如下代码定义:self.实例属性名 = 初始值
- 在本类的其它实例方法中,也是通过self进行访问:self.实例属性名
- 创建对象后,通过实例对象进行访问:
obj01=类名() # 创建对象,调用init初始化属性
obj01.实例属性名 = 值 # 可以给已有属性赋值,也可以新加属性
class Student: # 类名一般蚕蛹首字母大写
def __init__(self,name,score): # self必须为第一个参数
self.name = name
self.score = score
def say_score(self): # 第一个参数必须是self
print("{0},{1}".format(self.name, self.score))
s1 = Student("gaoqi",100) # 定义参数的值,并将她赋值给s1
s1.age = 18
print(s1.age)
s1.say_score() # 引用函数(注意函数形式
实例方法
实例方法是从属于实例对象的方法, 实例方法的定义如下:
def 方法名(self[,形参列表]):
函数体
方法的调用格式如下:
对象.方法名([实参列表])
要点:
- 第一个参数必须为self
- 调用实例方法时,不需要也不能给self传参,self由解释器自动传参.
函数和实例方法的区别:
方法需要通过对象来调用,方法从属于特定实例对象.
直观上来看,方法定义时需要传递self,函数不需要.
class Student: # 类名一般蚕蛹首字母大写
def __init__(self,name,score): # self必须为第一个参数
self.name = name
self.score = score
def say_score(self): # 第一个参数必须是self
print("{0},{1}".format(self.name, self.score))
s1 = Student("gaoqi",100) # 定义参数的值,并将她赋值给s1
s1.age = 18
print(s1.age)
s1.say_score() # 引用函数(注意函数形式
s2 = Student("grace",100)
s2.say_score()
Student.say_score(s2) # 解释器翻译
print(dir(s2))
print(s2.__dict__)
class Man:
pass
print(isinstance(s2,Man))
其它操作:
dir(obj)可以获得对象的所有属性、方法
obj.__dict__获得直观上的属性
pass空语句
isinstance(对象,类型) 判断对象是否为指定类型
类对象
“class 类名:”
class Student: # 类名一般蚕蛹首字母大写
def __init__(self,name,score): # self必须为第一个参数
self.name = name
self.score = score
def say_score(self): # 第一个参数必须是self
print("{0},{1}".format(self.name, self.score))
stu1 = Student
# 指向同一个对象
s1 = Student("grace",99)
s2 = stu1("grace",100)
# 不要忘记返回值
s1.say_score()
s2.say_score()
类属性和类方法
注意区分类属性和实例属性:
实例属性:self.name,
类属性:Student.company
class Student:
company = "sxt"
count = 0
def __init__(self,name,score):
self.name = name
self.score = score
def say_score(self):
print("我的公司是", Student.company)
print(self.name,"的分数是",self.score)
s1 = Student("grace",100)
s1.say_score()
类方法
类方法是从属于类对象的方法.类方法通过装饰器@classmethod来定义,格式如下:
@classmethod
def 类方法名(cls [,形参列表]):
函数体
要点如下:
- @classmethod必须位于方法上面第一行
- 第一个cls必须有:cls指的就是类对象本身
- 调用类方法格式:“类名.类方法名(参数列表)”,参数列表中不需要也不能给cls传值
- 类方法中访问实例属性和实例方法会导致错误
- 子类继承父类时,传入cls是子类对象,而非父类对象
class Student:
company = "sxt"
@classmethod
def printcompany(cls):
print(cls.company) # 注意格式是cls.object
Student.printcompany() # 引用类方法名
静态方法
Python中允许定义类对象无关的方法,称为静态方法。格式如下
@staticmethod
def 静态方法名([形参列表]):
函数体
(可以看做和类无关)
class Student:
company = "sxt"
@staticmethod
def add(a,b):
print("a+b=",a+b) # 注意格式是cls.object
return a+b
Student.add(5,6) # 引用类中的函数方法
类方法和静态方法中不能调用实例变量和实例方法
del()析构方法
用于销毁对象
python实现自动的;垃圾回收,当对象没有被引用时(引用计数为0),由垃圾回收器调用__del__方法
class Student:
def __del__(self):
print("销毁对象{0}".format(self))
p1 = Student()
p2 = Student()
del p2
print("程序结束")
#销毁对象<__main__.Student object at 0x000000FC48821EB8>,这里销毁的是p2
#程序结束
#销毁对象<__main__.Student object at 0x000000FC487267B8>,这里销毁的是p1
call()方法
定义了__call__()方法的对象,称为“可调用对象”,即该对象可像函数那样被调用
class Salary:
def __call__(self,salary):
yearsalary = salary*12
monthsalary = salary
daysalary = salary/22.5
hoursalary = daysalary/8
# 这里通过return以字典的形式返回工资的值
return dict(yearsalary=yearsalary, monthsalary=monthsalary, daysalary=daysalary,hoursalary=hoursalary)
s1 = Salary() # 类后面要加括号
print(s1(30000))