Python package + module: class + inherit + polymorphism brief dark horse course

base

# -*- coding:utf8 -*-
"""
# editor: hjjdreamer
# create-time: 2022/12/4-23:28
# Python-Script: chapter10-class
# describe:

"""


# lesson1
# 面向对象编程
# 设计类class        == 设计表格
# 基于类创建对象      == 打印生产表格
# 对象属性赋值        == 填写表格

# 1. 设计一个类 == 类似于生活中设计一张登记表
class Student:
    name = None  # 记录学生姓名
    gender = None  # 记录学生性别
    nationality = None  # 记录国籍
    native_place = None  # 记录籍贯
    age = None  # 记录年龄


# 2. 创建一个对象 == 类似于打印生活中的一张登记表
stu_1 = Student()  # 即是对象也是变量

# 3. 对象属性进行赋值 == 类似于填报表格
stu_1.name = "as"
stu_1.gender = "male"
stu_1.nationality = "CN"
stu_1.native_place = "ShangDong"
stu_1.age = 31

# 4. 获取对象中的记录信息
print(f"""
{stu_1.name}
{stu_1.gender}
{stu_1.nationality}
{stu_1.native_place}
{stu_1.age}
""")

# lesson2
# class define + use
# 成员使用方法
# self
"""
封装:
类 封装了属性,基于类创建一个个对象来使用
语法:
class <key-words>:   ==> 定义了类
class 属性            ==> 定义了类的变量(成员变量)
class 行为            ==> 定义了类的函数(成员方法)

创建类对象的语法
对象 = 类名称()

说函数 == 不在类里面的函数逻辑
说方法 == 在类里面的函数逻辑
"""

"""
在类中定义方法:
留意self
def <func-name>(self ,形参1, ..., 形参N)
    方法体
    
注意:
self (类的内部引用)
1. 必须写,用于成员方法定义
2. 表示类对象自身
3. 类对象调用方法,self会被python自动传入
4. 方法内部,想访问类成员变量,必须使用self    
"""


class Student1():
    """
    定义一个Student1的类
    """
    name = None  # 初始化值,为None,是一个容器,装main传入的实参

    def say_hi(self):  # 定义必须有self
        print(f"hello, I am {self.name}, loving you.")

    def say_hi2(self, msg2):
        print(f"hello, I am {self.name}, loving you and {msg2}.")


stu1 = Student1()
stu1.name = "qwer"
stu1.say_hi()  # 调用不能有self

stu2 = Student1()
stu2.name = "rewq"
stu2.say_hi()

stu3 = Student1()
stu3.name = "asdf"
stu3.say_hi2("123456789")

"""
summary:
=======================================
class 类名称:
    成员变量
    
    def 成员方法(self, 参数列表):
        成员方法体

    def 成员方法1(self):
        成员方法体1    
        
        
对象 = 类名称()
对象.成员方法(实参)
对象.成员方法1()

attention:
只用通过self, 成员方法才能访问类的成员变量
self出现在形参中,但不占用参数位置,无需理会
"""

# lesson3 类与对象
"""
对象名 = 类名称
类只是一种程序内的设计图纸,需要基于图纸生产实体(对象),才能正常工作
"""


class Clock:  # 可以没有括号,因为没有参数
    """
    定义闹钟模板
    """
    id = None
    price = None

    def ring(self):
        import winsound
        # 闹钟声音刺耳
        winsound.Beep(37, 300)


clock1 = Clock()
clock1.id = "001206"
clock1.price = 20.00
# 输出的是闹钟001206实体的信息
print(f"clock1_id == {clock1.id}, clock1_price == {clock1.price}")
clock1.ring()

clock2 = Clock()
clock2.id = "001205"
clock2.price = 20.00
# 输出的是闹钟001206实体的信息
print(f"clock1_id == {clock2.id}, clock1_price == {clock2.price}")
clock2.ring()

"""
思想: 
    事物 = 属性 + 行为
    类 == 设计图纸
    对象 == 具体实体
面向对象编程:
    使用对象进行编程
    设计类 ==> 基于类创建对象 ==> 使用对象完成具体工作            
"""

# lesson4: 构造方法
"""
构造方法向成员变量赋值
以传参的形式将成员变量的值给传进去

__init__() == 构造方法
功能:
1. 创建类对象时候,会自动执行
2. 创建类对象时候,将传入参数自动传递给__init__方法使用
"""


class Student2:
    name = None  # 假如相关属性没有在这里定义,
    age = None  # 则会在__init__方法下完成定义+赋值
    tel = None

    def __init__(self, name, age, tel):  # 类似与形参的功能
        self.name = name  # 定义类的属性name = 外部传参的属性name
        self.age = age  # 构造方法内定义成员变量,需要使用self关键字
        self.tel = tel
        print("student2 create success")


stu4 = Student2("ZXC", 32, "13465798782")
print(f"name == {stu4.name}")
print(f"age == {stu4.age}")
print(f"tel == {stu4.tel}")

"""
attention:
__init__(self)
1. 2条下划线__
2. self不能省略
"""

# lesson5 魔术方法
"""
__init__    ==      构造方法
__str__     ==      字符串方法               == 控制类转换为字符串的行为
运算符重载
__lt__      ==      小于符号比较
__le__      ==      小于等于,大于等于符号比较
__eq__      ==      ==符号比较
"""


class Student4:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    # __str__(self)
    def __str__(self):
        return f"Student4 == class, class name = {self.name} + age = {self.age}"

    # __lt__(self)
    def __lt__(self, other):  # F   # 2个对象。other表示另外一个
        return self.age < other.age  # T   # Bool + 不能带上等于号

    # __le__(self) 比较的是内存地址
    def __le__(self, other):
        return self.age <= other.age

    # __eq__(self)
    def __eq__(self, other):
        return self.age == other.age


stu6 = Student4("cvb", 62)
stu7 = Student4("cvb", 62)
stu5 = Student4("ewr", 45)
print(stu5)  # <__main__.Student4 object at 0x0000023090D04E80>
print(str(stu5))  # <__main__.Student4 object at 0x0000023090D04E80>
# Student4 == class, class name = ewr + age = 45
# Student4 == class, class name = ewr + age = 45

# __lt__
print(stu5 > stu6)
print(stu5 < stu6)
# __le__
print(stu5 <= stu6)
print(stu5 >= stu6)
print(stu6 == stu7)  # F --> T
# __eq__
print(stu5 == stu6)
print(stu6 == stu7)

# lesson6 封装 + 私有成员
"""
面向对象编程:
基于模板(类),去创建实体(对象),使用对象完成功能开发

私有成员
现实世界有不公开的属性与行为,那么作为现实事物在程序中映射的类,也应该支持

类中使用私有成员的形式来支持程序中不公开的属性与行为
1. 私有成员变量 ==> 定义:变量名以"__"开头
2. 私有成员方法 ==> 定义:变量名以"__"开头

私有成员能被类的其他成员属性+方法调用,外部不能使用
在类中提供仅供内部使用的属性和方法,而不对外公开(类对象无法使用)
"""


class Phone():
    # 私有成员变量
    __current_voltage = 0.5  # 当前手机运行电压

    # 私有成员方法
    def __keep_single_core(self):  # 定义手机以单核运行
        print("CPU以单核模式运行")

    # phone1 = Phone()
    # phone1.keep_single_core()
    # Traceback (most recent call last):
    #   File "E:/python/ithelma/chapter10-class.py", line 277, in <module>
    #     phone1.keep_single_core()
    # AttributeError: 'Phone' object has no attribute 'keep_single_core'

    # 私有成员能被类的其他属性 + 方法调用,外部不能使用
    def call_by_5g(self):
        if self.__current_voltage >= 1:
            print("5G calling is ok")
        else:
            self.__keep_single_core()
            print("ele is lower, can not use 5g, keep_single_core to safe")


phone2 = Phone()
# __current_voltage = 1
phone2.call_by_5g()

# __current_voltage = 0.2
phone2 = Phone()
phone2.call_by_5g()


# lesson7: Example
class Phone1:
    #  提供私有成员变量
    __is_5g_enable = False

    # 提供私有成员方法:__check_5g()
    def __check_5g(self):
        if self.__is_5g_enable:
            print("5g开启")
        else:
            print("5g close")

    # 提供公开成员方法:call_by_5g()
    def call_by_5g(self):
        self.__check_5g()
        print("running")


phone3 = Phone1()
phone3.call_by_5g()

polymorphism

# -*- coding:utf8 -*-
"""
# editor: hjjdreamer
# create-time: 2022/12/11-10:45
# Python-Script: chapter10-class-polymorphism.py
# describe:
多态
多种状态 == 完成某个行为时候,使用不同的对象会得到不同的状态
        == 同一个行为,使用不同对象获得不同的状态

定义函数,通过类型注释声明需要父类对象,
实际传入子类对象进行工作
从而:获得不同的工作状态
"""


class Animal:
    Animal = None

    def speak(self):
        pass  # 空实现


class Dog(Animal):
    Animal = "DOG"

    def speak(self):
        print("wang~~~~")


class Cat(Animal):
    Animal = "CAT"

    def speak(self):
        print("miao~~~~")


def make_noise(animal: Animal):
    print(animal.Animal)
    animal.speak()


dog1 = Dog()
cat1 = Cat()

make_noise(dog1)
make_noise(cat1)
"""
同样的行为(函数),传入不同的对象,得到不同的状态
父类定义声明 == 函数/方法/声明在父类对象接收
子类执行函数 == 实际传入父类的子类对象进行工作
结果 == 获得同一行为的不同状态
"""

"""
父类用来决定有哪些方法
具体的方法实现:由子类自行决定

这种写法:抽象类 == 接口 == 包含抽象方法的类叫抽象类
含有抽象方法的类称为抽象类
抽象方法:方法体是空实现的pass称之为抽象方法
"""


# 父类定义顶层设计 == 抽象类
"""
抽象类 == 顶层设计,对子类的软性约束,要求子类必须复写父类的一些方法
"""
class AC:
    def cool_wind(self):
        """cold"""
        pass

    def hot_wind(self):
        """hot"""
        pass

    def swing_l_r(self):
        """swing"""
        pass


# 子类根据抽象类定义具体对象执行类功能
"""
子类做具体实现
"""
class Midea_AC(AC):
    def cool_wind(self):
        print("midea-cool")

    def hot_wind(self):
        """hot"""
        print("midea-hot")

    def swing_l_r(self):
        "swing"
        print("midea-swing")


class GREE_AC(AC):
    def cool_wind(self):
        print("GREE-cool")

    def hot_wind(self):
        """hot"""
        print("GREE-hot")

    def swing_l_r(self):
        "swing"
        print("GREE-swing")


# 定义方法调用 == 如何调用
def make_cool(ac: AC):
    ac.cool_wind()


# 创建类对象
midea_ac1 = Midea_AC()
gree_ac1 = GREE_AC()

# 调用方法
make_cool(midea_ac1)
make_cool(gree_ac1)

you inherit

# -*- coding:utf8 -*-
"""
# editor: hjjdreamer
# create-time: 2022/12/11-9:57
# Python-Script: chapter10-class-TypeAnnotation.py.py
# describe:
演示变量的类型注解
"""
# 基础数据类型注解
import json
from typing import List, Tuple, Dict
import random

var_1: int = 10
var_2: str = "asdadaffa"
var_3: bool = False


# 类对象类型注解
class Student:
    pass


stu: Student = Student()

# 基础容器类型注解
my_list: list = [1, 2, 3]
my_tuple: tuple = (1, 2, 3)
my_dict: dict = {"da": 456}

# 容器类型详细注解
my_list: List[int] = [1, 2, 3]
my_tuple: Tuple[int, str, bool] = (1, "eeq", True)
my_dict: Dict[str, int] = {"da": 456}
# 在注释中进行类型注解
var_12 = random.randint(1, 10)  # type: int
var_22 = json.loads('{"name": "dadasdfa"}')  # type: dict[str,str]


def func1():
    return 10


var_32 = func1()  # type: int


# 函数方法的类型注解
# 1.形参的类型注解
def add(x: int, y: int):
    return x + y


print(add(1, 2.3))


# 对返回值进行类型注解
def func(data: list) -> list:
    return data


print(func(1))

# Union
from typing import Union

my_list1: List[Union[int, str]] = [1, 2, "dfas", "asdff"]


def func1(data: Union[int, str]) -> Union[int, str]:
    pass


func()

example

data

# -*- coding:utf8 -*-
"""
# editor: hjjdreamer
# create-time: 2022/12/12-8:08
# Python-Script: data_define.py
# describe:

"""

# 数据定义类
class Record:

    def __init__(self, date, order_id, money, province):
        # 在构建方法__init__内定义变量更好,如下
        self.date = date        # 订单日期
        self.order_id = order_id    # 订单ID
        self.money = money       # 订单金额
        self.province = province    # 销售省份

    def __str__(self):
        return f"{self.date}, {self.order_id}, {self.money}, {self.province}"

file

# -*- coding:utf8 -*-
"""
# editor: hjjdreamer
# create-time: 2022/12/12-8:16
# Python-Script: file_define.py
# describe:

"""
from data_define import Record
from typing import List, Tuple, Dict
import json


# 抽象类 == 确定顶层设计, 确定有哪些功能需要实现
class FileReader:

    def read_data(self) -> List[Record]:
        """
        读取文件数据,读到每一条数据转换为Record对象
        封装为list进行返回
        """
        pass


class TextFileReader(FileReader):

    def __init__(self, path):
        self.path = path  # 定义成员变量记录文件路径

    # 复写(实现抽象方法)父类方法
    def read_data(self) -> List[Record]:
        f = open(self.path, "r", encoding="UTF-8")

        record_list: List[Record] = []
        for line in f.readlines():
            # 测试输出结果
            # print(line)
            line = line.strip()  # 换行符进行处理 == 删除\n
            # 测试输出结果
            # print(line)
            data_list = line.split(",") # 定义分隔符
            # 测试输出结果
            # print(line)
            record = Record(data_list[0], data_list[1], int(data_list[2]), data_list[3])
            record_list.append(record)

        f.close()
        return record_list


class JsonFileReader(FileReader):
    def __init__(self, path):
        self.path = path  # 定义成员变量记录文件路径

    # 复写(实现抽象方法)父类方法
    def read_data(self) -> List[Record]:
        f = open(self.path, "r", encoding="UTF-8")

        record_list: List[Record] = []
        for line in f.readlines():
            data_dict = json.loads(line)
            record = Record(data_dict["date"], data_dict["order_id"], int(data_dict["money"]), data_dict["province"])
            record_list.append(record)

        f.close()
        return record_list


if __name__ == "__main__":
    text_file_reader = TextFileReader("../data/201101_sale.txt")
    json_file_reader = JsonFileReader("../data/201102_salejson.txt")
    list1 = text_file_reader.read_data()
    list2 = json_file_reader.read_data()

    for l in list1:
        print(l)

    for l in list2:
        print(l)

main

# -*- coding:utf8 -*-
"""
# editor: hjjdreamer
# create-time: 2022/12/12-12:51
# Python-Script: main.py
# describe:

"""
from typing import List

from file_define import FileReader, JsonFileReader, TextFileReader
from data_define import Record

test_file_reader = TextFileReader("../data/201101_sale.txt")
json_file_reader = JsonFileReader("../data/201102_salejson.txt")

jan_data: List[Record] = test_file_reader.read_data()
feb_data: List[Record] = json_file_reader.read_data()

# 将2个月的数据合并为一个list来存储
all_data: List[Record] = jan_data + feb_data

# 进行数据计算
data_dict = {}
for record in all_data:
    if record.date in data_dict.keys():
        # 当前日期已经有记录了,所以和老记录做数据累计即可
        data_dict[record.date] += record.money
    else:
        # 没有新纪录就进行赋值操作
        data_dict[record.date] = record.money

print(data_dict)
# {'2011-01-31': 29250, '2011-02-01': 14448}

Guess you like

Origin blog.csdn.net/m0_59267075/article/details/128296025