Python 面向对象 进阶

类属性

生活中总会出现这样一种特征,一类事物共有的共同的特征,Python语法中提供了类型属性(简称类属性)描述表现这样的特征。

什么是类属性

定义给类型的属性,直接描述一类事物的特征,而不是具体某个对象的特征。

类属性的声明

类属性,声明在类型的内部,方法的外部。

class Person:
    """人的类型"""

    # 类属性
    max_age = 150

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

类属性的特点

类属性描述了一类事物的特征,所以可以被这个类型创建的所有对象去访问(不能修改)

类属性的访问及修改

class Person:
    max_age = 150

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

# 类属性的访问
# 1. 通过 类名.类属性 访问
>>> print(Person.max_age)
150

# 2. 通过 对象.类属性 访问
>>> man = Person("tom", 35)
>>> man.max_age
150

# 类属性的修改
# 通过 类名.类属性 修改
>>> Person.max_age = 130
>>> print(Person.max_age)
130

类属性的适用场景

类属性的出现,主要是用来描述一类事物共同的特征,如果在项目开发中,出现了类似的特征,要求所有对象都能遵循满足同一个特征数据,考虑适用类属性声明这个特征!

类方法

基本语法

class 类型名称:

    ...
    
    @classmethed
    def 类方法名称(cls, [形参]):
        pass
  • 类方法,也是一种方法,遵循方法的命名规范
  • 类方法,需要在方法上边加上 @classmethed 装饰器声明,表示这是一个类方法
  • 类方法,第一个参数 cls 表示的是当前类
  • 类方法可以访问和修改类属性,通过 cls 直接访问和修改

类方法的调用执行

类方法和类属性一样,推荐直接通过 类名.方法名调用执行

类方法属于一类事物的共同行为,所以通过对象也可以调用

什么时候声明类方法

项目中的某个类型出现了一种行为,和具体的对象无关,此时这样的行为方法,就可以被声明为类方法。

类属性的封装,属性的 set/get 方法必须通过类方法来实现

静态方法

基本语法

class 类名:
  ...

  @staticmethod
  def get_current_time():
    return datatime.now()

什么时候声明静态方法

项目开发过程中,出现了一些功能性的方法,如获取当前系统时间,如此简单之行为,抽取对象声明类型,反倒有过度设计的嫌疑!

注意:面向对象的开发中,不要为了面向对象去专门强行设计类型,很容易造成过度设计!

1. 声明函数实现

面向对象的项目中,如果出现了一些实现独立的小功能行为,可以将这样的功能声明成函数在项目中调用执行(面向过程 面向对象 混合开发

  • 优点:函数式的实现,开发过程中适用方便,哪里需要哪里声明哪里调用!
  • 缺点:如果没有足够的项目规范约束,项目中声明的多个函数到处都是不好维护!

2. 静态方法实现

类似获取时间这样的功能性函数,如果抽取对象声明类型比较繁琐,Python语法中针对这样的函数提供了一个特殊的方法:静态方法。包含在任意一个类型中,通过类型统一管理,可以通过类型名称直接调用,但是静态方法不能访问实例属性,也不能访问类型属性,只起到了函数的作用!

静态方法深入浅出

  • 静态方法声明在类型中,使用 @staticmethod 声明
  • 静态方法既不能访问实例属性,也不能访问类属性,只起到函数的作用
  • 静态方法推荐通过 类名调用执行
  • 如果一个方法既不访问对象数据也不访问类数据,考虑使用静态方法

小结

实例方法类方法静态方法
访问实例属性YNN
访问类属性YYN

魔法方法

什么是魔法方法

魔法方法如同它的名字一样神奇,是指哪些Python内部已经包含的,被双下划线所包围的方法,这些方法在进行特定的操作时会被自动调用。

class Person:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def __str__(self):
        """当对象被打印时调用"""
        return f"name is {self.name}, age is {self.age}"

tom = Person("tom", 18)
print(tom)
# name is tom, age is 18

基础魔法方法

魔法方法名描述
new(cls)构造方法
init(self)初始化方法
call(self[,…])允许一个对象像函数一样被调用:x(a,b)调用x.__call__(a,b)
len(self)定义当被len()调用时的行为
repr(self)定义当被repr()调用时的行为
str(self)定义当被str()调用时的行为
hash(self)定义当被hash()调用时的行为

属性相关

魔法方法名描述
getattr(self,name)定义一个当用户试图获取一个不存在的属性时的行为
getattribute(self, name)定义当该类的属性被访问时的行为
setattr(self, name, value)定义当一个属性被设置时的行为
delattr(self, name)定义当一个属性被删除时的行为
dir(self)定义当 dir() 被调用时的行为

比较操作符

魔法方法名描述
lt(self, other)定义小于号的行为:x < y 调用 x.__lt__(y)
eq(self, other)定义等于号的行为:x == y 调用 x.__eq__(y)
ne(self, other)定义不等号的行为:x != y 调用 x.__ne__(y)
gt(self, other)定义大于号的行为:x > y 调用 x.__gt__(y)

算术运算符

魔法方法名描述
add(self, other)定义加法的行为:+
sub(self, other)定义减法的行为:-
mul(self, other)定义乘法的行为:*
truediv(self, other)定义真除法的行为:/

增量赋值运算

魔法方法名描述
iadd(self, other)定义赋值加法的行为:+=
isub(self, other)定义赋值减法的行为:-=
imul(self, other)定义赋值乘法的行为:*=
itruediv(self, other)定义赋值真除法的行为:/=

类型转换

魔法方法名描述
int(self)让当前对象支持 int() 类型转换操作
float(self)让当前对象支持 float() 类型转换操作
bool(self)让当前对象支持 bool() 类型转换操作
str(self)让当前对象支持 str() 类型转换操作

… more and more

反射方法

什么是反射方法

反射方法,就是不通过方法名称调用方法,而是通过一个字符串反向解析得到方法对象执行方法的过程。

# 常规
Object.study()  # 执行了 study() 方法

# 反射
method = getattr(Object, "study")
method()

常见的反射方法

魔法方法名描述
hasattr(obj, attr)判断目标对象中是否包含指定的属性或者方法
getattr(obj, attr)从目标对象中获取执行名称的属性或者方法
setattr(obj, attr, value)获取并执行目标对象中的属性或者方法
delattr(obj, attr)从目标对象中删除对应的属性或者方法
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值