Python面向对象详解

文章目录

    • 类和继承
    • 变量保护
    • 类装饰器

类和继承

Python虽然以函数式著称,但在Python中,万物皆对象,其对面向对象编程是有着非常不错的支持的。类是面向对象的核心数据类型,下面代码就创建了一个Person类。

class Person:count = 0def __init__(self, name, ID):self.name = nameself.ID = IDPerson.count += 1def introduce(self):print(f"I'm {self.name}")def peopleCount(self):print(f"There are {Person.count} persons")p1 = Person("micro", 1)
p2 = Person("cold", 2)
p1.introduce()      # I'm micro
p1.peopleCount()    # There are 2 persons

其中,__init__函数用于类的初始化,参数self表示当前对象。所以创建p1和p2时,两人分别被赋予了不同的姓名和编号,并可通过introduce方法进行调用。

写在类内部、函数外部的变量属于整个类的共有变量,所以每当创建一个新的对象时,count都会加一。所以,无论p1还是p2在调用peopleCount函数时,均回得到共有两人的结果。当然,随着创建对象的增多,这个值也会随之增长。

在一个类中,一般变量被称作成员变量,函数被称作成员函数,也可称为方法。

如果只用一个关键词来形容面向对象,那么这个关键词一定是继承,不能继承的类将和结构体没什么区别。下面是一个继承了【Person】的类。

class Student(Person):def __init__(self, name, ID, grade):super(Student, self).__init__(name, ID)self.grade = gradedef introduce(self):print(f"I'm {self.name}", end=', ')self.getGrade()def getGrade(self):print(f"my grade is {self.grade}")p3.introduce()      # I'm soft, my grade is 4
p3.peopleCount()    # There are 3 persons

在类的继承过程中,如果想连带着继承类的某个方法,那么就可以直接将这个方法省略,比如peopleCount,便直接沿用了Person类中的内容。

相应地,如果重新写了这个函数,那么这个函数就会焕然一新,而与父类的同名方法变得毫无关联,这个过程叫做方法重写。introduce就是这种情况,虽然与Person类有着相同的名字,但输出结果发生了变化。

初始化函数也是一样,如果省略,就会沿用父类的做法;如果重写,就会变得与父类无关。super函数为子类和父类的函数之间架设了一道桥梁,super(Student, self)即可找到Student的父类,并调用其中的函数。所以Student类尽管重写了初始化方法,但也沿用了父类的一些处理,从而节约了代码。

变量保护

在Python中,出于于某些考虑,会对属性加以保护,不得随意访问。比如一个人的年龄,大小倒是无所谓了,但必须得是个数值,如果完全暴露出去,那被人改成字符串麻烦可就大了。

为此,在Python中,如果某个成员以双下划线开头,那么这就是无法被访问的,从而使得变量得以保护。

但另一方面,又不得不围绕这个属性创建一系列方法,最起码就得包括设置和读取的功能,为了让这些功能更易于调用,Python提供了property函数,示例如下

class Private(Person):def set_age(self, age):if type(age)==int:self.__age = agedef get_age(self):return self.__agedef del_age(self):del self.__ageage = property(get_age, set_age, '年龄')p3 = Private("c", 3)
p3.age = 18
print(p3.age)   # 18
p3.__age
'''直接调用会报错
Traceback (most recent call last):File "<stdin>", line 1, in <module>
AttributeError: 'Person' object has no attribute '__age'
'''
p3.age = "20"
print(p3.get_age())
print(p3.age)   # 18

其中,_age是一个私有变量,受到保护,无法访问。而age则可以赋值和调用值。但是,当把age的值设为字符串时,并没有响应,可见当赋值的时候,的确是调用了set_age方法。

property提供了装饰器的语法糖,从而上述功能可以写成形如下式的更加简洁的形式,并且添加了删除属性的功能。

class Private(Person):@propertydef age(self):return self.__age@age.setterdef age(self, age):if type(age)==int:self.__age = age@age.deleterdef age(self):del self.__age

在编程时,类内部的很多东西并不想被外界得到,即需要一种访问限制的方法,以避免下列情况的发生

p3.count -= 5
print(p3.count)   # -2

类装饰器

一般来说,在Python类中不加修饰的方法叫做实例方法,即只有经过经过实例化之后,才能调用。但也存在另一种需求,即不创建类的对象,而直接调用类的方法。比如想通过类的方法进行初始化,或者干脆只是把类当作一个函数库。

为此,可以使用类方法和静态方法,这两种方法可直接通过类的名字进行调用。区别在于,类方法会将类自身作为第一个参数传入,而静态方法则完全就是一个函数,某种意义上来讲,似乎和这个类并无关联,示例如下。

class Person:count = 0def __init__(self, name, ID):self.name = nameself.ID = IDPerson.count += 1def introduce(self):print(f"I'm {self.name}")@classmethoddef peopleCount(cls):print(f"There are {cls.count} persons")@classmethoddef alphaMan(cls, name, ID):cls.count -= 1return Person(name, ID)@staticmethoddef add(a,b):return a+b

其中,introduce是实例方法,无需多言。

【classmethod】是类方法的装饰器,上面代码中,peopleCount和alphaMan都是类方法,其第一个参数cls指代的就是Person自身。

【staticmethod】是静态方法修饰器,add方法即为静态方法,可见这个方法的目的是求和,从代码结构来看,实在看不到与Person的半点关联。

示例如下,可见静态方法和类方法均可不经实例化而调用,且前者与普通的函数没什么区别。当调用构造函数创建对象时,count会增加;而创建一个透明人,由于代码中剪掉了一个计数,所以count并不会增加。

Person.add(3,4)         # 7
Person.peopleCount()    # There are 0 persons
p1 = Person("a", 1)
Person.peopleCount()    # There are 1 persons
p2 = Person.alphaMan("b", 2)
Person.peopleCount()    # There are 1 persons

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/803157.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

2024马来西亚电商选品博览会

2024马来西亚电商选品博览会 展会概况 展会名称&#xff1a;2024马来西亚电商选品博览会 主办单位&#xff1a;广东进出口商会 时间:2024.11.29-12.1 地点&#xff1a;马来西亚国际贸易展览中心(MITEC) 展览面积&#xff1a;10000平方米 展会简介 2024马来西亚跨境电商选…

包和final.Java

1&#xff0c;包 包就是文件夹。用来管理不同功能的Java类&#xff0c;方便后期代码的维护。 &#xff08;1&#xff09;包名的规则是什么&#xff1f; 公司域名反写报的作用&#xff0c;需要全部英文小写&#xff0c;见名知意。com.itheima.domain &#xff08;2&#xff…

抓住风口,快速上手RAG应用开发!

免责声明~ 任何文章不要过度深思&#xff01; 万事万物都经不起审视&#xff0c;因为世上没有同样的成长环境&#xff0c;也没有同样的认知水平&#xff0c;更「没有适用于所有人的解决方案」&#xff1b; 不要急着评判文章列出的观点&#xff0c;只需代入其中&#xff0c;适度…

蓝桥杯第十一届c++大学B组详解

目录 1.字符串排序 2.门牌制作 3.即约分数 4.蛇型填数 5.跑步锻炼 6.七段码 7.成绩统计 8.回文日期 9.字串分值和 10.平面切分 1.字符串排序 题目解析&#xff1a;这个题目真没搞懂。有会的大佬教我一下谢谢。 2.门牌制作 题目解析&#xff1a;出过超级多这类题目&am…

NumPy进阶(二)

2. NumPy进阶(二) 2.1 Numpy数组操作 2.1.1 添加元素 numpy.append 函数在数组的末尾添加值。 追加操作会分配整个数组&#xff0c;并把原来的数组复制到新数组中 注意&#xff1a; 插入的维度要保证所有数组的长度是相同的如果没有指定轴&#xff0c;数组会被扁平处理 ndarr…

第四百四十九回

文章目录 1. 知识回顾2. 使用方法3. 示例代码4. 经验与总结4.1 经验分享 我们在上一章回中介绍了"overlay_tooltip简介"相关的内容&#xff0c;本章回中将再谈flutter_launcher_icons包.闲话休提&#xff0c;让我们一起Talk Flutter吧。 1. 知识回顾 我们第四百一十…

docker安装nodejs

要在 Docker 中安装 Node.js&#xff0c;你可以使用官方提供的 Node.js 镜像。以下是在 Docker 中安装 Node.js 的基本步骤&#xff1a; 拉取 Node.js 镜像&#xff1a; docker pull node 运行 Node.js 镜像&#xff1a; docker run -it node 确认 Node.js 是否成功安装&…

教你如何玩转副业:开启编程副业新篇章

前言 在浩瀚的编程海洋中&#xff0c;C语言以其简洁、高效、贴近硬件的特性&#xff0c;成为无数程序员心中的“白月光”。作为一位程序员&#xff0c;如果你不仅掌握了这门语言的精髓&#xff0c;更渴望通过副业来挑战自我、实现价值。那么&#xff0c;如何用C语言开启你的副…

题目:取一个整数a从右端开始的4~7位。

题目&#xff1a;取一个整数a从右端开始的4&#xff5e;7位。 There is no nutrition in the blog content. After reading it, you will not only suffer from malnutrition, but also impotence. The blog content is all parallel goods. Those who are worried about being…

pta L1-010 比较大小

L1-010 比较大小 分数 10 全屏浏览 切换布局 作者 杨起帆 单位 浙大城市学院 本题要求将输入的任意3个整数从小到大输出。 输入格式: 输入在一行中给出3个整数&#xff0c;其间以空格分隔。 输出格式: 在一行中将3个整数从小到大输出&#xff0c;其间以“->”相连。…

【力扣】209. 长度最小的子数组

209. 长度最小的子数组 题目描述 给定一个含有 n 个正整数的数组和一个正整数 target 。 找出该数组中满足其总和大于等于 target 的长度最小的 连续子数组 [numsl, numsl1, ..., numsr-1, numsr] &#xff0c;并返回其长度。如果不存在符合条件的子数组&#xff0c;返回 0 …

A7 STM32_HAL库函数 之 LCORTEX通用驱动程序所有函数的介绍及使用

A1 STM32_HAL库函数 之 HAL系统驱动程序所有函数的介绍及使用 1 LCORTEX通用驱动程序预览1.1 HAL_NVIC_SetPriorityGrouping1.2 HAL_NVIC_SetPriority1.3 HAL_NVIC_EnableIRQ1.4 HAL_NVIC_DisableIRQ1.5 HAL_NVIC_SystemReset1.6 HAL_SYSTICK_Config1.7 HAL_MPU_Disable1.8 HAL…

亚信安慧AntDB:在数据的宇宙中探索无限可能

亚信安慧AntDB数据库探索出自主可控的数据库架构&#xff0c;在架构层面消除应用对特定数据库的依赖。它以其稳定可靠的性能和高度可伸缩性而备受赞誉。AntDB数据库架构通过引入创新的分布式体系结构&#xff0c;充分利用集群资源&#xff0c;实现数据的高效分布和快速存取。 …

浅谈对进程的理解

一、多任务的概念 1、举个栗子 思考&#xff1a;我们在使用网盘下载资料的时候&#xff0c;为什么要多个任务同时下载呢&#xff1f; 答&#xff1a;多个任务同时执行可以大大提高程序的执行效率 2、提出问题 问题&#xff1a;利用我们目前所学的技术&#xff0c;我们能否…

输入框验证数字类型

校验大于0的数,且小数点后最多为八位小数 let k /^(?!0(\.0)?$)\d(\.\d{1,8})?$/; console.log(k.test(0.00000001)); // true console.log(k.test(0.00000000)); // false console.log(k.test(0.12)); // true console.log(k.test(12.12)); // true输入0-1的数字&#xf…

【计算机考研】408算法大题怎么练?

先说结论&#xff1a;基础阶段学好各个数据结构与&#xff0c;重点是数组、链表、树、图。然后强化阶段突破算法提 在基础阶段&#xff0c;并不需要过于专门地练习算法。相反&#xff0c;基础阶段的重点应该放在对各种数据结构原理的深入理解上。在我个人的经验中&#xff0c;…

python--异常处理

异常处理 例一&#xff1a; try: #可能出现异常代码 except&#xff1a; #如果程序异常&#xff0c;则立刻进入这儿 [finally: #不管是否捕获异常&#xff0c;finally语法快必须要执行&#xff01;&#xff01;&#xff01; #资源关闭&#xff0c;等各种非常重要的操作&…

HarmonyOS实战开发-如何使用 geolocation 实现获取当前位置经纬度

介绍 本示例使用 geolocation 实现获取当前位置的经纬度,然后通过 http 将经纬度作为请求参数,获取到该经纬度所在的城市。通过 AlphabetIndexer 容器组件实现按逻辑结构快速定位容器显示区域。 效果预览 使用说明 1.进入主页,点击国内热门城市,配送地址会更新为选择的城…

【Erlang】【RabbitMQ】Linux(CentOS7)安装Erlang和RabbitMQ

一、系统环境 查版本对应&#xff0c;CentOS-7&#xff0c;选择Erlang 23.3.4&#xff0c;RabbitMQ 3.9.16 二、操作步骤 安装 Erlang repository curl -s https://packagecloud.io/install/repositories/rabbitmq/erlang/script.rpm.sh | sudo bash安装 Erlang package s…

CAXA电子图版2019版 下载地址及安装教程

CAXA电子图板是一款由国内软件公司CAXA开发的专业CAD&#xff08;计算机辅助设计&#xff09;软件。它主要用于绘制和编辑各种类型的二维图纸和工程图纸&#xff0c;广泛应用于建筑、机械、电气和电子等行业。 CAXA电子图板具有以下主要功能和特点&#xff1a; 二维绘图&…