python 第四章面向对象

1.类和对象的关系

类和对象的关系就像数据结构和数据的关系一样,类规定了存储什么数据,对象用来实际存储数据

1.1.对象构建小例子
"""
1.类的定义和构造
2.类的方法(函数) 构造 析构
一般函数的第一个参数是实例对象名,代之需要调用函数的对象,传参时不传入
3.类的属性(成员) 公有 私有
"""

"""
python 不存在无法访问的私有属性
如何保持封装的封闭性
"""

class student:
    
    __age=0#私有成员
    
    name=""#公有成员
    Id=""
    
    def __init__(self,name,age,Id):#构造函数
        self.name=name
        self.Id=Id
        self.__age=age
        print("%s同学的信息构造完成"%self.name)
        
    def __del__(self):#析构函数
        print("%s同学的信息被删除"%self.name)
        
    def printf(self):#查看信息
        print("%s同学的年龄为:%s\n学号为:%s"%(self.name,self.__age,self.Id))
        
        
        
if __name__ == '__main__':
    #信息构造
    stu1=student("李华","21","20212203")
    stu2=student("李明","20","20212204")
    stu3=student("李强","21","20212201")
    
    #信息查看
    stu1.printf()
    stu2.printf()
    stu3.printf()
    
    #在类外调用私有成员要加类名限制(私有成员在类外也是可以定义的)
    print("%s同学的年龄为:%s"%(stu1.name,stu1._student__age))
    
    #信息删除
    stu4=stu1
    
    del stu1#对象信息备份在stu4
    del stu2
    del stu3
    

2.常用内置方法

2.1 __str__ 方法
应用场景:当一个类的对象要以字符串的形式使用时要用到此方法;
举例:复数类

"""
这里的复数对象要当作字符串输出,定义__str__方法实现
"""

class complex:
    def __init__(self,real,image):
        self.real=real
        self.image=image
    
    
    def __str__(self):
        if self.image >=0:
            return str(self.real)+'+'+str(self.image)+'i'
        else:
            return str(self.real)+str(self.image)+'i'
    
    '''
    def __str__(self):
        if self.image >= 0:
            return '{}+{}i'.format(self.real,self.image)
        else:
            return '{}{}i'.format(self.real,self.image)
    '''
c=complex(-1,2.3)
print(c)
c1=c=complex(1,-2.3)
print(c1)
2.2 比较运算内置方法
应用场景:比较某个类两个对象的某种属性大小,返回逻辑真和逻辑假

在这里插入图片描述

举例:比较两个人成绩大小
"""
定义一个学生类,判断一个同学的成绩是否大于另一个
感觉有点类似于C++运算符重载
"""

class student:
    def __init__(self,name,score):
        self.score=score
        self.name=name
        
    def __gt__(self,other):
        return self.score>=other.score
    
stu1=student('李华',78)
stu2=student('李明',80)
print('李明的成绩高于李华:',stu2.score>stu1.score)

3 多态前置知识:鸭子类型

命名的来由:

“当看到一只鸟走起来像鸭子、游泳起来像鸭子、叫起来也像鸭子,那么这只鸟就可以被称为鸭子。”
在鸭子类型中,关注点在于对象的行为,能作什么;而不是关注对象所属的类型。
鸭子类型使得有相同功能的不同类也能实现多态,这是C++不具备的

鸭子类型举例:
"""
在鸭子类型中,关注点在于对象的行为,能作什么;
而不是关注对象所属的类型。
"""
class person:
    
    def __init__(self,name,age):
        self.name=name
        self.age=age
        
    def printt(self):
        print('%s的年龄为%d'%(self.name,self.age))
        

class Dog:
    def __init__(self,name,weight):
        self.name=name
        self.weight=weight
    def printt(self):
        print('狗狗%s的体重为%d'%(self.name,self.weight))    

def printt(tmp):
    tmp.printt()


c1=person('李华',12)
c2=Dog('乔治', 100)
printt(c1)
printt(c2) 

4.super方法、单继承与多继承、方法重写

概述

1.单继承与多继承
2.方法重写: 方法重写就是在继承中子类对于父类已有的功能进行重写,可以通过鸭子类型实现多态
3.super: 获取当前类父类的代理对象(一般用于子类构造函数对父类元素赋值)

实例:
"""
1.单继承与多继承
2.方法重写: 方法重写就是在继承中子类对于父类已有的功能进行重写,可以通过父类的引用实现多态
3.super:  获取当前类父类的代理对象(一般用于子类构造函数对父类元素赋值)


        学生
人——>           ——> 助教
        老师
        
        
"""




class person:
    
    def __init__(self,sex,name):
        self.sex=sex;
        self.name=name
        
    def Printinfo(self):
        print('{}的性别为{}'.format(self.name,self.sex))
        
class student(person):
    def __init__(self,sex,name,sno):
        super().__init__(sex,name)
        self.sno=sno
        
    def Printinfo(self):
        print('{}的性别为{},学号为{}'.format(self.name,self.sex,self.sno))
        
class teacher(person):
    def __init__(self,sex,name,tno):
        super().__init__(sex,name)
        self.tno=tno    
    
    def Printinfo(self):
        print('{}的性别为{},教师号为{}'.format(self.name,self.sex,self.tno))
        
class assistant(teacher,person):
    pass


def Printinfo(tem):
    tem.Printinfo()
    
c1=teacher('男', '李华', '11230')
c2=student('女', '李梅', '12345')
c3=person('男', '李强')
Printinfo(c1)
Printinfo(c2)
Printinfo(c3)

暂时不知python怎么消除多继承二义性,对于助教类先不扩展

5.type函数,issubclass函数和isinstance函数

简介:

1.isinstance 判断一个类是否是指定类或者是指定类的子类
2.issubclass 判断一个类是否是另一个类的子类
3.type()函数 获取一个对象所属的类

小例子:
"""
1.isinstance  判断一个类是否是指定类或者是指定类的子类
2.issubclass  判断一个类是否是另一个类的子类
3.type()函数  获取一个对象所属的类
"""

class person:
    
    def __init__(self,sex,name):
        self.sex=sex;
        self.name=name
        
class student(person):
    def __init__(self,sex,name,sno):
        super().__init__(sex,name)
        self.sno=sno

        
class flower:
    def __init__(self,colour):
        self.colour=colour
        
    
c1=person('男','李明')
c2=student('女','李华','12345')
c3=flower('red')

print(type(c1))
print(type(c2))
print(type(c3))

print('flower类是person类的子类:',issubclass(flower,person))
print('flower类是person类的子类:',issubclass(student,person))

6.类方法与静态方法

简介:

当一个属性是类所有而不是每个对象所拥有的时候要定义为类方法或静态方法,二者的区别是静态方法不用 写self,即静态方法并不绑定对象,也就无法修改对象的值

实例:类方法和静态方法实现复数加法
# -*- coding: utf-8 -*-
"""
类方法与静态方法:当类的一个方法是类所有而不是对象的方法时,可以定义为类方法或静态方法
类方法:@calssmethon               绑定了对象
静态方法:@staticmethod            未绑定对象
未绑定对象无法修改对象的值
"""

class complex:
    def __init__(self,real=0,image=0):
        self.real=real
        self.image=image
        
    @classmethod#类方法
    def add1(cls,c1,c2):
        c=complex()
        
        c2.real=3
        
        c.real=c1.real+c2.real
        c.image=c1.image+c2.image
        if c.image >=0:
            return str(c.real)+'+'+str(c.image)+'i'
        else:
            return str(c.real)+str(c.image)+'i'
        
        
        
    @staticmethod#静态方法
    def add2(c1,c2):
        c=complex()
        
        #c2.real=1 在静态方法里修改对象的值无法修改成功
        
        c.real=c1.real+c2.real
        c.image=c1.image+c2.image
        if c.image >=0:
            return str(c.real)+'+'+str(c.image)+'i'
        else:
            return str(c.real)+str(c.image)+'i'

        
c1=complex(1,2)
c2=complex(2,3)
c3=complex.add1(c1,c2)
print(c3)
c4=complex.add1(c1,c2)
print(c4)
        
    

7.动态扩展类和__slots__用法

简介:

动态扩展类:在不修改原有类的情况下动态的为类添加新的属性或方法
1.绑定新方法:需要使用 types 模块的 MethodType 方法
from types import Mythodtype
2.绑定新属性:
可以使用__slots__函数限制可绑定的新属性

绑定新方法例子
"""
动态扩展类:在不修改原有类的情况下动态的为类添加新的属性或方法
1.绑定新方法:需要使用 types 模块的 MethodType 方法
from types import Mythodtype
2.绑定新属性:
可以使用__slots__函数限制可绑定的新属性
"""
from types import MethodType 

class person:
    
    def __init__(self,sex,name):
        self.sex=sex;
        self.name=name
        
def printname(self):
    print('%s'%self.name)
    
def printsex(self):
    print('%s'%self.sex)

# 注意 __name__ 的用法
if  __name__ == '__main__':   
    person.printname=printname
    p1=person('男','李强')
    p2=person('女','李华')
    p1.printsex=MethodType(printsex,p1)
    
	#给person类绑定printname方法,给对象p1绑定printsex
    p1.printname()
    p2.printname()
    p1.printsex()
   #p2.printsex()  p2 无 printsex 这个功能
绑定新属性例子
class person:
    __slots__=('name')
        
class teacher(person):
    __slots__=('tno')

class student(person):
    pass

# 子类有限制会继承父类的限制,子类无限制不继承父类限制
if  __name__ == '__main__':   
    p1=person()
    p1.name='李华'
    
    t1=teacher()
    t1.name='李强'
    t1.tno='123'
    #t1.sno='122'  t1 不允许扩展 sno 会报错
    
    print('%s'%t1.tno)
    
    s1=student()
    s1.name='丽丽'
    s1.tno='123'
    s1.height='12'
    
    print('%s'%s1.height)
    
    # student类无限制,随意扩展

8.__del__ 方法和引用计数

简介:

使用 __del__ 方法时 , 当要释放一个对象的内存时
会先检查一个对象的引用计数,只有 count = 0 时才会释放内存

"""
使用 __del__ 方法时 , 当要释放一个对象的内存时
会先检查一个对象的引用计数,只有 count = 0 时才会释放内存

我们可以通过 sys 模块中的 getrefcount 来获取一个对象的引用计数

导致引用计数+1的情况:
1.对象被创建
2.对象被引用
3.对象作为参数被传入到一个函数中
4.对象作为元素被存储在容器中

导致引用计数-1的情况:
1.对象的别名被显式销毁
2.对象的别名被赋给了新的对象
3.一个对象离开了它的作用域(如一个函数执行完后,它里面的局部变量)
4.对象所存在的容器被销毁,或从容器中删除了对象

"""
import sys

class people:
    def __del__(self):
        print("对象已被销毁")
        
    pass

p1=people() #count = 1

count=sys.getrefcount(p1) # 对象作为参数被传到了一个函数中 count = 2
print(count)

p2=p1 #对象被引用 count = 3

count=sys.getrefcount(p1)
print(count)

del p2 #count = 1
print("-------1--------")
del p1 #count = 0
print("-------2--------")
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
可以定义一个名为`Student`的类来管理学生的成绩信息。以下是一个基本的示例: ```python class Student: def __init__(self, name, id): self.name = name self.id = id self.scores = {} def add_score(self, subject, score): self.scores[subject] = score def get_score(self, subject): return self.scores.get(subject) def get_average_score(self): total_score = sum(self.scores.values()) average_score = total_score / len(self.scores) return average_score ``` 在这个示例中,`Student`类具有以下几个方法和属性: - `__init__(self, name, id)`: 初始化方法,用于设置学生的姓名和学号,并创建一个空的成绩字典。 - `add_score(self, subject, score)`: 添加学生的某门课程的成绩,将科目和分数作为参数传入,并将其添加到成绩字典中。 - `get_score(self, subject)`: 获取学生某门课程的成绩,传入科目作为参数,返回该科目的成绩。 - `get_average_score(self)`: 计算学生所有科目的平均成绩,并返回平均成绩值。 使用这个类,你可以创建学生对象并进行成绩管理,例如: ```python # 创建学生对象 student1 = Student("张三", "20210001") # 添加成绩 student1.add_score("数学", 90) student1.add_score("英语", 85) student1.add_score("物理", 95) # 获取成绩和平均成绩 math_score = student1.get_score("数学") average_score = student1.get_average_score() print(f"{student1.name}的数学成绩为:{math_score}") print(f"{student1.name}的平均成绩为:{average_score}") ``` 输出结果: ``` 张三的数学成绩为:90 张三的平均成绩为:90.0 ``` 这只是一个简单的示例,你可以根据需求进一步扩展和修改`Student`类的功能。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

.Ashy.

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值