1、类的写法
class 类名():
代码
...
类的创建例子
class Test():
# 函数的构造方法
def __init__(self, name):
self.__name=name # 这个是表示内部类的属性
def __innerMethod(self):
print('this is inner method')
# self相当于js中的this
def printContent(self):
self.__innerMethod()
print(self.__name)
t = Test('content') # 创建对象
t.printContent() # 调用对象的方法
# print(t.__name) # 在python中__表示private,外部不能调用
# print(t.__innerMethod()) # 也调用不了
__slots__ 是一个特殊的类属性,用于指定类实例中允许的属性名称列表。通过使用 __slots__,你可以限制类的实例仅包含预先定义的属性。
class MyClass:
__slots__ = ['property1', '__name'] # __name是内部变量
def __init__(self, value1, name):
self.property1 = value1
self.__name = name
def printName(self):
print(self.__name)
# 创建类的实例
obj = MyClass("Hello", "content")
# 访问属性
print(obj.property1) # 输出: Hello
obj.printName()
# 尝试赋值和访问未声明的属性,将引发 AttributeError
obj.age = 12
print(obj.age)
注意:
- 正常情况下,Python 的类实例在内部使用字典(
__dict__)来存储属性。这允许你在运行时动态地添加、删除和修改属性。然而,字典结构会占用一定的内存空间,并且属性的访问速度相对较慢。 - 当你在类中定义
__slots__属性时,它将替代默认的__dict__结构,从而节省了内存并提高了属性访问的性能。通过指定允许的属性名称列表,你可以告诉Python只为这些属性分配内存空间,并限制实例只能具有这些属性。 - 例如,如果在类中定义了
__slots__ = ['property1', 'property2'],那么类的实例只能具有property1和property2这两个属性。如果尝试给其他属性赋值,将引发AttributeError错误。 - 需要注意的是,
__slots__只对当前类的实例起作用,并不会影响其子类的属性。子类仍然可以拥有自己的__dict__和__slots__属性。 - 使用
__slots__有助于优化内存占用和属性访问速度,但也会带来一些限制,如无法动态地添加新的实例属性、无法使用继承的__dict__属性等。因此,在使用__slots__时需要仔细考虑其对应用的影响。
2、常用类的魔法方法
__init__(self, ...): 初始化方法,在创建对象时调用。__del__(self): 析构方法,在对象被销毁前调用。__str__(self): 定义对象的可读字符串表示形式,通过str()函数调用。- __mro__: 类名.__mro 查询类的继承层级顺序
class Test():
__slots__ = ['name', 'age']
def __init__(self, name, age):
self.name = name
self.age = age
print('这个是初始化会被调用')
def __str__(self):
return f'name:{self.name}, age: {self.age}'
def __del__(self):
print('这个是销毁的魔法方法')
t = Test('aaa', 12)
print(str(t))
# 输出:
# 这个是初始化会被调用
# name:aaa, age: 12
# 这个是销毁的魔法方法
3、python中public, protect, private
在python中通常都是public属性,如果protect属性是用 _属性名 来定义,private的属性是用 __属性名来定义
protect属性在类外也可以调用,但通常这个是不鼓励的,但private是类外是不能被调用
class Parent():
__slots__ = ["_name", "__age"]
def __init__(self, name, age):
self._name = name
self.__age = age
class Child(Parent):
def printProp(self):
print(self._name, self.__age) # 注意:这里的__age是在父类中定义的,这里不能访问
# p = Parent('even', 12)
# print(p._name) # 可以访问
# print(p.__age) # 不能被访问
c = Child('even', 11)
c.printProp()
4、python中类的继承
python中类的函数是多继承,即一个类可以继承多个类,当一个类有多个父类时,默认使用第一个父类的同名属性和方法
class Master():
def __init__(self, name):
self.name = name
def query(self):
print(f'this is Master query {self.name}')
def masterFn(self):
print('this is master function')
class Parent():
def __init__(self, name):
self.name = name
def query(self):
print(f'this is parent query {self.name}')
class Current(Parent, Master):
pass
c = Current('even')
c.query() # this is parent query even
c.masterFn() # this is master function
python中子类调用父类的同名方法
class Master():
def __init__(self, name, age):
self.name = name
self.age = age
def printInfo(self):
print(f'master里的方法,name: {self.name}, age: {self.age}')
class Child(Master):
def __init__(self, name, age):
super().__init__(name, age)
def printInfo(self):
super().printInfo()
print(f'Child里的方法,name: {self.name}, age: {self.age}')
c = Child('even', 12)
c.printInfo()
5、类属性及相关方法
类属性
类属性就是类对象所拥有的属性, 它被该类的所有实例对象所共有
class Base():
name = "even"
b = Base()
print(Base.name, b.name)# even even
b.name = 'efg'
print(Base.name, b.name) # even efg
Base.name = "abc"
print(Base.name, b.name) # abc efg
注意:类属性只能通过类对象修改,不能通过实例对象修改,如果通过实例对象修改类属性,表示的是创建了一个实例属性。即当类属性更改,实例属性就会变化,当实例属性更改就相当于创建了一个实例属性与原有的类属性无关系了
类方法
需要用装饰器@classmethod来标识其为类方法,对于类方法, 第一个参数属性是类对象,一般是以cls作为第一个参数
class Base():
__name = "even"
name = "abc"
@classmethod
def printName(cls):
print(cls.__name)
print(Base.__name) # 私有类属性,外部不能直接访问
print(Base.name) # 输出 abc
Base.printName() # 输出 even
类的静态方法
- 当方法中 既不需要使用实例对象(如实例对象,实例属性),也不需要使用类对象(如类属性、类方法、创建实例等)时,定义静态方法
- 取消不需要的参数传递,有利于 减少不必要的内存占用和性能消耗
class Base():
@staticmethod
def staticFunc(name, age):
print(f"name:{name}, age: {age}")
b = Base()
b.staticFunc('aaa', 12) # name:aaa, age: 12
Base.staticFunc('bbb', 20) # name:bbb, age: 20

浙公网安备 33010602011771号