当前位置: 首页 > news >正文

python | Python中的类多态:方法重写和动态绑定

本文来源公众号“python”,仅用于学术分享,侵权删,干货满满。

原文链接:Python中的类多态:方法重写和动态绑定

多态(Polymorphism)是面向对象编程的核心特性之一,它允许同一接口在不同的类中具有不同的实现。多态通过方法重写和动态绑定来实现,使得代码更加灵活和可扩展。本文将详细介绍Python中的类多态,包括方法重写和动态绑定,涵盖基本概念、具体用法和实际应用示例。

1 多态的基本概念

多态是指一个接口可以有多个实现。在Python中,多态通常通过继承和方法重写来实现,使得子类可以提供特定于自己的实现,同时保持与父类接口的一致性。

1.1 方法重写

方法重写(Method Overriding)是指子类重新定义父类中的方法。重写的方法必须具有与父类方法相同的名称和参数。

class Animal:def speak(self):return "Animal sound"class Dog(Animal):def speak(self):return "Woof!"class Cat(Animal):def speak(self):return "Meow!"animal = Animal()
dog = Dog()
cat = Cat()print(animal.speak())  # 输出:Animal sound
print(dog.speak())     # 输出:Woof!
print(cat.speak())     # 输出:Meow!

在这个示例中,DogCat类重写了Animal类的speak方法,提供了各自的实现。

2 动态绑定

动态绑定(Dynamic Binding)是指在运行时决定调用哪个方法。Python的动态绑定机制使得程序在运行时能够根据对象的实际类型调用相应的方法。

class Animal:def speak(self):return "Animal sound"class Dog(Animal):def speak(self):return "Woof!"class Cat(Animal):def speak(self):return "Meow!"def make_sound(animal):print(animal.speak())make_sound(Animal())  # 输出:Animal sound
make_sound(Dog())     # 输出:Woof!
make_sound(Cat())     # 输出:Meow!

在这个示例中,make_sound函数接受一个Animal对象,并调用其speak方法。由于Python的动态绑定机制,调用的是对象实际类型的方法实现。

3 多态的实际应用

3.1 图形绘制系统

假设需要实现一个图形绘制系统,不同的图形(如圆形、矩形)有不同的绘制方法。

class Shape:def draw(self):raise NotImplementedError("Subclasses must implement this method")class Circle(Shape):def draw(self):print("Drawing a circle")class Rectangle(Shape):def draw(self):print("Drawing a rectangle")def draw_shape(shape):shape.draw()circle = Circle()
rectangle = Rectangle()draw_shape(circle)     # 输出:Drawing a circle
draw_shape(rectangle)  # 输出:Drawing a rectangle

在这个示例中,CircleRectangle类重写了Shape类的draw方法,draw_shape函数根据传入对象的实际类型调用相应的draw方法。

3.2 支付系统

假设需要实现一个支付系统,不同的支付方式(如信用卡、Paypal)有不同的处理方法。

class Payment:def pay(self, amount):raise NotImplementedError("Subclasses must implement this method")class CreditCardPayment(Payment):def pay(self, amount):print(f"Paying {amount} using Credit Card")class PaypalPayment(Payment):def pay(self, amount):print(f"Paying {amount} using Paypal")def process_payment(payment, amount):payment.pay(amount)credit_card_payment = CreditCardPayment()
paypal_payment = PaypalPayment()process_payment(credit_card_payment, 100)  # 输出:Paying 100 using Credit Card
process_payment(paypal_payment, 200)       # 输出:Paying 200 using Paypal

在这个示例中,CreditCardPaymentPaypalPayment类重写了Payment类的pay方法,process_payment函数根据传入对象的实际类型调用相应的pay方法。

4 使用抽象基类

抽象基类(Abstract Base Class, ABC)提供了一种强制子类实现特定方法的方式。Python的abc模块允许定义抽象基类和抽象方法。

from abc import ABC, abstractmethodclass Animal(ABC):@abstractmethoddef speak(self):passclass Dog(Animal):def speak(self):return "Woof!"class Cat(Animal):def speak(self):return "Meow!"dog = Dog()
cat = Cat()print(dog.speak())  # 输出:Woof!
print(cat.speak())  # 输出:Meow!

在这个示例中,Animal是一个抽象基类,定义了一个抽象方法speak,子类必须实现这个方法。

5 动态绑定和鸭子类型

鸭子类型(Duck Typing)是Python的一种动态类型机制,通过对象的行为而不是类型来决定对象是否合适。在使用多态时,鸭子类型可以使代码更加灵活。

class Duck:def quack(self):return "Quack!"class Person:def quack(self):return "I'm pretending to be a duck!"def make_quack(duck):print(duck.quack())duck = Duck()
person = Person()make_quack(duck)    # 输出:Quack!
make_quack(person)  # 输出:I'm pretending to be a duck!

在这个示例中,make_quack函数不关心传入对象的类型,只要对象具有quack方法即可。

6 多态和组合

组合(Composition)是另一种代码复用的方式,它通过包含对象而不是继承来实现代码复用。多态和组合可以结合使用,以提高代码的灵活性和可维护性。

class Engine:def start(self):return "Engine started"class Car:def __init__(self, engine):self.engine = enginedef start(self):return self.engine.start()engine = Engine()
car = Car(engine)print(car.start())  # 输出:Engine started

在这个示例中,Car类包含一个Engine对象,通过组合实现了代码复用,并通过多态调用了Enginestart方法。

7 总结

本文深入探讨了Python中的类多态,重点介绍了方法重写和动态绑定的概念与实现。通过具体示例,如图形绘制系统和支付系统,展示了如何利用多态使代码更加灵活和可扩展。还介绍了使用抽象基类和鸭子类型实现多态的高级用法,展示了它们在实际开发中的应用。多态是面向对象编程的核心特性之一,它通过允许不同类以相同接口进行操作,使代码更加简洁和可维护。

THE END !

文章结束,感谢阅读。您的点赞,收藏,评论是我继续更新的动力。大家有推荐的公众号可以评论区留言,共同学习,一起进步。

相关文章:

python | Python中的类多态:方法重写和动态绑定

本文来源公众号“python”,仅用于学术分享,侵权删,干货满满。 原文链接:Python中的类多态:方法重写和动态绑定 多态(Polymorphism)是面向对象编程的核心特性之一,它允许同一接口在…...

Rust编写Windows服务

文章目录 Rust编写Windows服务一:Windows服务程序大致原理二:Rust中编写windows服务三:具体实例 Rust编写Windows服务 编写Windows服务可选语言很多, 其中C#最简单。本着练手Rust语言,尝试用Rust编写一个服务。 一:Win…...

MATLAB 从 R2024B 开始支持树莓派 5

树莓派(Raspberry Pi)系列是一系列基于单板计算机的微型电脑,由英国的树莓派基金会于 2012 年开始发布。它的目标是提供一个低成本、易于学习和玩耍的平台,用于教育和初学者学习计算机科学和编程。 目前市面上,最新最…...

MiniBlogum项目简介

MiniBlogum项目简介 文章目录 MiniBlogum项目简介一、引言二、技术栈与开发环境三、主要功能(一)用户注册与登录(二)查看当前登录用户/作者头像、昵称、Gitee仓库地址(三)查看博客列表(四&#…...

如何用 OBProxy 实现 OceanBase 的最佳路由策略

引言 OBProxy,即OceanBase Database Proxy,也简称为ODP,是 OceanBase数据库的专属服务代理。通过应用OBProxy,由后端OceanBase集群的分布式特性所带来的复杂性得以屏蔽,从而使得访问分布式数据库的体验如同访问单机数…...

new/delete和malloc/free到底有什么区别

new和malloc 文章目录 new和malloc前言一、属性上的区别二、使用上的区别三、内存位置的区别四、返回类型的区别五、分配失败的区别六、扩张内存的区别七、系统调度过程的区别总结 前言 new和malloc的知识点,作为一个嵌入式工程师是必须要了解清楚的。new和malloc的…...

Flutter启动无法运行热重载

当出现这种报错时,大概率是flutter的NO_Proxy出问题。 请忽略上面的Android报错因为我做的是windows开发这个也就不管了哈,解决下面也有解决报错的命令大家执行一下就行。 着重说一下Proxy的问题, 我们看到提示NO_PROXY 没有设置。 这个时候我…...

CSS调整背景

一、设置背景颜色 通过 background-color 属性指定,值可以是十六进制 #ffffff,也可以是rgb(0, 255, 255),或是颜色名称 "red" div {background-color: red; /* 通过颜色名称设置 */background-color: #ff0000; /* 通过十六进制设…...

FinalShell连接Linux服务器并解决反复输入密码问题

FinalShell是一款由国人开发的SSH客户端工具,它支持多平台,包括Windows、Mac OS X和Linux。FinalShell主要用于一体化服务器管理,它不仅是一个SSH客户端,还具备强大的开发和运维功能,能够充分满足开发和运维的需求。 本…...

实用类工具!分享6款AI论文一键生成器免费8000字

在当前的学术研究和写作领域,AI论文生成工具的出现极大地提高了写作效率和质量。这些工具不仅能够帮助研究人员快速生成论文草稿,还能进行内容优化、查重和排版等操作。千笔-AIPassPaper是一款备受推荐的AI论文一键生成器。 千笔-AIPassPaper是一个一站式…...

vue使用TreeSelect设置带所有父级节点的回显

Element Plus的el-tree-select组件 思路: 选中节点时,给选中的节点赋值 pathLabel,pathLabel 为函数生成的节点名字拼接,数据源中不包含。 在el-tree-select组件中设置 props“{ label: ‘pathLabel’ }” 控制选中时input框中回…...

智能机巢+无人机:自动化巡检技术详解

智能机巢与无人机的结合,在自动化巡检领域展现出了巨大的潜力和优势。以下是对这一技术的详细解析: 一、智能机巢概述 智能机巢,也被称为无人机机场或无人机机巢,是专门为无人机提供停靠、充电、维护等服务的智能化设施。它不仅…...

摩托车加装车载手机充电usb方案/雅马哈USB充电方案开发

长途骑行需要给手机与行车记录仪等设备供电,那么,加装USB充电器就相继在两轮电动车上应用起来了。摩托车加装usb充电方案主要应用于汽车、电动自行车、摩托车、房车、渡轮、游艇等交通工具。提供电动车USB充电器方案/摩托车加装usb充电方案/渡轮加装usb充…...

进阶岛 任务3: LMDeploy 量化部署进阶实践

进阶岛 任务3: LMDeploy 量化部署进阶实践 任务:https://github.com/InternLM/Tutorial/blob/camp3/docs/L2/LMDeploy/task.md 使用结合W4A16量化与kv cache量化的internlm2_5-1_8b-chat模型封装本地API并与大模型进行一次对话,作业截图需包…...

vue 使用jszip,file-saver下载压缩包,自定义文件夹名,文件名打包下载为zip压缩包文件,全局封装公共方法使用。

记录一下后台管理全局封装一个压缩包下载方法,文件夹名自定义,文件名自定义,压缩包名自定义。 安装必要的库 npm install jszip npm install file-saver自定义一个公共方法全局注入 页面使用 /** 下载按钮操作 */handleDownload() {const i…...

计网八股文

1.HTTP和HTTPS的区别 安全性: HTTP:是未加密的协议,意味着数据在传输过程中可以被截获、篡改或监听。它不提供任何数据加密。HTTPS:在HTTP的基础上加入了SSL/TLS协议,提供了数据加密、完整性校验和身份验证。这使得传输…...

[001-03-007].第07节:Redis中的事务

我的后端学习大纲 我的Redis学习大纲 1、Redis事务是什么: 1.可以一次执行多个命令,本质是一组命令的集合。一个事务中的所有命令都会序列化, 按顺序地串行化执行而不会被其他命令插入,不许加塞2.一个队列中,一次性、…...

WLAN实验简述

一:配置生产AP1上级接入层交换机LSW3 sys [Huawei]sysname LSW3 [LSW3]undo info-center enable [LSW3]vlan batch 10 100 [LSW3]int g0/0/2 [LSW3-GigabitEthernet0/0/2]port link-type trunk [LSW3-GigabitEthernet0/0/2]port trunk allow-pass vlan 10 100 [LSW…...

Docker简介在Centos和Ubuntu环境下安装Docker

文章目录 1.Docker简介2.Docker镜像与容器3.安装Docker3.1 Centos环境3.2 Ubuntu环境 1.Docker简介 Docker 是一个开源的应用容器引擎,它允许开发者将应用程序及其依赖项打包到一个可移植的容器中,然后发布到任何流行的 Linux 或 Windows 操作系统上。D…...

C:字符串函数(续)-学习笔记

穗 一些闲话: 最近玩了这款饿殍-明末千里行,不知大家是否有听过这款游戏,颇有感触!!! 游戏中最让我难以忘怀的便是饿殍穗线的故事,生在如今时代的我之前无法理解杜甫在目睹人间悲剧时的心情&…...

React Native 开发环境搭建(全平台详解)

React Native 开发环境搭建(全平台详解) 在开始使用 React Native 开发移动应用之前,正确设置开发环境是至关重要的一步。本文将为你提供一份全面的指南,涵盖 macOS 和 Windows 平台的配置步骤,如何在 Android 和 iOS…...

k8s从入门到放弃之Ingress七层负载

k8s从入门到放弃之Ingress七层负载 在Kubernetes(简称K8s)中,Ingress是一个API对象,它允许你定义如何从集群外部访问集群内部的服务。Ingress可以提供负载均衡、SSL终结和基于名称的虚拟主机等功能。通过Ingress,你可…...

练习(含atoi的模拟实现,自定义类型等练习)

一、结构体大小的计算及位段 (结构体大小计算及位段 详解请看:自定义类型:结构体进阶-CSDN博客) 1.在32位系统环境,编译选项为4字节对齐,那么sizeof(A)和sizeof(B)是多少? #pragma pack(4)st…...

跨链模式:多链互操作架构与性能扩展方案

跨链模式:多链互操作架构与性能扩展方案 ——构建下一代区块链互联网的技术基石 一、跨链架构的核心范式演进 1. 分层协议栈:模块化解耦设计 现代跨链系统采用分层协议栈实现灵活扩展(H2Cross架构): 适配层&#xf…...

学习STC51单片机31(芯片为STC89C52RCRC)OLED显示屏1

每日一言 生活的美好,总是藏在那些你咬牙坚持的日子里。 硬件:OLED 以后要用到OLED的时候找到这个文件 OLED的设备地址 SSD1306"SSD" 是品牌缩写,"1306" 是产品编号。 驱动 OLED 屏幕的 IIC 总线数据传输格式 示意图 …...

关于 WASM:1. WASM 基础原理

一、WASM 简介 1.1 WebAssembly 是什么? WebAssembly(WASM) 是一种能在现代浏览器中高效运行的二进制指令格式,它不是传统的编程语言,而是一种 低级字节码格式,可由高级语言(如 C、C、Rust&am…...

Linux 中如何提取压缩文件 ?

Linux 是一种流行的开源操作系统,它提供了许多工具来管理、压缩和解压缩文件。压缩文件有助于节省存储空间,使数据传输更快。本指南将向您展示如何在 Linux 中提取不同类型的压缩文件。 1. Unpacking ZIP Files ZIP 文件是非常常见的,要在 …...

Kubernetes 节点自动伸缩(Cluster Autoscaler)原理与实践

在 Kubernetes 集群中,如何在保障应用高可用的同时有效地管理资源,一直是运维人员和开发者关注的重点。随着微服务架构的普及,集群内各个服务的负载波动日趋明显,传统的手动扩缩容方式已无法满足实时性和弹性需求。 Cluster Auto…...

C++_哈希表

本篇文章是对C学习的哈希表部分的学习分享 相信一定会对你有所帮助~ 那咱们废话不多说,直接开始吧! 一、基础概念 1. 哈希核心思想: 哈希函数的作用:通过此函数建立一个Key与存储位置之间的映射关系。理想目标:实现…...

在 Visual Studio Code 中使用驭码 CodeRider 提升开发效率:以冒泡排序为例

目录 前言1 插件安装与配置1.1 安装驭码 CodeRider1.2 初始配置建议 2 示例代码:冒泡排序3 驭码 CodeRider 功能详解3.1 功能概览3.2 代码解释功能3.3 自动注释生成3.4 逻辑修改功能3.5 单元测试自动生成3.6 代码优化建议 4 驭码的实际应用建议5 常见问题与解决建议…...