属性
例一:BMI指数(bmi是计算而来的,但很明显它听起来像是一个属性而非方法,如果我们将其做成一个属性,更便于理解)
成人的BMI数值:
过轻:低于18.5
正常:18.5-23.9
过重:24-27
肥胖:28-32
非常肥胖, 高于32
体质指数(BMI)=体重(kg)÷身高^2(m)
EX:70kg÷(1.75×1.75)=22.86
class Person: def __init__(self,name,weight,hight): self.name=name self.__weight=weight self.__hight=hight def bmi(self): print("%s的BMI指数是%s" % (self.name,self.__weight//self.__hight**2)) p1=Person("大牛",74.6,1.68) print(p1.bmi())
class Person:
def __init__(self,name,weight,hight):
self.name=name
self.__weight=weight
self.__hight=hight
self.BMI=print("%s的BMI指数是%s" % (self.name,self.__weight//self.__hight**2))
p1=Person("大牛",74.6,1.68)
什么是特性property
property是一种特殊的属性,访问它时会执行一段功能(函数)然后返回值
class Person: def __init__(self,name,weight,hight): self.name=name self.__weight=weight self.__hight=hight @property def bmi(self): return "%s的BMI指数是%s" % (self.name,self.__weight//self.__hight**2) p1=Person("大牛",74.6,1.68) print(p1.bmi)
为什么要用property
将一个类的函数定义成特性以后,对象再去使用的时候obj.name,根本无法察觉自己的name是执行了一个函数然后计算出来的,这种特性的使用方式遵循了统一访问的原则
由于新式类中具有三种访问方式,我们可以根据他们几个属性的访问特点,分别将三个方法定义为对同一个属性:获取、修改、删除
class Person: def __init__(self,name,age): self.name=name if type(age) is int: self.__age=age else: print("输入的年龄的类型有误,请输入数字") def age(self): return self.__age p1=Person("帅",25) print(p1.age()) 结果:25 p1=Person("帅","25") print(p1.age()) 结果:"输入的年龄的类型有误,请输入数字 并报错
加装饰器:查(获取)
class Person: def __init__(self,name,age): self.name=name if type(age) is int: self.__age=age else: print("输入的年龄的类型有误,请输入数字") @property def age(self): return self.__age p1=Person("帅",25) print(p1.age) print(p1.__dict__) 25 {'name': '帅', '_Person__age': 25}
属性更改(加装饰器):修改
class Person: def __init__(self,name,age): self.name=name if type(age) is int: self.__age=age else: print("输入的年龄的类型有误,请输入数字") @property def age(self): return self.__age @age.setter def age(self,a1): if type(a1) is int: self.__age=a1 else: print("输入更改的年龄的类型有误,请输入数字") p1=Person("帅",25) print(p1.age) p1.age=333 print(p1.age) print(p1.__dict__) 25 333 {'name': '帅', '_Person__age': 333}
属性删除(加装饰器):删
class Person: def __init__(self,name,age): self.name=name if type(age) is int: self.__age=age else: print("输入的年龄的类型有误,请输入数字") @property def age(self): return self.__age @age.setter def age(self,a1): if type(a1) is int: self.__age=a1 else: print("输入更改的年龄的类型有误,请输入数字") @age.deleter def age(self): del self.__age p1=Person("帅",25) del p1.age print(p1.__dict__) {'name': '帅'}
property:类似于bmi这种,(计算),area面积,周长
类方法:
class A: #普通方法 def func(self): print(self) a1=A() a1.func() A.func(a1) <__main__.A object at 0x0000017787125EB8> <__main__.A object at 0x0000017787125EB8>
类方法: 通过类名调用的方法,类方法中第一个参数约定俗称cls,python自动将类名(类空间)传给cls.
class A: def func(self): print(self) @classmethod #类方法 def func1(cls): print(cls) A.func1() <class '__main__.A'>
对象调用类方法,cls 得到的是类本身.
class A: def func(self): print(self) @classmethod #类方法 def func1(cls): print(cls) a1=A() a1.func1() <class '__main__.A'>
类方法的应用场景:
1, 类中有些方法是不需要对象参与.
class A: name="aaaaas" count=1 def func(self): return A.name+str(A.count+1) # A.func(111)#不可取 a1=A() print(a1.func()) aaaaas2
class A: name="aaaaas" count=1 @classmethod def func(cls): return A.name+str(A.count+1) print(A.func()) aaaaas2
class A: name="aaaaas" count=1 @classmethod def func(cls): return cls.name+str(cls.count+1) print(A.func()) aaaaas2
2, 对类中的静态变量进行改变,要用类方法.
3,继承中,父类得到子类的类空间.
class A: name="aaaaas" count=1 @classmethod def func(cls): print(cls) class B(A): pass B.func() <class '__main__.B'>
class A: age=10 @classmethod def func(cls): print(cls.age) class B(A): age=22 def func1(self): pass B.func() 22
class A: age=10 @classmethod def func(cls): print(cls.age) class B(A): age=22 B.func() 22
不通过类方法,想让我的父类的某个方法得到子类的类空间里面的任意值.
class A: age=10 def func(self): print(self) # self 子类的对象,能得到子类 空间的任意值 class B(A): age=22 b=B() b.func() <__main__.B object at 0x0000022BA0595EB8>
静态方法:
class A: @staticmethod def login(username, password): if username == 'alex' and password == 123: print('登录成功') else: print('登录失败...') A.login('alex',1234) def login(username, password): if username == 'alex' and password == 123: print('登录成功') else: print('登录失败...') login('alex',1234) 结果:登录失败..
1,代码块.清晰.
2,复用性.