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

Python 属性封装(Attribute Encapsulation)

封装是面向对象编程中的基本概念之一(与继承、多态和抽象并列)。封装将属性隐藏在类内部,就像胶囊一样,防止未经授权的直接访问。同时类会提供一些方法来访问和修改属性值,这为属性提供了一定程度的隐私保护——不能直接访问对象属性,但可以通过调用方法(代理)对属性执行操作。


文章目录

  • 一、类变量命名约定
    • 1.1 "私有"变量
  • 二、通过@property对属性进行封装
    • 2.1 定义属性访问
    • 2.2 定义属性修改
    • 2.3 定义属性删除

一、类变量命名约定

1.1 "私有"变量

在 Python 中,如果想要命名“私有变量”,通常有以下两种约定方式:

  • _variable,前置单下划线,这是一种命名约定,表示“别随便用”,提示该变量为内部使用。
  • __variable,前置双下划线,Python 解释器会进行名称改写(Name Mangling),将其转换为 _类名__variable 的形式,以减少被子类或外部意外修改的可能性。

要注意的是,这两种方式只是一种希望大家遵守的"约定",并不是真正的私有变量,即使是双下划线命名,仍然可以通过改写后的变量名进行访问。

下面定义一个类,包含2个"私有"变量:

class Attr:def __init__(self, var1, var2):self._var1 = var1self.__var2 = var2    # 变量名会被改写成_Attr__var2

实例化之后,通过_var1和改写后的a._attr__var2依然可以访问变量内容:

a = Attr(1,2)
a._var1
a._Attr__var2

在这里插入图片描述

二、通过@property对属性进行封装

如要要对属性进行更复杂的控制,Python提供了内置装饰器@property,它可以控制属性的访问,对外部调用者来说,可以像正常一样访问属性,但内部可以对属性增加校验、计算等逻辑。

2.1 定义属性访问

下面的类Acct,定义了一个"私有"变量__balance,并通过@property装饰器定义了一个方法来对它进行访问

class Acct:def __init__(self, balance):self.__balance = balance@propertydef balance(self):print('通过方法访问balance:')return self.__balance

正常访问balance属性,Python会自动调用@property修饰的balance方法(方法名作为属性名):

a = Acct(100)
a.balance

在这里插入图片描述
属性封装对调用者是透明的,调用者无法意识到他是直接访问了属性,还是在和控制属性访问的方法对话,这里我们故意加了一个print语句,告诉调用者通过方法访问了属性,实际应用中可以根据需要进行校验、日志记录等操作。

2.2 定义属性修改

@property修饰的是属性读取方法,这种方法称为getter,通过"@变量名.setter"装饰器可以指定属性的修改方法。

在上面代码基础上新增一个修改方法,并在修改方法中定义了一个校验逻辑:不能将balance修改为负值:

class Acct:def __init__(self, balance):self.__balance = balance@propertydef balance(self):print('通过方法访问balance:')return self.__balance@balance.setterdef balance(self, amt):if amt < 0:raise ValueError('余额不能设置为负')print('通过方法设置balance为:', amt)self.__balance = amt

实例化后,尝试将balance修改为正值和负值,观察效果:

a = Acct(100)
a.balance = 200    # 修改成功
a.balance = -200    # 修改失败,禁止修改为负值

在这里插入图片描述

这里可以看到校验逻辑生效了,成功阻止了将balance修改为负值,这种方式可以有效阻止在程序中输入非法值。

2.3 定义属性删除

和修改方法类似,通过"@变量名.deleter"可以指定属性删除方法,在上面的代码后新增删除方法,在删除属性的时候提示"不能删除balance属性",并将其设置为空:

class Acct:def __init__(self, balance):self.__balance = balance@propertydef balance(self):print('通过方法访问balance:')return self.__balance@balance.setterdef balance(self, amt):if amt < 0:raise ValueError('余额不能设置为负')print('通过方法设置balance为:', amt)self.__balance = amt@balance.deleterdef balance(self):print('不能删除balance属性,设置为空')self.__balance = None

实例化后,尝试删除balance属性,删除方法成功执行,提示禁止删除,并将变量设置为空:

a = Acct(100)
del a.balance

在这里插入图片描述

以上即是使用@property进行属性封装的用法,通过封装可以在给属性赋值或获取值时加入条件判断、类型检查、逻辑计算等操作,从而保证对象的完整性和数据有效性。

http://www.dtcms.com/a/341430.html

相关文章:

  • Docker在Linux中安装与使用教程
  • ubuntu privileged cont 一直在读取硬盘
  • ubuntu24.04 frps服务器端自动启动设置【2025-08-20】
  • JUC之CompletableFuture【下】
  • 内网安全——出网协议端口探测
  • RAG拓展、变体、增强版(一)
  • 【深度学习-Day 43】解密LSTM:深入理解长短期记忆网络如何克服RNN的遗忘症
  • 8.20网络编程——sqlite3数据库
  • 计算机视觉(二):视觉的处理流程
  • Promise.all 速查与扩展实战
  • 基于SpringBoot的蜗牛兼职网平台
  • React框架超详细入门到实战项目演练【前端】【React】
  • Spring Retry实战指南_让你的应用更具韧性
  • PyTorch API 2
  • 漫漫长夜 全DLC(The Long Dark)免安装中文版
  • Docker之MySQL安装
  • Redis(以Django为例,含具体操作步骤)
  • 数字人制作全流程解析:从概念到落地的完整步骤​
  • 实战:本地大模型+function Calling,获取北京天气
  • uniapp学习【上手篇】
  • [激光原理与应用-314]:光学设计 - 光学系统设计与电子电路设计的相似或相同点
  • 1-2前端撸码前的准备,包管理工具和环境搭建
  • 升级Android系统webview
  • Spring事务源码
  • Linux Capability 解析
  • 【81页PPT】智慧方案智能化弱电智能家居系统解决方案(附下载方式)
  • 如何解决pip安装报错ModuleNotFoundError: No module named ‘requests-html’问题
  • VPS服务器安全审计方案:从风险评估到防护实施
  • 汇编语言学习3---GDB调试
  • 【StarRocks】TabletChecker逻辑