day16

# demo01
"""
    迭代器
    10:10
    练习:exercise01.py
        demo02.py
        exercise03.py
"""


class SkillIterator:
    """
        技能迭代器
    """

    def __init__(self, data):
        self.__target = data
        self.__index = -1

    def __next__(self):
        if len(self.__target) - 1 == self.__index:
            raise StopIteration()
        # 返回下一个数据
        self.__index += 1
        return self.__target[self.__index]


class SkillManager:
    """
        技能管理器
    """

    def __init__(self):
        self.__skills = []

    def add_skill(self, str_skill):
        self.__skills.append(str_skill)

    def __iter__(self):
        # 返回迭代器对象
        return SkillIterator(self.__skills)

manager = SkillManager()
manager.add_skill("九阳神功")
manager.add_skill("九阴白骨爪")
manager.add_skill("化骨绵掌")

# for item in manager:
#     print(item)

iterator = manager.__iter__()
while True:
    try:
        item = iterator.__next__()
        print(item)
    except StopIteration:
        break

# demo02
"""
    迭代器  --> yield
    练习1:
        使用 yield 重构图形管理器/员工管理器
        调试程序,体会yield执行过程.
        exercise04
    练习2:
        使用 yield 重构MyRange.
        调试程序,体会yield执行过程.
"""

class SkillManager:
    """
        技能管理器
    """

    def __init__(self):
        self.__skills = []

    def add_skill(self, str_skill):
        self.__skills.append(str_skill)

    def __iter__(self):
        # 自动生成迭代器代码
        # 大致生成过程:
        # 1. 将yield关键字以前的代码放到__next__方法中。
        # 2. 将yield关键字以后的数据作为__next__方法返回值
        # print("准备数据")
        # yield "九阳神功"
        #
        # print("准备数据")
        # yield "九阴白骨爪"
        #
        # print("准备数据")
        # yield "化骨绵掌"

        for item in self.__skills:
            yield item

manager = SkillManager()
manager.add_skill("九阳神功")
manager.add_skill("九阴白骨爪")
manager.add_skill("化骨绵掌")

# for item in manager:
#     print(item)

# 调用__iter__方法不执行
iterator = manager.__iter__()
while True:
    try:
        # 调用__next__方法,执行__iter__方法语句
        item = iterator.__next__()
        print(item)
    except StopIteration:
        break

# demo03
"""
    yield -- 生成器函数
    练习:exercise06
    练习:exercise07
    练习:exercise08
"""

"""
class 生成器类:# 可迭代对象 + 迭代器对象
    def __iter__(self):
        return self
    
    def __next__(self):
        if 没有数据了:
            抛出异常
        return 数据

"""

def my_range(stop_value):
    start_value = 0
    while start_value < stop_value:
        # (3)每次执行到yield语句时返回数据,暂时离开。
        # (4)待下次调用__next__()方法时继续从离开处继续执行。
        yield start_value
        start_value += 1

# for item in my_range(3):
#     print(item)

# (1)创建生成器对象
generater = my_range(3)
iterator = generater.__iter__()
while True:
    try:
        # (2)调用迭代器对象的__next__()方法时才执行生成器函数
        item = iterator.__next__()
        print(item)
    except StopIteration:
        break

# demo04

"""
    生成器表达式
    练习:exercise09.py
    练习:exercise10.py
"""
list01 = [2, 33, "a", 1.3, True, 2.5, False]

# 获取所有的小数
# result01 = []
# for item in list01:
#     if type(item) == float:
#         result01.append(item)
#
# print(result01)

# 列表推导式
result02 = [item for item in list01 if type(item) == float]
for item in result02:
    print(item)

# def get_floats():
#     for item in list01:
#         if type(item) == float:
#              yield item
#
# for item in get_floats():
#     print(item)

# 生成器表达式
result02 = (item for item in list01 if type(item) == float)
for item in result02:
    print(item)

# 请简述生成器与迭代器的关系.
# 答:生成器的本质就是迭代器,
# 生成器函数通过yield关键字将函数分解为多个部分,
# 每个部分就是一迭代器中的__next__方法.
# 生成器主要是延迟操作/惰性操作。
# 迭代器主要为了以一种方式获取可迭代对象中的元素.

# exercise01

"""
    练习: 迭代图形管理器
         体会(推导)自定义类如何参与for循环
"""

class GraphicIterator:
    """
         迭代器
    """

    def __init__(self, data):
        self.__target = data
        self.__index = -1

    def __next__(self):
        if len(self.__target) - 1 == self.__index:
            raise StopIteration()
        # 返回下一个数据
        self.__index += 1
        return self.__target[self.__index]

class GraphicManager:
    """
        管理器
    """

    def __init__(self):
        self.__graphic = []

    def add_skill(self, str_graphic):
        self.__graphic.append(str_graphic)

    def __iter__(self):
        # 返回迭代器对象
        return GraphicIterator(self.__graphic)

manager = GraphicManager()
manager.add_skill("圆形")
manager.add_skill("三角形")
manager.add_skill("矩形")

iterator = manager.__iter__()
while True:
    try:
        item = iterator.__next__()
        print(item)
    except StopIteration:
        break

# exercise02
"""
    练习: 迭代员工管理器
         体会(推导)自定义类如何参与for循环

    画出架构设计图
"""
# exercise03
"""
    练习3:参照下列代码,自定义MyRange类,实现相同效果.
    for item in range(10):
        print(item)

"""


class MyRnageIterator:
    def __init__(self, end_value):
        self.__begin_value = -1
        self.__end_value = end_value

    def __next__(self):
        # 0 1 2 3 8 9...   9
        if self.__begin_value == self.__end_value - 1:
            raise StopIteration
        self.__begin_value += 1
        return self.__begin_value

class MyRange:
    def __init__(self, stop_value):
        self.__stop_value = stop_value

    def __iter__(self):
        return MyRnageIterator(self.__stop_value)

# 循环一次  调用一次next  返回一个结果
# 循环一次  调用一次next  返回一个结果
iterator = MyRange(99999999999999999999999999999999)
for item in iterator:
    print(item)  # 0 1 2 ... 9



# exercise04
"""
      练习1:使用 yield 重构图形管理器/员工管理器
          调试程序,体会yield执行过程.


"""


class GraphicManager:
    """
        管理器
    """

    def __init__(self):
        self.__graphic = []

    def add_skill(self, str_graphic):
        self.__graphic.append(str_graphic)

    def __iter__(self):
        for itme in self.__graphic:
            # 返回数据
            yield itme  # 返回数据 暂时离开(再次调用__next__时回来)  [返回多个结果]
            # return item  返回数据并且退出方法 [返回一个结果]


manager = GraphicManager()
manager.add_skill("圆形")
manager.add_skill("三角形")
manager.add_skill("矩形")

for item in manager:
    print(item)

# exercise05

"""
    练习3:yield --< MyRange
"""


class MyRange:
    def __init__(self, stop_value):
        self.__stop_value = stop_value

    def __iter__(self):
        start_value = 0
        while start_value < self.__stop_value:
            yield start_value
            start_value += 1


for item in MyRange(3):
    print(item)


# exercise06

"""
    练习1:从列表[4,54,5,6,7,8,9]中获取所有偶数
         -- 传统思想:定义函数,将结果存入列表,再返回列表
         -- 生成器思想:定义生成器函数实现,使用yield返回结果.
         通过调试,体会两种思想的差异,与生成器的魅力.
"""
list01 = [4, 54, 5, 6, 7, 8, 9]


def get_even01():
    result = []
    for item in list01:
        if item % 2 == 0:
            result.append(item)
    return result


re = get_even01()
for item in re:
    print(item)


def get_even02():
    for item in list01:
        if item % 2 == 0:
            yield item

# 返回多个数据
re = get_even02()
# 循环一次 计算一次 返回一次
for item in re:
    print(item)



# exercise07
# 练习: 根据以下代码现象,自定义函数 my_enumerate.
list01 = [4, 54, 5, 6, 7, 8, 9]

# 如果希望遍历可迭代对象时,具有索引,使用enumeraten内置生成器
for item in enumerate(list01):
    print(item)  # (索引,元素)

for index, element in enumerate(list01):
    print(index, element)  # (索引,元素)


def my_enumerate(iterable_target):
    index = 0
    for item in iterable_target:
        yield (index, item)
        index += 1


for index, element in my_enumerate(list01):
    print(index, element)  # (索引,元素)

dict01 = {"a": "A", "b": "B"}
for index, key in enumerate(dict01):
    print(index, key, dict01[key])

# exercise08

# 练习:根据以下代码现象,自定义函数 my_zip.
# 17:05

list01 = ["张无忌", "张翠山", "张三丰"]
list02 = [101, 102, 103]

for itme in zip(list01, list02):
    print(itme)  # ('张无忌', 101)


def my_zip(iterable_target01, iterable_target02):
    for i in range(len(iterable_target01)):
        yield (iterable_target01[i], iterable_target02[i])


for itme in my_zip(list01, list02):
    print(itme)

list01 = ["张无忌", "张翠山", "张三丰"]
list02 = [101, 102]

for itme in zip(list01, list02, list02):
    print(itme)  # ('张无忌', 101)

# exercise09

# 练习1:在列表中获取所有整数,并计算它的平方.
# 练习2:在列表中获取所有大于10的小数.
# 要求:使用列表推导式,生成器表达式完成.
# 通过调试,体会差异.

list01 = [43.9, 54, "b", 5, 6.5, "a", 67, 7.6, 8.8, 9]
# 练习1
result01 = [item ** 2 for item in list01 if type(item) == int]
for item in result01:
    print(item)

result02 = (item ** 2 for item in list01 if type(item) == int)
for item in result02:
    print(item)

# 练习2
result01 = [item for item in list01 if type(item) == float and item > 10]
for item in result01:
    print(item)

result02 = (item for item in list01 if type(item) == int and item > 10)
for item in result02:
    print(item)

# exercise10

# 练习:
# 创建老婆类(姓名,体重,身高,年龄)
# 定义老婆列表
# -- 在老婆列表中,查找体重在30 - 50 之间的所有老婆对象
# -- 在老婆列表中,查找所有老婆的姓名与年龄.
# -- 在老婆列表中,查找姓名是"铁锤"的老婆对象
# 要求:定义函数实现
class Wife:
    def __init__(self, name="", weight=0.0, height=0.0, age=0):
        self.name = name
        self.weight = weight
        self.height = height
        self.age = age

list01 = [
    Wife("铁扇公主",50,1.6,27),
    Wife("白雪公主",40,1.7,23),
    Wife("铁锤",70,1.9,30),
    Wife("赵敏",35,1.5,27),
]

def find01():
    for item in list01:
        if 30 <= item.weight <= 50:
            yield item

def find02():
    for item in list01:
            yield (item.name,item.age)

def find03():
    for item in list01:
        if item.name == "铁锤":
            return item

for item in find01():
    print(item.name)

for item in find02():
    print(item)


tc = find03()
print(tc.name)




# exercise.txt
作业
1. 三合一
2. 当天练习独立完成(exercise10.py)
3. 准备面向对象答辩.

#review

"""
    复习
        time --> 时间戳(1970 1 1)   时间元组(年月日...)
                 看文档
        异常处理
            现象:程序不再向下执行,而是返回给调用者.
            处理目的:让错误(异常 / 向上)状态改为正常(向下)状态
            处理手段:
                try:
                    可能出错的代码:
                except 错误类型:
                    处理逻辑

                try:
                    可能出错的代码:
                finally:
                    必须完成的任务

                try:
                    可能出错的代码:
                except 错误类型:
                    出错的处理逻辑
                else:
                    没出错的逻辑
            人为抛出异常:
                raise 异常对象
                为了快速/简单的传递错误信息(避免层层return)

        迭代:在上一次结果的基础上重复.
            for item in 容器:
                print(item)

            1. 获取迭代器对象
            iterator = 容器.__iter__()
            2. 通过迭代器对象获取下一个元素
            while True:
                try:
                    item = iterator.__next__()
                    print(item)
                3. 如果停止迭代则退出循环
                except StopIteration:
                    break




"""

 

posted @ 2019-10-05 23:46  晓亮86  阅读(154)  评论(0)    收藏  举报