object是所有类的基类
type是所有类的类型---metaclass可以指定类的类型
补充
from collections import namedtuple
Point = namedtuple("point",["x","y"])
t1 = Point(1,2)
print(t1.x)
print(t1.y)
#没有方法并且属性不会发生变化的类
#定义简单
#不能改变
面向对象封装
私有属性,私有方法,用装饰器描述的几个方法
私有属性(__私有属性)
私有方法(__私有方法)
class Teacher:
__identifier = "Teacher" #私有静态属性
def __init__(self,name,pwd):
self.name = name
self.__pwd = pwd #私有属性
self.__p() #调用私有方法
def pwd(self):
print(self.__pwd)
def __p(self): ##私有方法
print(self.__pwd)
alex = Teacher("alex","3714")
alex.pwd()
print(alex.__dict__) #打印属于alex的属性
#类外调用私有属性(_类名__私有属性名)--不要去使用这个方法
print(alex._Teacher__pwd)
#类外调用私有方法
alex._Teacher__p()
#类外调用私有静态属性
print(Teacher._Teacher__identifier)
#类外定义私有属性形式的属性,没有任何意义,就跟普通属性一样的
私有方法的意义:
1--有一些方法的返回值只是用来作为中间结果
2--父类的方法不希望子类继承
class Teacher:
__identifier = "Teacher"
def __init__(self,name,pwd):
self.name = name
self.__pwd = pwd
self.__p()
def __p(self):
return hash(self.__pwd)
def judge(self,password):
return hash(password) == self.__p()
alex = Teacher("alex","3714")
ret = alex.judge("3417")
print(ret)
私有属性的意义:
class Person:
def __init__(self,name,height,weight):
self.name = name
self.__height = height
self.__weight = weight
def get_bmi(self):
return self.__weight /(self.__height * self.__height)
def change_weigth(self,new_weight):
if new_weight > 20:
self.__weight = new_weight
else:
print("体重过轻")
jinghong = Person("jinghong",1.81,94)
print(jinghong.get_bmi())
jinghong.change_weigth(80)
print(jinghong.get_bmi())
![]()
class Host:
def __init__(self,owner,length,width):
self.owner = owner
self.__length = length
self.__width = width
def area(self):
return self.__length * self.__width
host = Host("aelx",50,30)
print(host.area())
例子:房屋有业主,长和宽,求面积
property方法--把类中的方法假装成一个属性(最常用)
class Person:
def __init__(self,name,height,weight):
self.name = name
self.__height = height
self.__weight = weight
@property
def bmi(self):
return self.__weight /(self.__height * self.__height)
jinghong = Person("jinghong",1.81,94)
print(jinghong.name,jinghong.bmi)#这里去调用的时候,就是相当于调用一个属性
![]()
class Host:
def __init__(self,owner,length,width):
self.owner = owner
self.__length = length
self.__width = width
@property
def area(self):
return self.__length * self.__width
host = Host("aelx",50,30)
print(host.area)
例子:房屋有业主,长和宽,求面积
@要伪装的方法名.setter---这样就更加像属性了
class Shop:
discount = 0.75
def __init__(self,name,price):
self.name = name
self.__price = price
@property
def price(self):
return self.__price * Shop.discount
@price.setter
def price(self,new_price):
self.__price = new_price
@price.deleter #---一般不会用到
def price(self,):
del self.__price
apple = Shop("apple",5)
print(apple.price)
apple.price = 6 #@price.setter,用了这个方法之后,就可以修改了
print(apple.price)
print(apple.__dict__)
del apple.price
print(apple.__dict__)
staticmethod---静态方法
在只使用这个方法时,跟参数没啥关系的时候
不能将函数独立的放在类外,完全使用面相对编程的时候,并且这个函数不需要依赖对象的属性和类的属性
就可以使用staticmethod装饰这个方法
class A:
def __init__(self,name):
self.name = name
def ah(self): #self就是形式参数,ah就是普通方法,绑定(对象)方法
print("ah")
@staticmethod #静态方法
def func():
print("func")
# a = A("a")
# A.func(a) #和a.func()一样
A.func()
静态方法--没有必须传的参数,不需要用对象的属性和类的属性
类方法--必须传一个类,不能使用对象属性,但可以使用类属性
普通方法--必须传一个参数,可以使用对象的属性和类的属性
类方法:
![]()
class A:
role = "a"
@classmethod
def class_metood(cls): #这里必须叫cls,默认的
print(cls.role)
A.class_metood()
# A.role
classmethod