类变量、绑定方法、静态方法和类方法
类变量
面向对象的结构
- 类成员
- 类变量(静态字段/属性)
- 方法
- 绑定方法:常规的形式(只能通过对象调用)
- 静态方法(推荐类调用)
- 类方法(推荐类调用)
- 属性
对象可以调用所用的方法
- 实例(对象)
- 实例变量(字段/属性)
class Foo:
city = "北京" #成员city就叫类变量
def __init__(self,name):
self.name = name
def func(self):
pass
obj1 = Foo("杨子莲")
obj2 = Foo("女神")
print(obj1.city)
print(Foo.city)#比较正式的写法
print(obj.city)
'''
输出结果为:
北京
北京
北京
'''
-
定义时:写在类的下一级和方法同级
-
访问:
-
类.类变量名称 对象.类变量名称
-
示例一
class Base:
x = 1
obj = Base()
print(obj.x)
'''
类里面没有方法只有一个类变量,所以输出的结果为1
'''
obj.y = 123 #在对象中添加一个y = 123的变量
obj.x = 123 #在对象中添加一个x-123的变量,并不能改变类中的x = 1的
Base.x = 666 #改变了类中的x = 1的变量
示例二
#练习1
class Base:
x = 1
class Foo(Base):
pass
print(Foo.x) #继承关系
#结果为1
#练习2
class Base:
x = 1
class Foo(Base):
pass
Foo.x = 666 #只改变自己,并没有改变Base
print(Base.x)
print(Foo.x)
'''
结果为
1
666
'''
示例三
class Parent:
x = 1
class Child(Parent):
pass
obj = Child()
print(obj.x)
obj.x = 2 #只改变了对象而未改变类,所以Child.x的结果依然为1
print(Child.x)
'''
输出结果为:
1
1
证明:
不用非得实例化后才能执行类,在不执行的时候依然可以调用其中的数据
'''
总结:
- 找变量优先找自己 ,自己没有找 类 或 基类
- 修改时或赋值时只能在自己的内存中进行赋值,不能修改父级或其他
绑定方法
class Foo:
def init(self):
self.name = 123
def func(self,a,b):
print(self.name,a,b)
obj = Foo()
obj.func(1,2)
静态方法
-
定义:
- @staticmethod装饰器
- 参数无限制
-
执行:
- 类.静态方法
class Foo: def __init__(self): self.name = 123 def func(self,a,b): print(self.name,a,b) def func1(a,b): print("yang") @staticmethod def f1(a,b): #静态方法:不用创建对象,直接通过类进行调用 print(123) Foo.func1("1","zi") ''' 思考: 我认为通过静态方法调用的函数和普通定义一个函数的区别不大。就像func1与f1的差别并不是很大一样。
在没有数据封装进去的时候,用静态方法。它就在那嘛,静静的不用绑定数据所以叫静态方法
'''
## 类方法
```python
class Foo:
@staticmethod
def f1(a,b): #静态方法:不用创建对象,直接通过类进行调用
print(123)
@classmethod #类方法
def f2(cls,a,b):#cls为固定参数,返回的为当前类
print("cls是当前类",cls)
print(a,b)
'''
结果为:
cls是当前类 <class '__main__.Foo'>
1 zi
'''
Foo.f2("1","zi")
类方法
- 定义:
- @classmethod装饰器
- 至少有cls参数,当前类
- 执行:
- 类.类方法
- 对象.类方法(不推荐)
问题 @classmethod和staticmethod的区别
- 一个是类方法一个是静态方法。
- 定义:
- 类方法:用@classmethod做装饰器且至少有一个cls参数
- 静态方法:用staticmethod做装饰器且参数无限制
- 调用:
- 类.方法直接调用
- 对象.方法也可以调用
麦叔:静态方法、类方法、静态方法
class Dog(object):
dogbook = {"黄色":30,"黑色":20,"白色":0}
def __init__(self,name,color,weight):
self.name = name
self.color = color
self.weight = weight
def bark(self):
print(f"{self.name}叫了起来")
@classmethod #类方法主要是用来方位类属性
def dog_num(cls): #就直接访问类的属性
num = 0
for v in cls.dogbook.values(): #就访问类的属性
num = num + v
return num
@staticmethod #与谁都无关,强行封装
def total_weight(dog):
total = 0
for o in dog:
total = total + o.weight
return total
print(f"共有{Dog.dog_num}条狗")
d1 = Dog("大黄","黄色",10)
d1.bark()
print(f"共有{d1.dog_num()}条狗")
d2 = Dog("旺财","黑色",8)
d2.bark()
print(f"狗共重{Dog.total_weight([d1,d2])}公斤")
#实例化方法就是正常的方法
#示例化方法是为了访问类的属性
#静态方法就是啥也不管强行归类,为了保持
记录学习的点点滴滴