Python 中的集合(Set)详解:从基础操作到实际应用

文章大纲

引言:集合在 Python 中的重要性

在 Python 编程中,集合(Set)是一种极为重要的内置数据结构,它以无序性和元素唯一性为主要特点。集合中的每个元素都是独一无二的,这使得它在处理数据去重、成员检测以及数学运算(如并集、交集)时表现出色。无论是进行大规模数据分析,还是优化算法效率,集合都能提供高效的解决方案。例如,在处理用户 ID 列表时,集合可以快速去除重复项,确保数据准确性。此外,集合与字典的键有相似之处,元素必须是不可变的、可哈希的对象,这为理解 Python 的数据结构提供了更深的视角。通过本文,我们将从基础操作到实际应用,全面探索集合在 Python 中的强大功能,助你在编程中更高效地解决问题。

集合的基础定义与创建方法

在 Python 中,集合(Set)是一种无序的、元素唯一的数据结构,用于存储不重复的元素。它是实现数学集合概念的理想工具,常用于数据去重、成员检测以及集合运算。创建集合的主要方式是使用 set() 函数,可以将列表、元组或字符串等可迭代对象转换为集合。在转换过程中,重复元素会自动被移除,只保留唯一值。

例如,通过以下代码可以从列表创建集合:

# 从列表创建集合,自动去除重复元素
numbers = [1, 2, 2, 3, 3, 4]
unique_numbers = set(numbers)
print(unique_numbers)  # 输出: {1, 2, 3, 4}

集合的元素可以是多种数据类型,包括整数、浮点数、字符串以及元组等,但前提是这些元素必须是不可变的且可哈希的。这意味着列表、字典和集合本身不能作为集合的元素,因为它们是可变的,无法保证哈希值的一致性。例如:

# 合法的集合元素
mixed_set = {1, "hello", 3.14, (1, 2)}
print(mixed_set)  # 输出: {1, 3.14, 'hello', (1, 2)}

# 非法元素会抛出 TypeError
try:
    invalid_set = {[1, 2]}  # 列表不可作为元素
except TypeError as e:
    print(e)  # 输出: unhashable type: 'list'

此外,还可以使用花括号 {} 直接定义集合,但需注意空花括号默认创建字典而非集合,因此空集合只能通过 set() 创建:

# 使用花括号定义非空集合
fruits = {"apple", "banana", "orange"}
print(fruits)  # 输出: {'apple', 'banana', 'orange'}

# 空集合只能用 set() 创建
empty_set = set()
print(type(empty_set))  # 输出: 

通过以上方法,集合的创建既灵活又高效,为后续操作奠定了基础。理解集合元素的可哈希性要求是使用集合的关键,这有助于避免运行时错误并确保数据结构的正确性。

集合的基本操作:添加与删除元素

在 Python 中,集合(Set)作为一种动态数据结构,支持通过多种方法添加和删除元素,从而灵活地管理数据内容。以下将详细介绍集合的基本操作,包括添加元素和删除元素的具体方法及其注意事项。

添加元素到集合中主要使用 add() 方法,该方法允许向集合中插入一个新元素。如果尝试添加的元素已经在集合中,由于集合的唯一性,该操作不会产生任何效果,也不会抛出错误。以下是一个简单的示例:

# 创建一个集合并添加元素
fruits = {"apple", "banana"}
fruits.add("orange")
print(fruits)  # 输出: {'apple', 'banana', 'orange'}

# 添加已存在的元素,不会重复
fruits.add("apple")
print(fruits)  # 输出: {'apple', 'banana', 'orange'}

删除元素则可以通过 remove() 方法实现,该方法会从集合中移除指定的元素。然而,如果尝试删除一个不存在的元素,remove() 会抛出 KeyError 异常。为了避免这种情况,可以使用 discard() 方法,它在元素不存在时不会抛出异常,而是默默地忽略操作。以下是两者的对比示例:

# 使用 remove() 删除元素
fruits = {"apple", "banana", "orange"}
fruits.remove("banana")
print(fruits)  # 输出: {'apple', 'orange'}

# 删除不存在的元素会抛出异常
try:
    fruits.remove("grape")
except KeyError as e:
    print(e)  # 输出: 'grape'

# 使用 discard() 删除元素,不抛出异常
fruits.discard("grape")
print(fruits)  # 输出: {'apple', 'orange'}

此外,集合还支持 pop() 方法随机移除并返回一个元素,以及 clear() 方法清空集合中的所有元素。这些方法为动态管理集合提供了更多灵活性,但需要注意 pop() 的随机性可能导致结果不可预测。

通过以上操作,集合的内容可以根据需求动态调整。理解 remove()discard() 的区别尤为重要,这有助于编写更健壮的代码,避免不必要的异常处理问题。集合的这些基本操作是后续复杂应用的基础,掌握它们将为数据处理提供便利。

集合的成员检测:使用 in 关键字

在 Python 中,集合(Set)的一个重要特性是高效的成员检测功能,这主要通过 in 关键字实现。成员检测是指检查某个元素是否属于一个集合,而集合由于其底层基于哈希表实现,使得这一操作的时间复杂度接近 O(1),非常适合需要频繁查找的场景。

使用 in 关键字可以快速判断一个元素是否存在于集合中,返回布尔值 TrueFalse。这一操作不仅语法简洁,而且在处理大规模数据时效率极高。以下是一个简单的示例,展示了如何使用 in 检测集合中的元素:

# 创建一个集合
fruits = {"apple", "banana", "orange"}

# 使用 in 关键字检测元素
print("apple" in fruits)     # 输出: True
print("grape" in fruits)     # 输出: False

除了直接使用 in,还可以结合 not in 来检查元素是否不在集合中:

# 使用 not in 检查元素是否不在集合中
print("grape" not in fruits) # 输出: True

成员检测在实际编程中有着广泛的应用,例如权限验证、数据过滤以及条件判断等场景。比如,在处理用户输入时,可以用集合快速判断输入是否属于允许的值范围:

# 检查用户输入是否在允许的选项中
allowed_options = {"yes", "no", "maybe"}
user_input = "yes"
if user_input in allowed_options:
    print("Valid input!")  # 输出: Valid input!
else:
    print("Invalid input!")

集合的成员检测效率远高于列表或元组中的线性搜索,尤其是在数据量较大时,集合的优势更加明显。这是因为集合的哈希表结构能够直接定位元素,而列表需要逐一遍历。因此,当需要频繁执行查找操作时,优先选择集合作为数据结构是明智的。

通过 in 关键字,集合提供了一种简单而强大的方式来处理成员检测问题。掌握这一特性,不仅能提升代码的性能,还能让逻辑表达更加清晰,为后续复杂的编程任务奠定基础。

集合的数学运算:并集、交集与对称差

在 Python 中,集合(Set)的一个核心优势是支持数学运算,如并集、交集和对称差等操作。这些操作不仅直观地体现了数学集合的概念,还在数据处理、逻辑运算和问题求解中有着广泛的应用。Python 提供了简洁的操作符和方法来实现这些运算,下面将逐一介绍并集、交集和对称差的定义、用法及实际意义,并通过代码示例加深理解。

并集(Union)是指将两个集合中的所有元素合并到一个新集合中,重复的元素只会出现一次。Python 中可以使用 | 操作符或 union() 方法来计算并集。并集操作适用于需要整合多个数据集的场景,例如合并两个用户的兴趣标签列表。以下是一个示例:

# 定义两个集合
set1 = {1, 2, 3}
set2 = {3, 4, 5}

# 使用 | 操作符计算并集
union_set = set1 | set2
print(union_set)  # 输出: {1, 2, 3, 4, 5}

# 使用 union() 方法计算并集
union_set_method = set1.union(set2)
print(union_set_method)  # 输出: {1, 2, 3, 4, 5}

交集(Intersection)是指提取两个集合中共同的元素,形成一个新集合。Python 提供了 & 操作符和 intersection() 方法来实现这一操作。交集在筛选共有特征的数据时非常有用,例如找出两组用户都喜欢的项目:

# 使用 & 操作符计算交集
intersection_set = set1 & set2
print(intersection_set)  # 输出: {3}

# 使用 intersection() 方法计算交集
intersection_set_method = set1.intersection(set2)
print(intersection_set_method)  # 输出: {3}

差集(Difference)是指在一个集合中但不在另一个集合中的元素,可以使用 - 操作符或 difference() 方法计算。差集常用于找出独有元素,例如某个用户特有的偏好:

# 使用 - 操作符计算差集
difference_set = set1 - set2
print(difference_set)  # 输出: {1, 2}

# 使用 difference() 方法计算差集
difference_set_method = set1.difference(set2)
print(difference_set_method)  # 输出: {1, 2}

对称差(Symmetric Difference)是指两个集合中不重叠的元素,即在任一集合中出现但不在两者交集中的元素。Python 提供了 ^ 操作符和 symmetric_difference() 方法来实现。对称差适用于需要找出两个数据集的差异部分的场景:

# 使用 ^ 操作符计算对称差
symmetric_diff_set = set1 ^ set2
print(symmetric_diff_set)  # 输出: {1, 2, 4, 5}

# 使用 symmetric_difference() 方法计算对称差
symmetric_diff_method = set1.symmetric_difference(set2)
print(symmetric_diff_method)  # 输出: {1, 2, 4, 5}

这些数学运算的背后是集合的高效实现,使得操作在大规模数据下依然保持良好的性能。直观上,可以将并集想象为“合并所有”,交集为“提取共有”,差集为“排除共有”,对称差为“仅取独有”。在实际应用中,这些操作常用于数据分析、权限管理(如用户角色交集)和推荐系统(如兴趣差异分析)等场景。

此外,Python 还支持就地修改的操作符,如 |=, &=, -=^=,它们会在原集合上直接应用运算结果,节省内存并简化代码。例如:

# 就地更新并集
set1 |= set2
print(set1)  # 输出: {1, 2, 3, 4, 5}

通过上述操作,集合的数学运算功能为解决复杂问题提供了强大工具。熟练掌握这些操作,不仅能简化代码逻辑,还能显著提升数据处理的效率。无论是处理简单的元素关系,还是复杂的多集合运算,这些方法都能在实际编程中发挥重要作用。

不可变集合:frozenset 的特性和用途

在 Python 中,除了普通的集合(Set)之外,还存在一种不可变的集合类型——frozenset。与普通集合不同,frozenset 一旦创建,其内容就无法修改,即不能添加或删除元素。这种特性使得 frozenset 在特定场景下非常有用,尤其是在需要不可变数据结构作为字典键或集合元素时。以下将详细介绍 frozenset 的创建方式、特性及其实际用途,并通过示例展示其与普通集合的区别。

创建 frozenset 的方式与普通集合类似,可以通过 frozenset() 函数将列表、元组或其他可迭代对象转换为不可变集合。创建后,frozenset 的元素固定,无法通过 add()remove() 等方法进行修改。以下是一个简单的创建示例:

# 从列表创建 frozenset
frozen_numbers = frozenset([1, 2, 2, 3])
print(frozen_numbers)  # 输出: frozenset({1, 2, 3})

# 从集合创建 frozenset
regular_set = {4, 5, 6}
frozen_set = frozenset(regular_set)
print(frozen_set)  # 输出: frozenset({4, 5, 6})

由于 frozenset 是不可变的,它可以作为字典的键或普通集合的元素,而普通集合由于其可变性无法满足这一要求。这是因为 Python 要求字典键和集合元素必须是可哈希的,而可哈希对象的内容在生命周期内不能改变。以下示例展示了 frozenset 在这些场景中的应用:

# 使用 frozenset 作为字典键
data = {frozenset([1, 2]): "pair"}
print(data[frozenset([1, 2])])  # 输出: pair

# 使用 frozenset 作为集合元素
nested_set = {frozenset([1, 2]), frozenset([3, 4])}
print(nested_set)  # 输出: {frozenset({1, 2}), frozenset({3, 4})}

尝试对 frozenset 进行修改操作会抛出 AttributeError,这进一步体现了它的不可变特性:

# 尝试修改 frozenset 会抛出异常
try:
    frozen_numbers.add(4)
except AttributeError as e:
    print(e)  # 输出: 'frozenset' object has no attribute 'add'

frozenset 支持与普通集合相同的数学运算,如并集、交集和差集等,但运算结果会返回新的 frozenset 对象,不会修改原始对象。此外,成员检测(in 关键字)等只读操作也完全适用。这使得 frozenset 在需要不可变集合进行逻辑运算时非常实用。

在实际应用中,frozenset 常用于需要确保数据不被意外修改的场景,例如作为配置数据的键、表示固定分组或在多线程环境中避免数据竞争。它的不可变性保证了数据的一致性和安全性,尤其是在复杂程序中作为不可变标识符时效果显著。

与普通集合相比,frozenset 牺牲了灵活性,换来了哈希能力和线程安全性。理解两者的区别有助于在设计程序时选择合适的数据结构。如果需要动态更新数据,普通集合是更好的选择;如果需要不可变性和可哈希性,frozenset 则是理想工具。通过合理使用 frozenset,可以有效提升代码的健壮性和可维护性,为复杂应用提供可靠的数据结构支持。

集合的性能优势与局限性

在 Python 中,集合(Set)作为一种高效的数据结构,在特定场景下展现出显著的性能优势,但同时也存在一些局限性,开发者在选择使用集合时需要权衡其特性和适用场景。以下将详细分析集合在性能上的优点、局限性以及在实际应用中的注意事项,帮助读者更好地理解何时以及为何使用集合。

集合的一个主要性能优势在于成员检测的高效性。由于集合底层基于哈希表实现,查找某个元素是否存在(使用 in 关键字)的平均时间复杂度为 O(1)。相比之下,列表或元组的线性搜索时间复杂度为 O(n),在大规模数据中效率低下。以下是一个对比示例,展示了集合在查找操作中的优势:

# 集合与列表的查找性能对比
large_list = list(range(1000000))
large_set = set(large_list)

# 列表查找
start_time = time.time()
print(999999 in large_list)  # 输出: True
print(f"List search time: {time.time() - start_time}")

# 集合查找
start_time = time.time()
print(999999 in large_set)   # 输出: True
print(f"Set search time: {time.time() - start_time}")

运行上述代码会发现,集合的查找速度远快于列表,尤其在数据量增大时,这种差距更加明显。因此,当频繁需要检查元素是否存在时,例如权限验证或数据过滤,集合是首选数据结构。

另一个性能优势是集合在去重操作中的高效性。将列表转换为集合可以快速移除重复元素,时间复杂度接近 O(n),而使用列表手动去重则可能需要 O(n²) 的复杂度。集合的这一特性在数据清洗和预处理中非常实用,例如处理日志文件中的唯一 IP 地址:

# 使用集合快速去重
ip_addresses = ["192.168.1.1", "192.168.1.2", "192.168.1.1"]
unique_ips = set(ip_addresses)
print(unique_ips)  # 输出: {'192.168.1.1', '192.168.1.2'}

然而,集合也存在一些局限性,其中最明显的是其无序性。集合中的元素没有固定顺序,无法通过索引访问,也无法保证插入顺序(尽管 Python 3.7+ 在某些实现中保留了插入顺序,但这不是标准行为)。这使得集合不适合需要维持元素顺序的场景,例如记录时间序列数据,此时列表或元组更为合适。

此外,集合的元素必须是可哈希的,这限制了其存储的数据类型。列表、字典和其他集合无法作为元素存储,这在需要嵌套复杂数据结构时可能成为障碍。虽然可以使用 frozenset 解决部分问题,但这增加了代码复杂性。

在内存使用方面,集合由于哈希表的实现,可能比列表占用更多内存,尤其是在元素较少时。这种内存开销在处理小型数据集时可能不划算,开发者需要根据实际需求权衡性能与资源消耗。

综上所述,集合在成员检测和去重操作中具有显著的性能优势,适用于需要高效查找和唯一性保证的场景,如权限管理、数据去重和集合运算。然而,其无序性和对元素类型的要求限制了其适用范围。在选择数据结构时,应充分考虑具体需求:如果需要顺序或支持复杂嵌套,列表或字典可能更合适;如果追求查找效率和唯一性,集合则是理想选择。通过理解集合的性能特性和局限性,开发者可以更精准地设计高效且健壮的程序。

实战案例:处理温度数据中的集合应用

在数据处理和分析中,集合(Set)因其去重能力和高效性,常被用于处理重复数据或需要唯一值的场景。本节以处理希思罗机场的温度数据为例,展示如何利用 Python 集合去除重复温度值,并结合其他方法计算关键统计指标,如最高、最低、平均和中位数温度。通过具体的代码实现和结果分析,体现集合在实际数据处理中的实用性。

假设我们有一组从希思罗机场记录的每日温度数据(单位:摄氏度),其中可能包含重复值。我们的目标是去除重复温度值,并计算一些基本的统计信息。首先,我们使用集合来快速提取唯一的温度值,然后基于这些数据进行进一步分析。以下是完整的代码实现:

# 假设的希思罗机场温度数据(包含重复值)
temperature_data = [15.5, 16.2, 14.8, 15.5, 17.1, 16.2, 18.0, 14.8, 19.3]

# 使用集合去除重复温度值
unique_temperatures = set(temperature_data)
print("唯一温度值:", unique_temperatures)

# 将集合转换回列表以便计算统计数据
unique_temp_list = list(unique_temperatures)

# 计算最高、最低和平均温度
max_temp = max(unique_temp_list)
min_temp = min(unique_temp_list)
avg_temp = sum(unique_temp_list) / len(unique_temp_list)

# 计算中位数温度(需对列表排序)
sorted_temps = sorted(unique_temp_list)
n = len(sorted_temps)
if n % 2 == 0:
    median_temp = (sorted_temps[n//2 - 1] + sorted_temps[n//2]) / 2
else:
    median_temp = sorted_temps[n//2]

# 输出统计结果
print(f"最高温度: {max_temp}°C")
print(f"最低温度: {min_temp}°C")
print(f"平均温度: {avg_temp:.2f}°C")
print(f"中位数温度: {median_temp}°C")

运行上述代码后,输出结果如下:

唯一温度值: {14.8, 15.5, 16.2, 17.1, 18.0, 19.3}
最高温度: 19.3°C
最低温度: 14.8°C
平均温度: 16.82°C
中位数温度: 16.65°C

在上述代码中,集合的核心作用是快速去除重复温度值。通过将原始数据转换为集合,重复的温度值(如 15.5、16.2 和 14.8)被自动移除,仅保留唯一值。这一操作的时间复杂度接近 O(n),非常高效。随后,我们将集合转换回列表,以便使用 max()min()sum() 等函数计算统计数据。由于中位数计算需要有序数据,我们还使用了 sorted() 函数对列表进行排序,并根据列表长度是奇数还是偶数来确定中位数。

这一案例展示了集合在数据预处理中的典型应用:去重。去重后的数据更具代表性,避免了重复值对统计结果的干扰。例如,如果不使用集合直接计算平均值,重复的温度值会多次参与计算,导致结果偏向于高频值,而非真实分布。集合的使用确保了每个温度值只被计算一次,从而提高了统计分析的准确性。

此外,集合的高效成员检测功能也可以扩展到此案例中。例如,如果需要检查某一天的温度是否为异常值(即不在常见温度范围内),可以使用集合快速判断:

# 检查特定温度是否为常见值
common_temps = set(temperature_data)
test_temp = 25.0
if test_temp in common_temps:
    print(f"{test_temp}°C 是常见温度")
else:
    print(f"{test_temp}°C 是异常温度")

输出结果为:

25.0°C 是异常温度

通过这一实战案例,可以清晰看到集合在数据处理中的实用性,尤其是在需要去重和高效查找的场景中。希思罗机场温度数据的处理只是集合应用的一个缩影,在更复杂的数据分析任务中,如处理大规模日志文件、用户行为数据或传感器读数时,集合同样能发挥重要作用。掌握集合的这些特性,可以帮助开发者编写更高效、更简洁的代码,同时确保数据处理的准确性和可靠性。

手写代码与 AI 生成代码的对比分析

在编程实践中,手写代码和使用 AI 生成代码(如通过 GitHub Copilot 或其他工具)各有优劣。本节以处理温度数据的案例为基础,对比手写代码与 AI 生成代码在风格、效率和可读性上的差异,分析两者的适用场景,并探讨 AI 代码生成工具的优势与潜在问题,强调程序员理解问题和代码逻辑的重要性。

首先,从代码风格上看,手写代码通常更贴近开发者的个人习惯和项目需求。以处理温度数据为例,手写代码可能会优先考虑逻辑的清晰性,逐步完成去重、排序和统计计算,代码结构分明,便于维护。以下是手写代码的片段(简化版):

# 手写代码:温度数据处理
temperature_data = [15.5, 16.2, 14.8, 15.5]
unique_temps = set(temperature_data)
temp_list = sorted(list(unique_temps))
avg_temp = sum(temp_list) / len(temp_list)
print(f"平均温度: {avg_temp:.2f}°C")

相比之下,AI 生成代码往往追求简洁和通用性,可能将多步操作压缩为更紧凑的代码,但有时会缺乏注释或中间步骤说明。例如,AI 可能生成如下代码:

# AI 生成代码:温度数据处理
temperature_data = [15.5, 16.2, 14.8, 15.5]
print(f"平均温度: {sum(set(temperature_data)) / len(set(temperature_data)):.2f}°C")

从效率角度看,AI 生成代码通常能快速提供解决方案,尤其在处理简单任务时,可以节省开发者编写和调试的时间。上例中,AI 代码直接在 print 语句中完成去重和计算,减少了中间变量的使用,执行效率略高。然而,这种紧凑风格可能在复杂任务中导致逻辑不够透明,增加后期维护成本。手写代码虽然开发时间较长,但开发者对每一步操作的控制更强,代码的意图更明确,适合需要长期维护的项目。

在可读性方面,手写代码通常通过合理的变量命名和注释,提供更好的自文档化特性,便于团队协作和代码审查。而 AI 生成代码可能缺乏上下文理解,变量名较为泛泛(如使用 dataresult),且很少主动添加注释,除非明确提示。这使得 AI 代码在初次阅读时可能需要额外时间理解逻辑,尤其是在没有开发者干预的情况下。

AI 代码生成工具的优势在于其快速原型化和学习价值。对于新手程序员,AI 可以提供参考代码,帮助理解问题解决思路;对于经验丰富的开发者,AI 能处理重复性任务,释放时间用于更复杂的设计。然而,AI 工具也存在潜在问题:生成的代码可能包含隐藏错误或不适用于特定环境。例如,AI 可能未考虑温度数据中可能出现的空值或异常值,导致代码健壮性不足。此外,过度依赖 AI 可能削弱开发者独立解决问题的能力,特别是在需要定制化逻辑时。

通过对比可以发现,手写代码和 AI 生成代码各有适用场景。手写代码更适合需要深度定制和长期维护的项目,而 AI 生成代码则在快速验证想法或处理标准任务时表现优异。无论采用哪种方式,程序员对问题本质和代码逻辑的理解始终是核心。AI 工具只是辅助手段,不能替代对编程基础的掌握和批判性思维。例如,在温度数据处理中,开发者需要明确去重是否符合分析目标,以及是否需要处理异常数据,这些决策是 AI 无法完全代替的。

综上所述,手写代码与 AI 生成代码的结合可能是最佳实践:利用 AI 快速生成草稿,再通过手写方式优化和定制,确保代码既高效又符合需求。这一过程不仅提升了开发效率,也帮助程序员在与 AI 工具的交互中不断提升技能,最终实现技术和思维的双重进步。

总结与进阶学习资源

在本文中,我们全面探讨了 Python 中集合(Set)这一重要数据结构,从基础定义与创建方法,到基本操作、数学运算、不可变集合 frozenset 的特性,再到性能分析和实际应用案例,系统地展示了集合的核心功能和使用场景。集合以其无序性和元素唯一性为特点,在数据去重、成员检测和集合运算(如并集、交集)中展现了高效性和灵活性。通过实战案例和代码对比分析,我们进一步理解了集合在数据处理中的实用价值,以及如何结合手写代码和 AI 工具优化开发流程。希望这些内容能帮助读者深入掌握集合的用法,并在实际编程中灵活运用。

对于想要进一步学习和探索集合的开发者,Python 官方文档是一个不可或缺的资源,提供了关于 setfrozenset 的详细说明和技术细节,可通过 Python 官方文档 访问。此外,推荐阅读《Python Cookbook》(David Beazley 著),该书包含了大量关于集合和其他数据结构的实用技巧和案例。如果对数据结构和算法感兴趣,可以参考《Introduction to Algorithms》(Thomas H. Cormen 著),以更深入理解集合背后的哈希表实现。这些资源将为进阶学习提供坚实基础,鼓励读者探索集合在复杂项目中的高级应用,如大数据处理和算法优化。结合实践和理论,持续提升编程能力,才能真正将集合的潜力发挥到极致。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

面朝大海,春不暖,花不开

您的鼓励是我最大的创造动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值