九 Python面向对象

九 Python面向对象

1. 面向对象与面向过程

1-1. 介绍

面向对象编程:Object Oriented Programming,简称OOP,是一种程序设计方法。

1-2. 概念及术语

术语概念及介绍
类(Class)用来描述具有相同属性和方法的对象的集合。它定义了该集合中每个对 象所共有的属性和方法。其中的对象被称作类的实例。
实例也称对象。通过类定义的初始化方法,赋予具体的值,成为一个"有血有肉 的实体"。
实例化创建类的实例的过程或操作。
实例变量定义在实例中的变量,只作用于当前实例。
类变量类变量是所有实例公有的变量。类变量定义在类中,但在方法体之外。
数据成员类变量、实例变量、方法、类方法、静态方法和属性等的统称。
方法类中定义的函数
静态方法不需要实例化就可以由类执行的方法
类方法类方法是将类本身作为对象进行操作的方法。
方法重写如果从父类继承的方法不能满足子类的需求,可以对父类的方法 进行改写,这个过程也称override。
封装将内部实现包裹起来,对外透明,提供api接口进行调用的机制。
继承即一个派生类(derived class)继承父类(base class)的变量和方法。
多态根据对象类型的不同以不同的方式进行处理。

1-3. 区别

面向过程:根据业务逻辑从上到下写代码
面向对象:将数据与函数绑定到一起,进行封装。减少重复代码的重写过程

1-4. 示例参考

示例1:面向过程

def stu_info(name,age,gender):
    print(name,age,gender)

stu_info("oldli","18","male")
stu_info("ellen","18","male")
stu_info("bruin","18","male")

示例2:面向对象

class Students(object):
    def stu_info(self,name, age, gender):
        print(name, age, gender)

s = Students()
s.stu_info("oldli","18","male")
s.stu_info("ellen","18","male")
s.stu_info("bruin","18","male")

2. 面向对象之(类)

2-1. 介绍

类是抽象的模板,用来描述具有相同属性和方法的对象的集合,比如 Animal类。
类名通常采用驼峰式命名,尽量让字面意思体现出类的作用。

2-2. 结构

Python使用class关键字来定义类,结构如下:

class 类名(object): # object 可有可无
	def 方法名(self,参数): # 行为
		pass
name = 类名() # 定义一个实例对象
name.方法名(参数) # 调用

3. 面向对象之 (self)

3-1. 介绍

self 形参
self 是对象本身,也就是说,当创建的对象是谁时,self就是谁

3-2. 示例参考

class Student(object):
    def test(self):
        # print(self)
        pass

oldli = Student() # 实例化对象
print(oldli)
oldli.test()

Chy = Student() # 实例化对象
print(Chy)
Chy.test() # 调用类
# 输出结果
#<__main__.Student object at 0x03955190>
#<__main__.Student object at 0x039552C8>
class Student(object):
    def info(self):
        print(self.name,self.age)

marshal = Student()
marshal.name = "marshal"
marshal.age = "18"
# print(marshal)
marshal.info() # 输出结果 marshl 18

xiaoming = Student() # 实例化对象
xiaoming.name = "xiaoming"
xiaoming.age = "22"
# print(marshal)
xiaoming.info() # 输出结果 xiaoming 22
  1. 当只有一个变量,其它相同时,可以参考这个
class Students(object):
    def stu_info(self,name):
        print(name, self.age, self.gender)

s = Students() # 实例化对象
s.age = "18"
s.gender = "male"
s.stu_info("oldli")
s.stu_info("ellen")
s.stu_info("bruin")
'''
输出结果:
oldli 18 male
ellen 18 male
bruin 18 male
'''

4. 面向对象之 init 魔法方法

4-1. 介绍

# 构造方法(初始化方法)
def __init__(self):
	pass
# 特殊意义
	创建对象的同时,通过对象执行这样的一个方法,叫做构造方法

4-2. 示例参考

class students(object):
	def __init__(self,age,gender):
	#属性
	self.age = age
	self.gender = gender
	self.addr = "ChongQing"
	
	# 打印信息
	def stu_info(self,name):
		print(name,self.age,self.gender,self.addr)
s = students() # 实例化对象
s.stu_info("oldli")
s.stu_info("enlen")
s.stu_info("bruin")
# 输出结果:
# oldli 18 male ChangSha
# ellen 18 male ChangSha
# bruin 18 male ChangSha

5. 面向对象之 str 魔法方法

5-1. 介绍

tips: 使用了该函数,一定返回字符串;如果返回出错,可以
定义的 str

def __str__(self):
	pass 
# 1. return 关键字 将我们的信息直接返回对象
# 2. 只能时str 如果非字符串 str() 强转

5-2. 示例参考

class People(object):
	def __init__(self):
		self.age = 18
		self.name = "zero"
		self.hobby = "play game"
	
	def __str__(self):
		return str({"name":self.name,"age":self.age})
		# return 返回的多个值 元组
        # 一定返回字符串

zero = People() 
print(zero) # 输出结果: {'name':'zero',

6. 练习

‘’‘只有当年龄>0的时候才返回出来,否则默认为0岁’’’

class People(object):
	def __init__(self): # 初始化参数
		self.age = 0

	def set_age(self,new_age): # 判断
		if new_age >= 0 and new_age <=120:
			self.age = new_age
		elif new_age > 120:
			self.age = 0
		else:
			# abs()取绝对值的内置方法
			self.age = abs(new_age)
	def get_age(self):
		return self.age

xiaoming = People() # 实例化对象
xiaoming.set_age(10) # 调用函数
print(xiaoming.get_age())
# 输出结果为 10

7. 私有属性与方法

7-1. 介绍

在类中,不希望外部去访问我的属性。
格式:

# 私有属性 -->__属性名():

7-2. 私有属性示例参考

# 定义一个类
class People(object):
	def __init__(self): # 初始化参数
		self.__age = 18 # 私有属性,外部访问不了
		self.name = zero

	def get_age(self): # 可从内部调用私有属性
		print(self.__age)

	def set_age(self,age):
		self.__age = age

zero = People() # 实例化对象
print(zero.name) # 打印取出名字  输出结果 zero
print(zero.__age) # 会报错,no attribute 。 不能直接从外部调用私有的属性(__age)
zero.get_age() # 调用get_age 方法获取私有属性 输出结果18
zero.set_age(22) # 重新传入参数
zero.get_age() # 输出结果 22 
print(zero.__dir__()) # 查看对象的方法跟属性

7-3. 私有方法示例参考

定义私有方法

class Demo(object): # 定义一个类
	def test1(self):
		print("test1:)
	
	def __test2(self):
		print("test2")

d = Demo() # 实例化对象
d.test1()	# 输出结果为 test1
d.__test2() # 报错,不能调用

8. 成员-方法与属性

8-1. 示例1 静态属性

class Province(object):
	country = "中国"  # 类属性, 静态属性  对象, 类来调用

	def __init__(self,name):
		self.name = name

	def print_info(self):
		print(Province.country,self.name) # 静态属性调用 类名.静态属性名

guangdong = Province("广东")
chongqing = Province("重庆")
guangdong.print_info() # 输出结果 中国广东
chongqing.print_info() # 输出结果 中国重庆
  1. 实例方法:对象需要保存的一些值,执行某功能时,需要使用对象中的值
    静态方法:跟我们在函数外部定义独立的方法没有什么区别,但是有的时方便维护。不需要创建对象 直接访问,不需要self参数。调用 通过类调用
    类方法: 保存在类中 由类直接调用 cls–>当前类
class Demo(object):
	def __init__(self):
		self.name = "zero"

	def test(self):
		print(self.name)

	@staticmethod # 静态方法,等同于上面的
	def test1(name):
		print(name)

	@classmethod
	def class_md(cls):
		print(cls)

d = Demo() # 实例化对象
d.test()  # 输出结果 zero
Demo.test1("王先生") # 输出结果 王先生 调用了静态属性@staticmethod
d.test1("小周") # 输出结果 小周

Demo.class_md() # <class '__main__.Demo'>

8-2. 在类中如何实现当前格式化时间

  1. 面向过程
import time
def show_time():
	print(time.strftime("%H:%M:%S",time.localtime()))

show_time() # 输出结果, 当前时间
  1. 面向对象
import time
class TimeTest(object):

	@staticmethod
	def show_time():
		print(time.strftime("%H:%M:%S",time.localtime()))

nowtime = Timetest()
TimeTest.showtime() # 输出结果, 当前时间

8-3. property

8-3-1. 介绍

可以将类的方法变为属性

8-3-2. 示例参考
class Demo(object):
	def __init__(self):
		self.name = "zero"

	@property  # 将方法变为属性
	def test(self):
		print(self.name)
		return "test"

	@test.setter   # d.test = "456"
	def test(self,nums):
		print(nums)

	@test.deleter
	def test(self):
		print(1111)

d = Demo() # 实例化对象
print(d.name)
res = d.test
print(res)

d.test = "456"  # 想要改变

del d.test
  1. 制作翻页效果
class Page(object):
	def __init__(self,current_page):
		try:
			p = int(current_page)
		except Exception as e: # 万能异常捕获
			p = 1
		self.page = p

	@property
	def start(self):
		start = (self.page-1)*10
		return start

	@property
	def end(self):
		end = self.page * 10
		return end

li = list(range(100))

while True:
	p = int(input("请输入要查看的页码:"))
	page = page(p)  # 实例化对象
	print(li[page.start:page.end])

9. 函数的继承

9-1. 介绍

创建新类的方式,新类可以继承一个或者多个父类;
作用:避免重复造轮子
新式类 继承object
经典类 不继承object

tips:
如果调用的是继承的父类中的方法,可以在这个公有方法中访问父类中的私有属性和私有方法;
但是如果在子类中实现了一个公有方法,那么这个方法是不能够调用继承的父类中的私有方法和私有属性

class Father(object):
    def __init__(self):
        self.name = "amy"
        self.__age = 18

    def __test(self):
        print("__test")

    def test1(self):
        print(self.__age)


class Son(Father):
    # def __init__(self):
    #     print("Son")
    #     super().__init__()
    def test3(self):
        # print(self.__age)
        self.__test()

    def __test(self):
        print("__test")


s = Son()
print(s.name)  #	amy
# print(s.__age)  # 私有属性不会被继承
# s.__test()  #私有方法不会被继承
# s.test1()
s.test3() #	__test

9-2. 示例

class GrandFather(object):
	def sleep(self):
		print("睡10个小时")

class Father(GrandFather): # 父类 基类
	def run(self):
		print("我会跑")

	def eat(self):
		print("我会吃")

class Son(Father):
	def study_python(self):
		print("我学python")

s = Son()
# 子类没有, 就往父类中去找
s.run() # 输出结果 我会跑
s.study_python() # 输出结果 我学python
# 父类没有 就会往父类的父类中去找
s.sleep()	#	输出结果 睡10个小时

9-3. 多继承

示例:

class GrandFather(object):
	def sleep(self):
		print("GrangF睡觉")

class Father(GrandFather):
	def run(self):
		print("Father会跑")

class Father1(Father):
	def run(self):
		print("Father1会跑")

	def sleep(self):
		print("Father1睡觉")

class Son(Father,Father1):
	pass

s = Son()
s.run()
s.sleep()	# C3
# print(Son.__mro__) # 可以查看调用顺序

tips:

  1. 左边优先
  2. 当左边父类的父类,有该方法。右边父类有该方法。左边一条路走到底
  3. 他们有一个根,根最后执行

10. 函数重写

10-1. 示例

'''
重写的同时并且执行父类中的方法
'''
class GrandFather(object):
	def sleep(self):
		print("睡10个小时")

class Father(GrandFather):
	def run(self):
		print("我会跑")

	def eat(self):
		print("我会吃")

class Son(Father):
	def study_python(self):
		print("我学python")

	def sleep(self):
		print("我睡8个小时")
		#super(Son,self).sleep()	#	下面的完整版
		super().sleep()	#	效果同上
		#GrandFather.sleep(self)	#	效果同上

s = Son()
s.sleep() # 输出结果 我睡8个小时 睡10个小时

总结:

  1. 继承机制 深度优先 先从自己找 自己找不到 就往父类找
  2. 重写 防止执行父类的该方法
  3. self 都指当前实例化的对象
  4. 既想要继承父类当中方法 又想拓展新的东西
    4.1 super(cls,self).父类中的方法(para)
    4.2 父类名父类中的方法(self,para)

11. 多态

示例:

class Person(object):
	def print_info(self):
		print("我是个人")

class Girl(Person): # 继承
	def print_info(self):
		print("我是zero")

def info(travel): # 定义一个函数
	travel.print_info()

zero = Person() # 实例化对象
info(zero)  # 我是个人

zero1 = Girl() # 实例化对象
info(zero1)	# 我是zero

12. 面向对象之魔法方法

12-1. 魔法方法

  1. doc
    tips:
    当函数中有多个注释时,只会打印第一个注释
# str()
# print(str().__doc__)

class Demo(object):
	'''
我是Demo的注释
	'''
	'我有一个构造方法'
    "我....."
	def __init__(self):
		pass

d = Demo()
print(d.__doc__) #	输出结果:我是demo的注释
  1. del
    tips:
    只有等到对象全部释放,才会主动触发__del__
class Demo:
	def __del__(self):
		print("好惨,我被回收了")

d = Demo()
d1 = d
print("-"*20)
del d
del d1
print("-"*20)

'''
输出结果:
--------------------
好惨,我被回收了
--------------------
'''
  1. call
    tips:
    一个实例,也可以变成一个可调用的对象
class Demo(object):
	def __call__(self,*args,**kwargs):
		print("我可以调用了哟")

d = Demo()
d() # 'Demo' object is not callable # 输出结果: 我可以被调用了哟
# str()
  1. dict 查看类或者对象的成员 字典
    dict 更像__dir__的一个子集
class Demo(object):
	gender = "female"
	def __init__(self):
		self.name = "zero"
		self.__age = 18

	def test(self):
		print("test")

d = Demo()
d.test()
print(d.__dict__) # dict 查看对象中的实例属性
print(Demo.__dict__) #	查看类中的成员 -->类属性与行为
print(d.__dir__()) #	列表 查看对象的 -->成员
print(Demo.__dir__(d))
print(d._Demo__age)

12-2. new方法

12-2-1. 介绍

new 在类准备自身实例化时调用的
new 静态方法 创建对象
init 实例方法,对象自动调用的方法

12-2-2. 示例
class Demo(object):
	def __init__(self):
		print("__init__")

	# 如果我们这个类中没有new,会创建对象的时候,会自动执行父类中的new方法
	def __new__(cls,*args,**kwargs):
		return super().__new__(cls) # 传入别的类名时,不会调用__init__方法

d = Demo()
# 1.创建对象 __new__
# 2.调用__init__方法
# 3.返回对象引用

12-3. 单例模式

12-3-1. 介绍

永远只使用一份对象 (重点:记录日志在logger)
对象不存在时候 -->创建对象
对象存在 -->永远只返回当前创建对象

12-3-2. 示例
class Demo(object):
	flag = None	#	标志

	# 创建对象 __new__
	def __new__(cls,*args,**kwargs):
		# return super().__new__(cls)
		if cls.fflag is None:
			cls.flag = super().__new__(cls):
			return cls.flag
		else:
			return cls.flag

d = Demo()
print(id(d))
d1 = Demo()
print(id(d1)) # 输出两个相同的ID地址

12-4. reflect 反射

12-4-1. 会用到的函数
  1. getattr 函数 获取属性值或者获取方法变量的地址
getattr(py文件名,输入的名字)

getattr(views,ipt)
  1. hasattr 函数 判断是否有此变量,返回bool 值
  • 6
    点赞
  • 39
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值