【100天精通python】Day24:python 迭代器,生成器,修饰器应用详解与示例

本文涉及的产品
日志服务 SLS,月写入数据量 50GB 1个月
简介: 【100天精通python】Day24:python 迭代器,生成器,修饰器应用详解与示例

专栏导读

a50b69cc81bb4be29749f2dca96b2f56.png

专栏订阅地址:https://blog.csdn.net/qq_35831906/category_12375510.html

f8d8821388dc41358195b24b9133d6b0.png


1 迭代器,生成器,修饰器概述

1.1 概述

  1. 迭代器(Iterators): 迭代器是一个对象,它实现了迭代协议,可以遍历容器中的元素。迭代器必须包含 __iter__() 和 __next__() 两个方法。__iter__() 方法返回迭代器对象自身,__next__() 方法返回容器中的下一个元素。当容器中的元素遍历完毕时,__next__() 应该引发 StopIteration 异常。
  2. 生成器(Generators): 生成器是一种特殊的迭代器,它允许我们更简洁地定义迭代器。生成器使用 yield 关键字来产生下一个值,而不是使用 return 返回结果。生成器函数在每次调用 yield 时暂停,并在下一次迭代时从上一次暂停的位置恢复执行。这样的特性使得生成器函数更加简洁和高效。
  3. 修饰器(Decorators): 装饰器是一种高阶函数,它可以用来修改其他函数的行为。装饰器的输入是一个函数,并返回一个新的函数,通常包装了原始函数,从而允许在不修改原始函数代码的情况下添加功能。装饰器可以用于在函数执行前后添加额外的逻辑,例如日志记录、权限验证、性能分析等。

       这些概念在 Python 中是非常重要的,它们提供了很多便利的方式来处理数据、优化代码和实现代码复用。迭代器和生成器使得处理大量数据时更加高效,而装饰器则使得代码更加模块化和易于维护。通过合理地运用这些概念,可以写出更加优雅和功能强大的 Python 代码。

1.2 应用场景

       迭代器、生成器和修饰器是在不同编程场景中广泛使用的 Python 编程工具。以下是它们的常见编程场景:

1.迭代器的编程场景:

  1. 遍历数据集:迭代器允许在遍历大型数据集时节省内存,因为它们按需逐个获取数据,而不是一次性加载整个数据集到内存中。
  2. 文件处理:对于大型文件,使用迭代器可以逐行读取和处理数据,而无需一次性将整个文件读入内存。
  3. 自定义容器:通过实现迭代器协议,我们可以创建自定义的容器对象,例如树、图等,从而可以使用 Python 的 for 循环来遍历容器中的元素。

2.生成器的编程场景:

  1. 大数据集的处理:生成器非常适合处理大型数据集,因为它们按需生成数据,避免了一次性加载所有数据到内存中。
  2. 无限序列:生成器可以生成无限长度的序列,例如斐波那契数列、素数序列等。
  3. 延迟计算:使用生成器可以实现延迟计算,只有在需要时才生成数据,这在某些情况下可以提高性能。

3.修饰器的编程场景:

  1. 日志记录:修饰器可以用于为函数添加日志记录功能,记录函数的调用信息、参数和执行时间。
  2. 性能分析:通过修饰器,我们可以测量函数的执行时间,从而进行性能分析和优化。
  3. 权限验证:修饰器可以用于对函数进行权限验证,确保只有具有特定权限的用户可以执行函数。
  4. 缓存结果:修饰器可以用于缓存函数的结果,避免重复计算,提高函数的执行效率。

综合应用场景:

  • 使用生成器处理大型数据集,并结合修饰器记录数据处理的日志和性能。
  • 使用迭代器遍历大型文件,并结合修饰器实现权限验证和缓存文件处理结果。
  • 使用生成器生成无限序列,例如生成斐波那契数列,并结合修饰器记录序列的计算时间和结果。

       总结:迭代器、生成器和修饰器在 Python 编程中都有着广泛的应用场景。它们使代码更加高效、灵活和易于维护,特别是在处理大型数据集和复杂任务时,它们的优势尤为明显。

2 语法与示例

2.1 迭代器

       在 Python 中,迭代器(Iterators)是一种用于遍历容器中元素的机制。它提供了一种简单而统一的方式来访问集合中的每个元素,而无需了解集合的内部结构。迭代器在处理大数据集时非常有用,因为它们不需要一次性加载整个数据集到内存中,而是按需逐个获取数据,从而节省内存和提高性能。

       Python中的许多内置数据类型都支持迭代,例如列表、元组、字典、集合等。迭代器的核心思想是通过 __iter__() 和 __next__() 方法来实现遍历。当我们调用 iter(iterable) 时,它会返回一个迭代器对象,然后我们可以通过 next(iterator) 来获取容器中的下一个元素,直到所有元素遍历完毕,此时会引发 StopIteration 异常。

下面是一个简单的迭代器示例:

class MyIterator:
    def __init__(self, data):
        self.data = data
        self.index = 0
    def __iter__(self):
        return self
    def __next__(self):
        if self.index >= len(self.data):
            raise StopIteration
        value = self.data[self.index]
        self.index += 1
        return value
# 使用自定义迭代器遍历列表
my_list = [1, 2, 3, 4, 5]
my_iterator = MyIterator(my_list)
for item in my_iterator:
    print(item)

输出:

1
2
3
4
5

在上面的示例中,我们定义了一个名为 MyIterator 的迭代器类,并在其中实现了 __iter__() 和 __next__() 方法。然后,我们使用自定义的迭代器遍历了一个列表 my_list。

值得注意的是,Python 提供了内置函数 iter() 和 next(),因此我们在实际编程中很少需要自己定义迭代器类。直接使用 iter() 和 next() 即可对可迭代对象进行迭代。

my_list = [1, 2, 3, 4, 5]
my_iterator = iter(my_list)
while True:
    try:
        item = next(my_iterator)
        print(item)
    except StopIteration:
        break

输出结果与之前相同

1
2
3
4
5

这里我们使用 iter() 和 next() 函数来手动遍历列表,当遇到 StopIteration 异常时停止遍历。

总结:迭代器是 Python 中非常强大且常用的特性,它使得遍历数据变得简单而高效。无论是自定义迭代器类还是使用内置的 iter() 和 next() 函数,迭代器在处理数据集时都是非常有用的。

2.2 生成器

       在 Python 中,生成器(Generators)是一种特殊类型的迭代器,它使用 yield 关键字来产生值,而不是使用 return 返回结果。生成器函数的执行在每次调用 yield 时暂停,而在下一次迭代时从上一次暂停的位置继续执行。这种特性使得生成器函数更加简洁、高效,并且节省内存。

       生成器的好处在于它不需要一次性将所有数据加载到内存中,而是按需生成数据。这在处理大量数据时非常有用,因为它可以减少内存占用并提高程序性能。

下面是一个简单的生成器示例:

def countdown(n):
    while n > 0:
        yield n
        n -= 1
# 使用生成器遍历倒计时
for i in countdown(5):
    print(i)

输出

5
4
3
2
1

        在上面的示例中,我们定义了一个名为 countdown 的生成器函数。它在每次循环中使用 yield 关键字产生一个倒计时的值,并在下一次迭代时从上一次暂停的位置继续执行。因此,每次迭代都会输出一个倒计时的值。

       值得注意的是,生成器函数并不返回一个值,而是生成一个迭代器。我们可以通过调用生成器函数来获得生成器对象,并使用它进行迭代。当所有值都生成完毕后,生成器会引发 StopIteration 异常。

       除了通过 yield 来定义生成器,Python 还支持使用生成器表达式来快速创建生成器。生成器表达式类似于列表推导式,但使用圆括号而不是方括号。

示例:

# 使用生成器表达式生成一个包含 1 到 5 的生成器
my_generator = (x for x in range(1, 6))
# 遍历生成器并输出值
for item in my_generator:
    print(item)

输出

1
2
3
4
5

生成器是 Python 中强大而灵活的工具。通过使用 yield 关键字定义生成器函数或生成器表达式,我们可以在处理大数据集时节省内存、提高性能,并使代码更加简洁。

2.3 修饰器

       修饰器(Decorators)是 Python 中的一种高级功能,它允许我们在不修改原始函数代码的情况下,为函数添加额外的功能或行为。修饰器本质上是一个函数,它接受另一个函数作为参数,并返回一个新的函数。通过这种方式,我们可以在调用函数之前、之后或在函数执行过程中注入一些通用的逻辑。

    修饰器的语法使用 @ 符号,将修饰器应用到目标函数之前。

让我们看一个简单的示例:

# 定义一个简单的修饰器函数
def my_decorator(func):
    def wrapper():
        print("Something is happening before the function is called.")
        func()
        print("Something is happening after the function is called.")
    return wrapper
# 使用修饰器来装饰函数
@my_decorator
def say_hello():
    print("Hello!")
# 调用被装饰的函数
say_hello()

输出:

Something is happening before the function is called.
Hello!
Something is happening after the function is called.

在上面的例子中,我们定义了一个名为 my_decorator 的修饰器函数,它接受一个函数 func 作为参数,并返回一个新的函数 wrapper。在 wrapper 函数内部,我们添加了额外的逻辑,即在目标函数 func 被调用之前和之后打印出一些信息。

然后,我们使用 @my_decorator 语法将 my_decorator 修饰器应用到函数 say_hello 上,相当于执行了以下操作:

say_hello = my_decorator(say_hello)

这样,当我们调用 say_hello() 函数时,实际上是调用了被修饰后的 wrapper 函数,从而在打印 "Hello!" 之前和之后分别执行了额外的逻辑。

除了上述示例外,修饰器还可以带有参数,使其更加灵活。例如:

def repeat(num_times):
    def my_decorator(func):
        def wrapper(*args, **kwargs):
            for _ in range(num_times):
                result = func(*args, **kwargs)
            return result
        return wrapper
    return my_decorator
@repeat(num_times=3)
def say_hello(name):
    print(f"Hello, {name}!")
say_hello("John")

输出:

Hello, John!
Hello, John!
Hello, John!

       在这个例子中,我们定义了一个带有参数的修饰器 repeat,它可以指定函数执行的次数。通过使用 @repeat(num_times=3) 语法,我们将 repeat 修饰器应用到 say_hello 函数上,并指定该函数将会被执行三次。

       总结:修饰器是 Python 中一种强大且灵活的编程工具,它使得代码更加模块化、可读性更高,并允许在不修改原始函数代码的情况下添加通用的逻辑。通过使用修饰器,我们可以轻松地实现日志记录、性能分析、权限验证等通用功能,从而使代码更加优雅和可维护。

3 综合应用案例

       假设你有一个包含大量整数的列表,现在需要对其中的每个整数进行平方运算,并在每次运算前后记录日志,包括函数的执行时间。

要求实现一个程序,包含以下功能:

  1. 定义一个生成器函数 square_generator(data),该函数接受一个整数列表 data 作为参数,并返回一个生成器。生成器会逐个生成列表中每个整数的平方值。
  2. 定义一个修饰器函数 log_decorator(func),该函数接受一个函数 func 作为参数,并返回一个新的函数 wrapper。在 wrapper 函数内部,它会记录 func 函数的执行时间,并输出执行时间日志。
  3. 将修饰器 log_decorator 应用到生成器函数 square_generator 上,创建一个新的经过修饰的生成器函数 log_square_generator。
  4. 创建一个包含大量整数的列表 data_list,调用经过修饰的生成器函数 log_square_generator(data_list),并观察运行时间的日志输出。

最终,程序能够处理大量数据并自动记录执行时间,使代码更加高效和可维护。

代码如下:

import time
# 生成器函数:平方生成器
def square_generator(data):
    for item in data:
        yield item ** 2
# 修饰器函数:日志记录
def log_decorator(func):
    def wrapper(*args, **kwargs):
        start_time = time.time()
        result = func(*args, **kwargs)
        end_time = time.time()
        print(f"Function {func.__name__} executed in {end_time - start_time:.6f} seconds.")
        return result
    return wrapper
# 经过修饰的生成器函数:带有日志记录的平方生成器
@log_decorator
def log_square_generator(data):
    for item in data:
        yield item ** 2
# 创建一个大型数据集的列表
data_list = list(range(1, 1000000001))
# 使用经过修饰的生成器处理数据,并观察日志输出
for square in log_square_generator(data_list):
    pass

输出结果如下:

2e7df0281eaf4ed5a6fee4283b253adc.png

      以上案例中,我们首先定义了 square_generator 生成器函数,它可以将列表中的每个元素平方后返回。然后,我们定义了 log_decorator 修饰器函数,用于记录函数的执行时间和参数。

       接下来,我们将修饰器应用到 square_generator 上,创建一个新的经过修饰的生成器函数 log_square_generator,它将在运算前后记录日志。

    最后,我们创建一个大型数据集的列表,并使用经过修饰的生成器函数 log_square_generator 来处理数据,并观察日志输出。在运行代码时,你会看到生成器的运行时间被记录下来。

       这个完整版的案例演示了如何利用迭代器、生成器和修饰器来处理大型数据集,并添加通用的日志记录功能,从而使代码更加高效、灵活和易于维护。


相关实践学习
日志服务之使用Nginx模式采集日志
本文介绍如何通过日志服务控制台创建Nginx模式的Logtail配置快速采集Nginx日志并进行多维度分析。
目录
相关文章
|
12天前
|
存储 数据采集 人工智能
Python编程入门:从零基础到实战应用
本文是一篇面向初学者的Python编程教程,旨在帮助读者从零开始学习Python编程语言。文章首先介绍了Python的基本概念和特点,然后通过一个简单的例子展示了如何编写Python代码。接下来,文章详细介绍了Python的数据类型、变量、运算符、控制结构、函数等基本语法知识。最后,文章通过一个实战项目——制作一个简单的计算器程序,帮助读者巩固所学知识并提高编程技能。
|
7天前
|
数据可视化 Python
以下是一些常用的图表类型及其Python代码示例,使用Matplotlib和Seaborn库。
通过这些思维导图和分析说明表,您可以更直观地理解和选择适合的数据可视化图表类型,帮助更有效地展示和分析数据。
45 8
|
14天前
|
API Python
【Azure Developer】分享一段Python代码调用Graph API创建用户的示例
分享一段Python代码调用Graph API创建用户的示例
38 11
|
17天前
|
网络安全 Python
Python网络编程小示例:生成CIDR表示的IP地址范围
本文介绍了如何使用Python生成CIDR表示的IP地址范围,通过解析CIDR字符串,将其转换为二进制形式,应用子网掩码,最终生成该CIDR块内所有可用的IP地址列表。示例代码利用了Python的`ipaddress`模块,展示了从指定CIDR表达式中提取所有IP地址的过程。
35 6
|
15天前
|
缓存 开发者 Python
深入探索Python中的装饰器:原理、应用与最佳实践####
本文作为技术性深度解析文章,旨在揭开Python装饰器背后的神秘面纱,通过剖析其工作原理、多样化的应用场景及实践中的最佳策略,为中高级Python开发者提供一份详尽的指南。不同于常规摘要的概括性介绍,本文摘要将直接以一段精炼的代码示例开篇,随后简要阐述文章的核心价值与读者预期收获,引领读者快速进入装饰器的世界。 ```python # 示例:一个简单的日志记录装饰器 def log_decorator(func): def wrapper(*args, **kwargs): print(f"Calling {func.__name__} with args: {a
29 2
|
15天前
|
机器学习/深度学习 人工智能 自然语言处理
探索未来编程:Python在人工智能领域的深度应用与前景###
本文将深入探讨Python语言在人工智能(AI)领域的广泛应用,从基础原理到前沿实践,揭示其如何成为推动AI技术创新的关键力量。通过分析Python的简洁性、灵活性以及丰富的库支持,展现其在机器学习、深度学习、自然语言处理等子领域的卓越贡献,并展望Python在未来AI发展中的核心地位与潜在变革。 ###
|
18天前
|
大数据 数据处理 开发者
Python中的迭代器和生成器:不仅仅是语法糖####
本文探讨了Python中迭代器和生成器的深层价值,它们不仅简化代码、提升性能,还促进了函数式编程风格。通过具体示例,揭示了这些工具在处理大数据、惰性求值及资源管理等方面的优势。 ####
|
13天前
|
人工智能 数据可视化 数据挖掘
探索Python编程:从基础到高级
在这篇文章中,我们将一起深入探索Python编程的世界。无论你是初学者还是有经验的程序员,都可以从中获得新的知识和技能。我们将从Python的基础语法开始,然后逐步过渡到更复杂的主题,如面向对象编程、异常处理和模块使用。最后,我们将通过一些实际的代码示例,来展示如何应用这些知识解决实际问题。让我们一起开启Python编程的旅程吧!
|
18天前
|
存储 索引 Python
Python编程数据结构的深入理解
深入理解 Python 中的数据结构是提高编程能力的重要途径。通过合理选择和使用数据结构,可以提高程序的效率和质量
131 59
|
12天前
|
小程序 开发者 Python
探索Python编程:从基础到实战
本文将引导你走进Python编程的世界,从基础语法开始,逐步深入到实战项目。我们将一起探讨如何在编程中发挥创意,解决问题,并分享一些实用的技巧和心得。无论你是编程新手还是有一定经验的开发者,这篇文章都将为你提供有价值的参考。让我们一起开启Python编程的探索之旅吧!
36 10