IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> Python知识库 -> 【Python面向对象编程】第16篇 运算符重载 -> 正文阅读

[Python知识库]【Python面向对象编程】第16篇 运算符重载

本篇我们学习 Python 运算符重载,了解如何使用内置运算符操作自定义的类对象。

运算符重载

以下示例创建了一个表示二维空间点的类,包含 x 坐标 和 y 坐标两个属性:

class Point2D:
    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __str__(self):
        return f'({self.x},{self.y})'

为了实现两个 Point2D 对象相加,我们可以定义一个 add() 方法:

class Point2D:
    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __str__(self):
        return f'({self.x},{self.y})'

    def add(self, point):
        if not isinstance(point, Point2D):
            raise ValueError('The other must be an instance of the Point2D')

        return Point2D(self.x + point.x, self.y + point.y)

如果 point 参数不是 Point2D 类的实例,add() 方法将会返回一个错误;否则,它会返回一个新的 Point2D 对象,该对象的 x 和 y 坐标等于两个点的 x 和 y 坐标之和。

以下代码创建了两个 Point2D 类实例并使用 add() 方法将两个坐标点进行相加:

a = Point2D(10, 20)
b = Point2D(15, 25)
c = a.add(b)

print(c)

输出结果如下:

(25,45)

以上代码可以正常运行,但是 Python 提供了更好的实现方法。除了使用 add() 方法之外,我们还可以使用内置的 + 运算符:

c = a + b

当我们使用 + 运算符操作 Point2D 对象时,Python 会调用对象的 __add__() 方法。以下调用方法效果相同:

c = a + b
c = a.__add__(b)

上面的 __add__() 方法必须返回一个新的 Point2D 对象实例。

使用内置运算符操作自定义类型的功能被称为运算符重载。以下示例中的 Point2D 类实现了 __add__() 方法,可以支持 + 运算符:

class Point2D:
    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __str__(self):
        return f'({self.x},{self.y})'

    def __add__(self, point):
        if not isinstance(point, Point2D):
            raise ValueError('The other must be an instance of the Point2D')

        return Point2D(self.x + point.x, self.y + point.y)


if __name__ == '__main__':
    a = Point2D(10, 20)
    b = Point2D(15, 25)
    c = a + b
    print(c)

输出结果如下:

(25,45)

运算符重载的特殊方法

下表列出了各种运算符以及对应的特殊方法:

运算符特殊方法
+__add__(self, other)
__sub__(self, other)
*__mul__(self, other)
/__truediv__(self, other)
//__floordiv__(self, other)
%__mod__(self, other)
**__pow__(self, other)
>>__rshift__(self, other)
<<__lshift__(self, other)
&__and__(self, other)
^__xor__(self, other)

例如,我们可以实现 Point2D 类的 __sub__() 方法,支持两个坐标点的减法运算:

class Point2D:
    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __str__(self):
        return f'({self.x},{self.y})'

    def __add__(self, point):
        if not isinstance(point, Point2D):
            raise ValueError('The other must be an instance of the Point2D')

        return Point2D(self.x + point.x, self.y + point.y)

    def __sub__(self, other):
        if not isinstance(other, Point2D):
            raise ValueError('The other must be an instance of the Point2D')

        return Point2D(self.x - other.x, self.y - other.y)


if __name__ == '__main__':
    a = Point2D(10, 20)
    b = Point2D(15, 25)
    c = b - a
    print(c)

inplace 运算符的重载

某些运算符还提供了 inplace 版本。例如,+ 运算符的 inplace 版本是 += 运算符。

对于不可变类型,例如元组、字符串以及数字,inplace 运算符执行计算操作但不会将结果赋予输入对象。对于可变类型,inplace 运算符直接对原始对象进行修改。

Python 同样为 inplace 运算符重载提供了许多特殊方法:

运算符特殊方法
+=__iadd__(self, other)
-=__isub__(self, other)
*=__imul__(self, other)
/=__itruediv__(self, other)
//=__ifloordiv__(self, other)
%=__imod__(self, other)
**=__ipow__(self, other)
>>=__irshift__(self, other)
<<=__ilshift__(self, other)
&=__iand__(self, other)
=
^=__ixor__(self, other)

我们来看一个重载 += 运算符的示例。

假设存在一个 cart 对象,我们想要将某个物品添加到购物车中。为此,我们可以为 Cart 类定义一个 add() 方法并调用该方法:

cart.add(item)

另外,我们也可以使用 Cart 类的 += 运算符,它可以为购物车添加一个物品:

cart += item

为了支持 += 运算符,我们需要实现 Cart 类的 __iadd__ 方法。

首先,定义一个 Item 类,它包含三个属性 name、quantity 以及 price。同时,它还拥有一个 amount 属性,返回物品的价格小计:

class Item:
    def __init__(self, name, qty, price):
        self.name = name
        self.qty = qty
        self.price = price

    @property
    def amount(self):
        return self.qty * self.price

    def __str__(self):
        return f'{self.name} {self.qty} ${self.price} ${self.amount}'

其次,定义 Cart 类并实现 __iadd__ 方法:

class Cart:
    def __init__(self):
        self.items = []

    def __iadd__(self, item):
        if not isinstance(item, Item):
            raise ValueError('The item must be an instance of Item')

        self.items.append(item)
        return self

    @property
    def total(self):
        return sum([item.amount for item in self.items])

    def __str__(self):
        if not self.items:
            return 'The cart is empty'

        return '\n'.join([str(item) for item in self.items])

在 __iadd__ 方法中,如果 item 不是 Item 类的实例,将会抛出 ValueError 错误;否则,将 item 添加到物品列表属性中。

total 属性返回了所有物品的总价。

如果购物车中没有任何物品,__str__ 方法将会返回字符串“The cart is empty”;否则,它会返回一个包含所有物品的字符串。

然后使用 += 运算符将物品添加到购物车中:

if __name__ == '__main__':
    cart = Cart()

    cart += Item('Apple', 5, 2)
    cart += Item('Banana', 20, 1)
    cart += Item('Orange', 10, 1.5)

    print(cart)
    # print the total line
    print('-' * 30)
    print('Total: $', cart.total)

输出结果如下:

Apple   5       $2      $10
Banana  20      $1      $20
Orange  10      $1.5    $15.0
------------------------------
Total: $ 45.0

总结

  • 运算符重载使得自定义类可以使用内置的运算符。
  Python知识库 最新文章
Python中String模块
【Python】 14-CVS文件操作
python的panda库读写文件
使用Nordic的nrf52840实现蓝牙DFU过程
【Python学习记录】numpy数组用法整理
Python学习笔记
python字符串和列表
python如何从txt文件中解析出有效的数据
Python编程从入门到实践自学/3.1-3.2
python变量
上一篇文章      下一篇文章      查看所有文章
加:2022-04-09 18:19:02  更:2022-04-09 18:21:57 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/15 18:23:57-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码