流暢的Python-2021:1.數據模型

第一章(下方資料)

https://github.com/fluentpython/example-code-2e/tree/master/01-data-model

Python風格的紙牌

"""
第一章:
1. 數據模型
https://docs.python.org/zh-cn/3/reference/datamodel.html
"""

# 容器數據類型
import collections

Card = collections.namedtuple('Card', ['rank', 'suit'])

class FrenchDeck:
    ranks = [str(n) for n in range(2, 11)] + list('JQKA')
    suits = 'spades diamonds clubs hearts'.split()

    def __init__(self):
        # 列表推導式-> 外層for循環 self.suits(花色)
        #               -> 內層for循環 self.ranks(牌面)
        self._cards = [Card(rank, suit) for suit in self.suits
                                        for rank in self.ranks]

    def __len__(self):
        """實現之後,對象可以len()"""
        return len(self._cards)

    def __getitem__(self, position):
        """實現之後,對象可以切片 、 下標取值、課迭代"""
        return self._cards[position]

    @property
    def cards(self):
        """將方法變成屬性"""
        return self._cards


if __name__ == '__main__':
    fd = FrenchDeck()
    print(fd.cards)
    print(len(fd))  # 類實現了 __len__ 函數
    print(fd[::-1]) # 實現了 __getitem__ 函數

自定義向量類

"""
vector2d.py: a simplistic class demonstrating some special methods

It is simplistic for didactic reasons. It lacks proper error handling,
especially in the ``__add__`` and ``__mul__`` methods.

This example is greatly expanded later in the book.

Addition::

    >>> v1 = Vector(2, 4)
    >>> v2 = Vector(2, 1)
    >>> v1 + v2
    Vector(4, 5)

Absolute value::

    >>> v = Vector(3, 4)
    >>> abs(v)
    5.0

Scalar multiplication::

    >>> v * 3
    Vector(9, 12)
    >>> abs(v * 3)
    15.0

"""


import math

class Vector:

    def __init__(self, x=0, y=0):
        self.x = x
        self.y = y

    def __repr__(self): # print時找不到__str__ 纔會進這裏, 控制檯的時候調用
        """ 把對象 已字符串內容形式返回
        轉換標誌:’!S’調用 str ()的值,’!R’調用 repr ()和’!A’調用 ascii ()。
        !r => 首先對參數調用 repr()
        !s => 首先對參數調用 str()
        !a => 首先對參數調用 ascii()
        :return:
        """
        return f'Vector({self.x!r}, {self.y!r})'

    def __str__(self):  # print的時候調用
        return "demo"

    def __abs__(self):  # 對象可用 abs()
        # math.hypot 多維計算
        return math.hypot(self.x, self.y)

    def __len__(self):
        return False

    def __bool__(self):  # 可使用 bool(), 當找不到__bool__時 會去找 __len__方法
        return bool(abs(self))

    def __add__(self, other):  # 對象 +
        x = self.x + other.x
        y = self.y + other.y
        return Vector(x, y)

    def __mul__(self, scalar):  # 對象 *
        return Vector(self.x * scalar, self.y * scalar)


if __name__ == '__main__':
    print(Vector())
    print(bool(Vector()))
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章