Python学习杂记

学习过程中的一些零散问题记录

[toc]

0. 一些规范

命名惯例

  1. 以单一下划线开头的变量名(_X)不会被from module import*等语句导入
  2. 前后有两个下划线的变量名(X)是系统定义的变量名,对解释器有特殊意义
  3. 以两个下划线开头但不以下划线结尾的变量名(__X)是类的本地(私有)变量

一些函数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
"""数学运算类"""
abs(x) # 求绝对值,参数可以是整型,也可以是复数,若参数是复数,则返回复数的模
complex([real[, imag]]) # 创建一个复数
divmod(a, b) # 分别取商和余数,注意:整型、浮点型都可以
float([x]) # 将一个字符串或数转换为浮点数。如果无参数将返回0.0
int([x[, base]]) # 将一个字符串或浮点数转换为int类型,base表示进制
long([x[, base]]) # 将一个字符串或浮点数转换为long类型
pow(x, y) # 返回x的y次幂
range([start], stop[, step]) # 产生一个序列,默认从0开始
round(x[, n]) # 四舍五入
sum(iterable[, start]) # 对集合求和
oct(x) # 将一个数字转化为8进制字符串
hex(x) # 将一个数字转换为16进制字符串
chr(i) # 返回给定int类型对应的ASCII字符
unichr(i) # 返回给定int类型的unicode
ord(c) # 返回ASCII字符对应的整数
bin(x) # 将整数x转换为二进制字符串
bool([x]) # 将x转换为Boolean类型

"""集合类操作"""
basestring() # str和unicode的超类,不能直接调用,可以用作isinstance判断
format(value [, format_spec]) # 格式化输出字符串,格式化的参数顺序从0开始,如“I am {0},I like {1}”
enumerate(sequence[, start=0]) # 返回一个可枚举的对象,注意它有第二个参数
iter(obj[, sentinel]) # 生成一个对象的迭代器,第二个参数表示分隔符
max(iterable[, args...][key]) # 返回集合中的最大值
min(iterable[, args...][key]) # 返回集合中的最小值
dict([arg]) # 创建数据字典
list([iterable]) # 将一个集合类转换为另外一个集合类
set() # set对象实例化
frozenset([iterable]) # 产生一个不可变的set
tuple([iterable]) # 生成一个tuple类型
str([object]) # 转换为string类型
sorted(iterable[, cmp[, key[, reverse]]]) # 集合排序
L = [('b',2),('a',1),('c',3),('d',4)]
sorted(L, key=lambda x: x[1], reverse=True) # 使用Key参数和reverse参数
sorted(L, key=lambda x: (x[0], x[1])) # 使用key参数进行多条件排序,即如果x[0]相同,则比较x[1]

"""逻辑判断"""
all(iterable) # 集合中的元素都为真的时候为真,特别的,若为空串返回为True
any(iterable) # 集合中的元素有一个为真的时候为真,特别的,若为空串返回为False
cmp(x, y) # 如果x < y ,返回负数;x == y, 返回0;x > y,返回正数

"""IO操作"""
file(filename [, mode [, bufsize]]) # file类型的构造函数。
input([prompt]) # 获取用户输入,推荐使用raw_input,因为该函数将不会捕获用户的错误输入,意思是自行判断类型
# 在 Built-in Functions 里有一句话是这样写的:Consider using the raw_input() function for general input from users.
raw_input([prompt]) # 设置输入,输入都是作为字符串处理,python3.x后已不再使用
open(name[, mode[, buffering]]) # 打开文件,与file有什么不同?推荐使用open

"""其他"""
callable(object) # 检查对象object是否可调用
classmethod(func) # 用来说明这个func是个类方法
staticmethod(func) # 用来说明这个func为静态方法
dir([object]) # 不带参数时,返回当前范围内的变量、方法和定义的类型列表;带参数时,返回参数的属性、方法列表。
help(obj) # 返回obj的帮助信息
eval(expression) # 计算表达式expression的值,并返回
exec(str) # 将str作为Python语句执行
execfile(filename) # 用法类似exec(),不同的是execfile的参数filename为文件名,而exec的参数为字符串。
filter(function, iterable) # 构造一个序列,等价于[item for item in iterable if function(item)],function返回值为True或False的函数
list(filter(bool, range(-3, 4)))# 返回[-3, -2, -1, 1, 2, 3], 没有0
hasattr(object, name) # 判断对象object是否包含名为name的特性
getattr(object, name [, defalut]) # 获取一个类的属性
setattr(object, name, value) # 设置属性值
delattr(object, name) # 删除object对象名为name的属性
globals() # 返回一个描述当前全局符号表的字典
hash(object) # 如果对象object为哈希表类型,返回对象object的哈希值
id(object) # 返回对象的唯一标识,一串数字
isinstance(object, classinfo) # 判断object是否是class的实例
isinstance(1, int) # 判断是不是int类型
isinstance(1, (int, float)) # isinstance的第二个参数接受一个元组类型
issubclass(class, classinfo) # 判断class是否为classinfo的子类
locals() # 返回当前的变量列表
map(function, iterable, ...) # 遍历每个元素,执行function操作
list(map(abs, range(-3, 4))) # 返回[3, 2, 1, 0, 1, 2, 3]
next(iterator[, default]) # 类似于iterator.next()
property([fget[, fset[, fdel[, doc]]]]) # 属性访问的包装类,设置后可以通过c.x=value等来访问setter和getter
reduce(function, iterable[, initializer]) # 合并操作,从第一个开始是前两个参数,然后是前两个的结果与第三个合并进行处理,以此类推
def add(x,y):return x + y
reduce(add, range(1, 11)) # 返回55 (注:1+2+3+4+5+6+7+8+9+10 = 55)
reduce(add, range(1, 11), 20) # 返回75
reload(module) # 重新加载模块
repr(object) # 将一个对象变幻为可打印的格式
slice(start, stop[, step]) # 产生分片对象
type(object) # 返回该object的类型
vars([object]) # 返回对象的变量名、变量值的字典
a = Class(); # Class为一个空类
a.name = 'qi', a.age = 9
vars(a) # {'name':'qi', 'age':9}
zip([iterable, ...]) # 返回对应数组
list(zip([1, 2, 3], [4, 5, 6])) # [(1, 4), (2, 5), (3, 6)]
a = [1, 2, 3], b = ["a", "b", "c"]
z = zip(a, b) # 压缩:[(1, "a"), (2, "b"), (3, "c")]
zip(*z) # 解压缩:[(1, 2, 3), ("a", "b", "c")]
unicode(string, encoding, errors) # 将字符串string转化为unicode形式,string为encoded string。

1.print()函数打印输出时不输出默认的换行符

在Python中,可以通过在print()函数中设置end参数来控制打印结束时的字符,默认为换行符 \n。如果你想要在打印结束时不换行,可以将end参数设置为空字符串 '',如下所示:

1
2
print('Hello, world!', end='')
print('This is a test.')

输出结果为:

1
Hello, world!This is a test.

注意,通过将end参数设置为空字符串,你需要手动控制换行的位置,以确保打印输出的格式符合你的预期。

2.如何将两个列表组合成一个元组列表

可以使用zip()函数将两个列表组合成一个元组列表。zip()函数将按索引位置将两个列表中的元素逐个配对,返回一个包含元组的迭代器。然后,你可以将迭代器转换为列表。以下是示例代码:

1
2
3
4
5
6
list1 = [1, 2, 3]
list2 = ['a', 'b', 'c']

combined_list = list(zip(list1, list2))

print(combined_list)

输出结果为:

1
[(1, 'a'), (2, 'b'), (3, 'c')]

在示例中,zip(list1, list2)将列表list1list2中的元素逐个配对,得到一个元组的迭代器。然后,通过list()函数将迭代器转换为列表,得到了一个包含元组的列表combined_list

3.双for循环遍历如何转为列表解析

双重循环可以通过嵌套的列表解析来转换。下面是一个示例:

1
result = [expression for outer_item in outer_list for inner_item in inner_list]

其中,expression 是要在循环中计算或执行的表达式,outer_listinner_list 是两个要遍历的列表。

举个例子,假设有两个列表 list1list2,你想要通过双重循环生成它们的所有组合,可以使用列表解析来实现:

1
2
3
list1 = [1, 2, 3]
list2 = [4, 5, 6]
combinations = [(x, y) for x in list1 for y in list2]

这将生成一个包含所有组合的列表 combinations,其中每个元素都是一个二元组 (x, y),其中 x 是来自 list1 的元素,y 是来自 list2 的元素。

注意,内层循环在外层循环之后。你可以根据实际需要调整循环的顺序。

4.多重赋值与顺序赋值的不同

多重赋值(Multiple Assignment),或者叫作元组赋值(Tuple Assignment)。它允许同时为多个变量赋值,使用逗号分隔多个变量名,并且可以将一个元组、列表或其他可迭代对象的值一次性赋给这些变量。

在给多个变量赋值时,右侧的表达式会先计算出所有中间结果,并按照从左到右的顺序一次性地赋值给相应的变量。这样可以简洁地交换变量的值,同时也可以将多个变量与多个表达式的结果关联起来。

下面这两段代码表示的意思是完全不同:

1
2
3
4
m1 = me + m3
m2 = m1
m3 = m2
me = me + m3
1
m1, m2 ,m3 ,me = me+m3, m1, m2,me+m3

这两段代码的区别在于变量的赋值顺序不同。

第一段代码中,赋值操作是从上到下按顺序执行的。每个变量的新值都是基于之前变量的旧值计算得到的。具体地:

  • m1 的新值是 me + m3,即 mem3 的和。
  • m2 的新值是 m1,即将 m1 的值赋给 m2
  • m3 的新值是 m2,即将 m2 的值赋给 m3
  • me 的新值是 me + m3,即 mem3 的和。

第二段代码中,赋值操作是一次性地同时进行的,使用了多重赋值语句。右侧的表达式会先计算出所有中间结果,然后依次赋值给左侧的变量。具体地:

  • me + m3 的值赋给 m1
  • m1 的旧值赋给 m2
  • m2 的旧值赋给 m3
  • me + m3 的值赋给 me

总结起来,第一段代码是逐个赋值的过程,每个变量的新值都是基于之前变量的旧值计算得到的。而第二段代码则是一次性地同时进行多个赋值操作,右侧的表达式会计算出所有中间结果,然后依次赋值给左侧的变量。两段代码的最终结果可能是不同的,取决于初始变量的值和具体的赋值逻辑。

5.json.load()与json.loads()的区别

json.load()json.loads() 都是 Python 中用于解析 JSON 数据的函数,但它们有一些区别:

  • json.load() 用于从文件中读取 JSON 数据。它接受一个文件对象作为参数,读取文件内容并将其解析为 JSON 对象或列表。示例:json.load(file_object)
  • json.loads() 用于将字符串解析为 JSON 数据。它接受一个 JSON 字符串作为参数,将其解析为 JSON 对象或列表。示例:json.loads(json_string)

总结来说,json.load() 适用于读取文件中的 JSON 数据,而 json.loads() 适用于将字符串中的 JSON 数据解析为 Python 对象。

6.让python支持中文目录路径

要在Python代码中支持中文文件目录,可以使用以下两种方法:

  1. 使用原始字符串(raw string)表示文件路径:在字符串前添加字母 “r”,以告诉Python将其作为原始字符串处理。这将确保Python不会对字符串中的特殊字符进行转义。例如:
1
data_dir = r'E:\Learning\python\LSTM_MODEL\data'
  1. 使用Unicode字符串:在字符串前添加 “u”,以告诉Python将其作为Unicode字符串处理。Unicode字符串可以包含非ASCII字符,包括中文字符。例如:
1
data_dir = u'E:\Learning\python\LSTM_MODEL\data'

使用其中一种方法将文件路径作为字符串表示,即可在Python代码中支持中文文件目录。请注意,如果使用的是非ASCII字符集(如UTF-8),确保代码文件本身以相应的编码保存。

7.统计字符串中各类字符的数量

一、正则表达式:

使用正则表达式可以表示字母、数字、符号和中文。下面是一些常用的正则表达式模式:

  • 字母:使用 [a-zA-Z] 表示所有的字母。
  • 数字:使用 \d 表示所有的数字。
  • 符号:使用 [!@#$%^&*()] 等字符集合来表示不同的符号。例如,[!@#$%^&*()] 表示常见的特殊符号。
  • 符号:使用 [^\w\s\u4e00-\u9fa5] 用于匹配除了字母、数字、空格和中文以外的其他字符
  • 中文:使用 [\u4e00-\u9fa5] 表示所有的中文字符。

下面是一个示例,演示如何使用正则表达式匹配不同类型的字符并统计它们的数量:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
import re

text = "Hello 123 你好!@#"

# 匹配字母
letters = re.findall(r'[a-zA-Z]', text)
letter_count = len(letters)

# 匹配数字
numbers = re.findall(r'\d', text)
number_count = len(numbers)

# 匹配符号
symbols = re.findall(r'[!@#$%^&*()]', text)
symbol_count = len(symbols)

# 匹配中文
chinese_chars = re.findall(r'[\u4e00-\u9fa5]', text)
chinese_count = len(chinese_chars)

print("字母数量:", letter_count)
print("数字数量:", number_count)
print("符号数量:", symbol_count)
print("中文数量:", chinese_count)

二、使得字符串的内置方法实现:

使用字符串的内置方法来判断字符是否为字母、数字或空格,然后进行计数。这里是一个使用 isdigit()isalpha()isspace() 方法的示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
def count_characters(text):
letter_count = sum(1 for char in text if char.isalpha())
number_count = sum(1 for char in text if char.isdigit())
space_count = sum(1 for char in text if char.isspace())
chinese_count = sum(1 for char in text if '\u4e00' <= char <= '\u9fa5')
other_count = len(text) - letter_count - number_count - space_count - chinese_count
return letter_count, number_count, space_count, chinese_count, other_count

text = "Hello 123 你好!@# 这是一个示例文本。"
letter_count, number_count, space_count, chinese_count, other_count = count_characters(text)

print("字母数量:", letter_count)
print("数字数量:", number_count)
print("空格数量:", space_count)
print("中文数量:", chinese_count)
print("其他符号数量:", other_count)

8.集合set的用法

集合(Set)是Python中的一种无序、可变的数据类型,它用于存储一组不重复的元素。集合中的元素是唯一的,不会重复出现。下面是一些常用的集合操作和方法:

  1. 创建集合:可以使用花括号 {}set() 函数来创建集合。

    1
    2
    my_set = {1, 2, 3}  # 使用花括号创建集合
    my_set = set([1, 2, 3]) # 使用set()函数创建集合
  2. 添加元素:使用 add() 方法向集合中添加单个元素,使用 update() 方法向集合中添加多个元素。

    1
    2
    3
    my_set = {1, 2, 3}
    my_set.add(4) # 添加单个元素
    my_set.update([5, 6, 7]) # 添加多个元素
  3. 移除元素:使用 remove() 方法从集合中移除指定元素,如果元素不存在会抛出 KeyError 异常。使用 discard() 方法也可以移除元素,但如果元素不存在不会抛出异常。

    1
    2
    3
    my_set = {1, 2, 3}
    my_set.remove(2) # 移除元素2
    my_set.discard(4) # 移除元素4,如果不存在不会抛出异常
  4. 集合操作:可以使用运算符和方法进行集合的交集、并集、差集和对称差集等操作。

    1
    2
    3
    4
    5
    6
    7
    set1 = {1, 2, 3}
    set2 = {2, 3, 4}

    intersection = set1 & set2 # 交集
    union = set1 | set2 # 并集
    difference = set1 - set2 # 差集
    symmetric_difference = set1 ^ set2 # 对称差集
  5. 遍历集合:可以使用循环语句遍历集合中的元素。

    1
    2
    3
    my_set = {1, 2, 3}
    for element in my_set:
    print(element)
  6. 其他常用方法:集合还提供了其他一些常用的方法,如 len() 获取集合的元素个数,clear() 清空集合中的元素等。

集合在处理需要唯一元素且顺序不重要的场景中非常有用,例如去除列表中的重复元素、检查两个集合是否有交集等。注意,集合中的元素必须是可哈希的(不可变类型),因此集合本身不能作为集合的元素,但可以包含元组等可哈希的数据类型。

9.数字集合可以直接进行计算

数字集合可以直接使用计算函数进行常见的数学运算。Python 提供了许多内置的数学函数和操作符,可以直接应用于数字集合。

以下是一些常见的数学函数和操作符的示例:

  • 求和:使用内置函数 sum() 可以对数字集合进行求和。

    1
    2
    3
    my_set = {1, 2, 3, 4, 5}
    total = sum(my_set)
    print(total) # 输出结果: 15
  • 最大值和最小值:使用内置函数 max()min() 可以找到数字集合中的最大值和最小值。

    1
    2
    3
    4
    5
    my_set = {10, 5, 20, 8, 15}
    max_value = max(my_set)
    min_value = min(my_set)
    print(max_value) # 输出结果: 20
    print(min_value) # 输出结果: 5
  • 平均值:使用 sum()len() 函数可以计算数字集合的平均值。

    1
    2
    3
    my_set = {1, 2, 3, 4, 5}
    average = sum(my_set) / len(my_set)
    print(average) # 输出结果: 3.0

除了上述示例中的基本数学函数,还可以使用其他数学函数,如幂函数 pow()、绝对值函数 abs()、四舍五入函数 round() 等,根据具体的需求进行选择和使用。

10.递归函数的调用

递归调用是指在函数内部调用自身的过程。通过递归调用,可以解决一些需要重复执行相同操作的问题。

下面是一个简单的示例,演示了如何使用递归调用来计算阶乘:

1
2
3
4
5
6
7
8
9
def factorial(n):
if n == 0: # 基线条件,当 n 等于 0 时,直接返回 1
return 1
else: # 递归条件,当 n 大于 0 时,调用自身并乘以 n
return n * factorial(n-1)

# 调用函数计算阶乘
result = factorial(5)
print(result) # 输出结果: 120

在这个示例中,函数 factorial() 通过递归调用自身来计算阶乘。当输入参数 n 等于 0 时,函数返回 1,作为递归的基线条件。当输入参数 n 大于 0 时,函数调用自身并将 n 乘以递归结果,实现了递归条件。

需要注意的是,使用递归调用时要确保存在合适的终止条件(基线条件),以避免无限递归导致程序崩溃。在编写递归函数时,确保每次递归调用都使问题规模减小,最终达到基线条件,从而实现问题的解决。

11.pygal世界地图上的国家名称显示为中文

在 Pygal 中,要将地图上的国家名称显示为中文,可以使用 pygal.style.Style 对象来设置样式,并通过设置 label_font_sizemajor_label_font_size 参数来指定标签和主要标签的字体大小。此外,还可以使用 pygal_config 参数来设置全局配置选项。

以下是一个示例代码,展示如何将地图上的国家名称显示为中文:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
import pygal.maps.world as pygal_maps

# 创建地图对象
world_map = pygal_maps.World(style=pygal_maps.style.Style(label_font_size=14, major_label_font_size=16))

# 设置地图标题
world_map.title = '世界地图'

# 设置国别代码和对应的中文名称
country_names = {
'cn': '中国',
'us': '美国',
'jp': '日本',
# 添加其他国家...
}

# 设置地图数据
world_map.add('国家', country_names)

# 渲染地图并保存为SVG文件
world_map.render_to_file('world_map.svg')

在上述示例中,我们创建了一个地图对象 world_map,并使用 pygal_maps.style.Style 对象来设置样式,其中 label_font_size 设置为 14,major_label_font_size 设置为 16,以调整标签的字体大小。然后,使用 add() 方法将国别代码和对应的中文名称添加到地图中。最后,使用 render_to_file() 方法将地图渲染为 SVG 文件。

通过以上方式,你可以将地图上的国家名称显示为中文。请注意,确保你的环境中已安装支持中文的字体,以便能够正确显示中文文本。

12.字符串

1.字符串的一些内置方法

字符串是 Python 中的内置数据类型之一,它有许多内置方法可以用于对字符串进行各种操作。以下是一些常用的字符串内置方法:

  1. len(): 返回字符串的长度。
  2. lower(): 将字符串转换为小写形式。
  3. upper(): 将字符串转换为大写形式。
  4. capitalize(): 将字符串的第一个字符转换为大写,其他字符转换为小写。
  5. title(): 将字符串中每个单词的首字母转换为大写。
  6. strip(): 去除字符串两端的空格或指定的字符。
  7. split(): 将字符串按指定的分隔符拆分成列表。
  8. join(): 将列表中的字符串元素连接成一个字符串。
  9. replace(): 将字符串中指定的子串替换为新的子串。
  10. startswith(): 检查字符串是否以指定的子串开头。
  11. endswith(): 检查字符串是否以指定的子串结尾。
  12. find(): 查找指定的子串在字符串中的位置。
  13. count(): 统计指定的子串在字符串中出现的次数。
  14. isalpha(): 检查字符串是否只包含字母字符。
  15. isdigit(): 检查字符串是否只包含数字字符。

这只是一些常用的字符串方法,还有更多方法可供使用。你可以查阅 Python 的官方文档或使用 help() 函数来获取关于字符串方法的详细信息和用法示例。

2.str.maketrans()

str.maketrans() 是一个字符串方法,用于创建一个字符映射转换表。它接受两个参数:第一个参数是一个包含要替换的字符的字符串,第二个参数是一个包含相应替换字符的字符串。

str.maketrans(x, y, z) 的语法如下:

  • x:要替换的字符。
  • y:替换的目标字符。
  • z:要删除的字符。

转换表可以用于 str.translate() 方法来执行字符串的字符替换或删除操作。

下面是一个示例,演示如何使用 str.maketrans()str.translate() 进行字符替换和删除:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
text = "Hello, World!"

# 创建一个转换表,将字母 "o" 替换为数字 "0"
trans_table = str.maketrans("o", "0")

# 使用转换表进行字符替换
new_text = text.translate(trans_table)
print(new_text) # 输出: Hell0, W0rld!

# 创建一个转换表,删除所有的元音字母
trans_table = str.maketrans("", "", "aeiouAEIOU")

# 使用转换表进行字符删除
new_text = text.translate(trans_table)
print(new_text) # 输出: Hll, Wrld!

在这个示例中,我们首先使用 str.maketrans() 创建了两个转换表,分别用于将字母 “o” 替换为数字 “0”,以及删除所有的元音字母。然后,我们使用 str.translate() 方法根据转换表进行字符替换和删除操作。

3. 其他内置处理函数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#-- 内置str处理函数:
str1 = "stringobject"
str1.upper(); str1.lower(); str1.swapcase(); str1.capitalize(); str1.title() # 全部大写,全部小写、大小写转换,首字母大写,每个单词的首字母都大写
str1.ljust(width) # 获取固定长度,左对齐,右边不够用空格补齐
str1.rjust(width) # 获取固定长度,右对齐,左边不够用空格补齐
str1.center(width) # 获取固定长度,中间对齐,两边不够用空格补齐
str1.zfill(width) # 获取固定长度,右对齐,左边不足用0补齐
str1.find('t',start,end) # 查找字符串,可以指定起始及结束位置搜索
str1.rfind('t') # 从右边开始查找字符串
str1.count('t') # 查找字符串出现的次数
#上面所有方法都可用index代替,不同的是使用index查找不到会抛异常,而find返回-1
str1.replace('old','new') # 替换函数,替换old为new,参数中可以指定maxReplaceTimes,即替换指定次数的old为new
str1.strip(); # 默认删除空白符
str1.strip('d'); # 删除str1字符串中开头、结尾处,位于 d 删除序列的字符
str1.lstrip();
str1.lstrip('d'); # 删除str1字符串中开头处,位于 d 删除序列的字符
str1.rstrip();
str1.rstrip('d') # 删除str1字符串中结尾处,位于 d 删除序列的字符
str1.startswith('start') # 是否以start开头
str1.endswith('end') # 是否以end结尾
str1.isalnum(); str1.isalpha(); str1.isdigit(); str1.islower(); str1.isupper() # 判断字符串是否全为字符、数字、小写、大写

4.字符串的格式化

基于C语言的’print’模型,并且在大多数的现有的语言中使用。通用结构:%[(name)][flag][width].[precision]typecode

1
2
3
4
5
6
7
8
9
"this is %d %s bird" %(1, 'dead')	#一般的格式化表达式
"%s---%s---%s" %(42, 3.14, [1, 2, 3]) #字条串输出:'42---3.14---[1, 2, 3]'
# 对齐方式及填充:"1234... 1234...1234 ...001234"
"%d...%6d...%-6d...%06d" % (1234, 1234, 1234, 1234)
x = 1.23456789
"%e | %f | %g" % (x, x, x) # 对齐方式:"1.234568e+00 | 1.234568 | 1.23457"
"%6.2f*%-6.2f*%06.2f*%+6.2f" % (x, x, x, x) # 对齐方式:' 1.23*1.23 *001.23* +1.23'
"%(name1)d---%(name2)s" % {"name1":23, "name2":"value2"} # 基于字典的格式化表达式
"%(name)s is %(age)d" % vars() # vars()函数调用返回一个字典,包含了所有本函数调用时存在的变量

字体串格式化调用方法

1
2
3
4
5
6
7
8
9
10
11
12
"{0}, {1} and {2}".format('spam', 'ham', 'eggs')            # 基于位置的调用
"{motto} and {pork}".format(motto = 'spam', pork = 'ham') # 基于Key的调用
"{motto} and {0}".format('ham', motto = 'spam') # 混合调用
# 添加键 属性 偏移量 (import sys)
"my {1[spam]} runs {0.platform}".format(sys, {'spam':'laptop'}) # 基于位置的键和属性
# 基于Key的键和属性
"{config[spam]} {sys.platform}".format(sys = sys, config = {'spam':'laptop'})
"first = {0[0]}, second = {0[1]}".format(['A', 'B', 'C']) # 基于位置的偏移量
# 具体格式化
# 输出'3.141590e+00, 3.142e+00, 3.14159'
"{0:e}, {1:.3e}, {2:g}".format(3.14159, 3.14159, 3.14159)
"{fieldname:format_spec}".format(......)

说明:

fieldname是指定参数的一个数字或关键字, 后边可跟可选的”.name”或”[index]”成分引用
format_spec ::= [[fill]align][sign][#][0][width][,][.precision][type]
fill ::= #填充字符
align ::= “<” | “>” | “=” | “^” #对齐方式
sign ::= “+” | “-“ | “ “ #符号说明
width ::= integer #字符串宽度
precision ::= integer #浮点数精度
type ::= “b” | “c” | “d” | “e” | “E” | “f” | “F” | “g” | “G” | “n” | “o” | “s” | “x” | “X” | “%”

例子:

1
2
3
4
5
6
'={0:10} = {1:10}'.format('spam', 123.456)    # 输出'=spam       =    123.456'
'={0:>10}='.format('test') # 输出'= test='
'={0:<10}='.format('test') # 输出'=test ='
'={0:^10}='.format('test') # 输出'= test ='
'{0:X}, {1:o}, {2:b}'.format(255, 255, 255) # 输出'FF, 377, 11111111'
'My name is {0:{1}}.'.format('Fred', 8) # 输出'My name is Fred .' 动态指定参数

4.textwrap

textwrap 模块是 Python 标准库中的一个模块,它提供了一些用于格式化和包装文本的函数和类。主要用于将长文本按照指定的宽度进行自动换行和格式化,以适应给定的输出区域。

以下是一些常用的 textwrap 模块函数和类:

  1. textwrap.wrap(text, width):将文本按照指定的宽度进行分割,返回一个列表,每个元素表示一行文本。
  2. textwrap.fill(text, width):将文本按照指定的宽度进行自动换行,并返回一个格式化后的文本字符串。
  3. textwrap.shorten(text, width, placeholder='...'):将文本缩短至指定的宽度,超出部分用指定的占位符替代。
  4. textwrap.dedent(text):去除文本块中的公共缩进。
  5. textwrap.indent(text, prefix):在文本块的每一行前添加指定的前缀。
  6. textwrap.TextWrapper 类:提供了更多高级的文本包装和格式化选项,可以定制换行、缩进、对齐等参数。

以下是一个示例,展示了如何使用 textwrap 模块来格式化文本:

1
2
3
4
5
6
7
8
9
10
11
12
import textwrap

text = "This is a long piece of text that needs to be wrapped properly to fit within the specified width."

# 使用 textwrap.wrap 进行文本分割
wrapped_lines = textwrap.wrap(text, width=30)
for line in wrapped_lines:
print(line)

# 使用 textwrap.fill 进行文本换行和格式化
formatted_text = textwrap.fill(text, width=30)
print(formatted_text)

你可以根据需要在输出中查看不同的格式化结果。请注意,textwrap 模块提供了更多的选项和功能,可以根据具体需求进行定制。

13.列表的一些内置方法

列表是 Python 中的内置数据类型之一,它提供了丰富的内置方法来操作和处理列表。以下是一些常用的列表内置方法:

  1. append(): 在列表末尾添加一个元素。
  2. extend(): 将一个列表的元素追加到另一个列表中。
  3. insert(): 在指定位置插入一个元素。
  4. remove(): 移除列表中指定的元素。
  5. pop(): 移除并返回列表中指定位置的元素。
  6. index(): 返回指定元素在列表中的索引位置。
  7. count(): 统计指定元素在列表中出现的次数。
  8. sort(): 对列表进行排序。
  9. reverse(): 反转列表中的元素顺序。
  10. copy(): 创建一个列表的副本。
  11. clear(): 清空列表中的所有元素。
  12. len(): 返回列表的长度。

这只是一些常用的列表方法,还有更多方法可供使用。你可以查阅 Python 的官方文档或使用 help() 函数来获取关于列表方法的详细信息和用法示例。

14.列表切片

列表切片是一种常用的操作,可以通过切片来获取列表中的部分元素,创建新的列表或对原列表进行修改。以下是一些常见的列表切片的内置方法:

  1. 切片操作:使用冒号(:)来表示切片操作,可以指定起始位置、终止位置和步长。示例:list[start:stop:step]
  2. list[start:stop]:获取从起始位置到终止位置的元素(不包括终止位置)。
  3. list[start:]:获取从起始位置到列表末尾的元素。
  4. list[:stop]:获取从列表开头到终止位置的元素(不包括终止位置)。
  5. list[:]:获取整个列表的副本。
  6. list[start:stop:step]:指定步长来获取指定间隔的元素。

除了切片操作,还有一些其他常见的列表方法:

  1. list.append(item):将元素添加到列表的末尾。
  2. list.extend(iterable):将可迭代对象中的元素添加到列表的末尾。
  3. list.insert(index, item):在指定索引位置插入元素。
  4. list.remove(item):从列表中删除指定的元素。
  5. list.pop(index):删除并返回指定索引位置的元素。
  6. list.index(item):返回指定元素在列表中的索引。
  7. list.count(item):返回指定元素在列表中出现的次数。
  8. list.sort():对列表进行排序。
  9. list.reverse():反转列表中的元素顺序。

15.使用pyecharts画中国、省、市地图

代码如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
#! -*- coding:utf-8 -*-

from pyecharts import options as opts
from pyecharts.charts import Map
import random

#设置两组数据列表,一组为省份,一组为城市
province = '安徽省,北京市,重庆市,福建省,甘肃省,广东省,广西壮族自治区,贵州省,海南省,河北省,黑龙江省,河南省,湖北省,湖南省,内蒙古自治区,江苏省,江西省,吉林省,辽宁省,宁夏回族自治区,青海省,山东省,山西省,陕西省,上海市,四川省,天津市,西藏自治区,新疆维吾尔自治区,云南省,浙江省,台湾省'
province = province.split(',')

# print(province)
#将省份转换为[['省1',值1],['省2',值2]....]这种格式,并存储到province_data列表中
province_data = []
for x in province:
temp = []
temp.append(x)
temp.append(random.randint(1,1000))
province_data.append(temp)

#另一种幅值方法
cities_data = [
['福州市',0],
['厦门市',0],
['泉州市',0],
['莆田市',0],
['漳州市',0],
['龙岩市',0],
['三明市',0],
['南平市',0],
['宁德市',0]
]

def data_filling(array):
'''给数据数据填充随机数'''
for i in array:
for j in i:
i[1] = random.randint(1,1000)

#调用data_filling函数给cities_data赋随机值
data_filling(cities_data)

def create_china_map():
"""生成一个中国地图"""
(
Map(init_opts=opts.InitOpts(height="860px", width="1800px"))
.add(
series_name='全国',
data_pair=province_data,
maptype="china",
#默认是否选中
# is_selected=False,
# 是否启用鼠标滚轮缩放和拖动平移,默认为True
is_roam=True,
# 是否显示图形标记,默认为True
is_map_symbol_show=False,
# 局部关闭标签显示
label_opts=opts.LabelOpts(is_show=False),
# 图元样式配置
# itemstyle_opts={
# # 常规显示
# "normal": {"areaColor": "white", "borderColor": "red"},
# # 强调颜色
# "emphasis": {"areaColor": "rgba(0,0,0,1)"}
# }
)
.add(
series_name='福建省',
data_pair=cities_data,
maptype="china-cities",
#默认是否选中
# is_selected=False
)
#设置标题
.set_global_opts(title_opts=opts.TitleOpts(title='中国地图'),
#设置分段显示
visualmap_opts=opts.VisualMapOpts(max_=1000,is_piecewise=False)
)
# 系列配置项
# 关闭标签名称显示
.set_series_opts(label_opts=opts.LabelOpts(is_show=False))
#生成本地html文件
.render("中国地图.html")
)

create_china_map()

其中maptype可选择:

  • china:全国地图,最小单元的省份

  • 省份名称:显示指定省份地图(如福建)显示的为福建地图

  • 市名:显示的为指定市地图,如(宁德)

  • china-cities:显示的为中国地图,按城市划分

  • worrld:世界地图

16. 字典

1.对字典根据关键字进行排序

要对字典列表根据关键字进行排序,可以使用 itemgetter() 函数配合 sorted() 函数来实现。

itemgetter() 函数可以用于获取字典中的特定键的值,它接受一个键作为参数,并返回一个函数,该函数用于获取给定键的值。sorted() 函数可以接受一个可迭代对象和一个关键字参数 key,用于指定排序的依据。

下面是一个示例,演示如何对字典列表根据关键字进行排序:

1
2
3
4
5
6
7
8
9
10
11
12
from operator import itemgetter

# 假设有一个字典列表
data = [{'name': 'Alice', 'age': 25}, {'name': 'Bob', 'age': 30}, {'name': 'Charlie', 'age': 20}]

# 按照 'name' 关键字进行排序
sorted_data = sorted(data, key=itemgetter('name'))
print(sorted_data)

# 按照 'age' 关键字进行排序
sorted_data = sorted(data, key=itemgetter('age'))
print(sorted_data)

可以加上resverse=True实现倒序

2. 常用字典常量和操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
D = {}
D = {'spam':2, 'tol':{'ham':1}} # 嵌套字典
D = dict.fromkeys(['s', 'd'], 8) # {'s': 8, 'd': 8}
D = dict(name = 'tom', age = 12) # {'age': 12, 'name': 'tom'}
D = dict([('name', 'tom'), ('age', 12)]) # {'age': 12, 'name': 'tom'}
D = dict(zip(['name', 'age'], ['tom', 12])) # {'age': 12, 'name': 'tom'}
D.keys(); D.values(); D.items() # 字典键、值以及键值对
D.get(key, default) # get函数
D.update(D_other) # 合并字典,如果存在相同的键值,D_other的数据会覆盖掉D的数据
D.pop(key, [D]) # 删除字典中键值为key的项,返回键值为key的值,如果不存在,返回默认值D,否则异常
D.popitem() # pop字典中随机的一项(一个键值对)
D.setdefault(k[, d]) # 设置D中某一项的默认值。如果k存在,则返回D[k],否则设置D[k]=d,同时返回D[k]。
del D # 删除字典
del D['key'] # 删除字典的某一项
if key in D: if key not in D: # 测试字典键是否存在
# 字典注意事项:(1)对新索引赋值会添加一项(2)字典键不一定非得是字符串,也可以为任何的不可变对象
# 不可变对象:调用对象自身的任意方法,也不会改变该对象自身的内容,这些方法会创建新的对象并返回。
# 字符串、整数、tuple都是不可变对象,dict、set、list都是可变对象
D[(1,2,3)] = 2

字典解析:

1
2
D = {k:8 for k in ['s', 'd']}                     # {'s': 8, 'd': 8}
D = {k:v for (k, v) in zip(['name', 'age'], ['tom', 12])} # {'age': 12, 'name': tom}

字典的特殊方法__missing__:当查找找不到key时,会执行该方法:

1
2
3
4
5
6
7
class Dict(dict):
def __missing__(self, key):
self[key] = []
return self[key]
dct = dict()
dct["foo"].append(1) # 这有点类似于collections.defalutdict
dct["foo"] # [1]

17.打印输出文字设置颜色

在标准输出中,Python 没有直接支持设置文本颜色的功能。然而,你可以通过使用 ANSI 转义序列来实现在终端中设置文本颜色。

下面是一个示例,展示了如何使用 ANSI 转义序列设置输出文本的颜色:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# ANSI 转义序列设置文本颜色
BLACK = "\033[0;30m"
RED = "\033[0;31m"
GREEN = "\033[0;32m"
YELLOW = "\033[0;33m"
BLUE = "\033[0;34m"
MAGENTA = "\033[0;35m"
CYAN = "\033[0;36m"
WHITE = "\033[0;37m"
RESET = "\033[0m"

# 示例输出
print(RED + "这是红色文本" + RESET)
print(GREEN + "这是绿色文本" + RESET)
print(YELLOW + "这是黄色文本" + RESET)
print(BLUE + "这是蓝色文本" + RESET)
print(MAGENTA + "这是品红色文本" + RESET)
print(CYAN + "这是青色文本" + RESET)
print(WHITE + "这是白色文本" + RESET)

上述代码使用 ANSI 转义序列设置了不同颜色的文本,并通过 print 函数打印到终端。输出结果将根据设置的颜色显示不同的文本颜色。要恢复默认的文本颜色,可以使用 RESET 序列。

请注意,ANSI 转义序列的可用性和效果可能因终端类型和操作系统而异。在某些情况下,它可能无法在某些终端或操作系统上正常工作。

18.变量作用域

变量作用域是指在程序中定义的变量所能被访问的范围或可见性。它决定了变量在程序的哪些部分可以被引用或修改。

在Python中,有以下几种变量作用域:

  1. 全局作用域(Global Scope):在整个程序中都可以访问的变量称为全局变量,它在程序的任何地方都是可见的。
  2. 局部作用域(Local Scope):在函数内部定义的变量称为局部变量,它只能在函数内部被访问。
  3. 嵌套作用域(Enclosing Scope):在嵌套的函数中,内部函数可以访问外部函数中定义的变量。

变量的作用域规则如下:

  • 在函数内部,可以访问该函数内部定义的变量、外部函数中定义的变量和全局变量。
  • 在函数外部,只能访问全局变量。
  • 如果在函数内部使用了与外部作用域相同名称的变量,会创建一个新的局部变量,覆盖外部作用域中的变量。
  • 在嵌套函数中,内部函数可以访问外部函数的变量,但不能修改它们(除非使用 nonlocal 关键字)。

了解变量作用域对于正确理解和使用变量非常重要,它可以帮助避免命名冲突、提高代码的可读性和可维护性。

19.lambda创建匿名函数

使用 lambda 表达式可以创建匿名函数。Lambda 表达式是一种快速定义简单函数的方式,它可以接受任意数量的参数,并返回一个表达式的结果。

下面是使用 lambda 表达式创建函数的示例:

1
2
3
4
5
# 创建一个接受两个参数并返回它们之和的 lambda 函数
addition = lambda x, y: x + y

# 调用 lambda 函数并打印结果
print(addition(3, 5)) # 输出: 8

在上面的示例中,addition 是一个 lambda 函数,它接受两个参数 xy,并返回它们的和。可以直接调用 addition(3, 5) 来执行 lambda 函数,并打印结果。

Lambda 表达式通常用于需要定义简单函数且不需要命名的场景。它可以在需要函数的地方直接使用,也可以作为参数传递给其他函数。需要注意的是,lambda 表达式不能包含复杂的语句块,只能包含一个表达式,并且返回该表达式的结果。

20.tkinter画图形

tkinter 是 Python 的标准图形用户界面(GUI)库,它提供了一组用于创建图形界面的工具和组件。tkinter 是 Python 的内置库,因此在安装 Python 后,无需额外安装即可使用它。

tkinter 基于 Tcl/Tk 工具包,它提供了一种简单和直观的方式来创建窗口、按钮、文本框、标签等各种图形界面组件,并通过编写事件处理程序来响应用户的交互操作。

通过 tkinter,您可以创建各种类型的桌面应用程序,包括简单的工具、图形化配置界面、数据可视化应用等。

以下是一个简单的 tkinter 示例,创建一个窗口并显示一个标签:

1
2
3
4
5
6
7
8
9
10
11
import tkinter as tk

# 创建主窗口
window = tk.Tk()

# 创建标签
label = tk.Label(window, text="Hello, tkinter!")
label.pack()

# 运行主循环
window.mainloop()

这段代码创建了一个主窗口,并在窗口中显示了一个标签。Tk() 函数用于创建主窗口对象,Label 函数用于创建标签对象,pack() 方法用于将标签放置到主窗口中,mainloop() 方法用于启动主循环,使窗口保持显示状态。

下面这个例子是画一个圆形:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
import tkinter as tk

# 创建主窗口
window = tk.Tk()

# 创建画布
canvas = tk.Canvas(window, width=400, height=400)
canvas.pack()

# 绘制圆形
circle = canvas.create_oval(100, 100, 300, 300, fill="red")

# 运行主循环
window.mainloop()

在这个例子中,我们首先创建了一个主窗口,并在窗口中创建了一个画布。然后,使用 create_oval() 方法在画布上绘制了一个圆形。create_oval() 方法接受四个参数,分别是圆形的左上角和右下角坐标。我们将圆形的左上角坐标设为 (100, 100),右下角坐标设为 (300, 300),这样圆形的直径就是 200 像素。最后,我们使用 fill 参数指定了圆形的填充颜色。

您可以根据需要调整圆形的位置、大小和颜色。通过 Canvas 组件的其他方法和属性,还可以绘制线条、矩形、多边形等其他图形,并实现更复杂的绘图效果。

21.map()函数的使用

map()函数是Python中的一个内置函数,用于将一个函数应用于一个或多个可迭代对象(例如列表、元组)的对应元素上,返回一个迭代器。

map()函数的语法如下:

1
map(function, iterable1, iterable2, ...)

其中:

  • function是一个函数,可以是内置函数、自定义函数或匿名函数(lambda表达式)。
  • iterable1, iterable2, ...是一个或多个可迭代对象,可以是列表、元组等。

map()函数将function应用于每个iterable中对应位置的元素,并返回一个迭代器,其中包含了应用了函数后的结果。

示例:

1
2
3
4
5
6
7
8
9
10
11
# 使用匿名函数对两个列表的元素进行相加
a = [1, 2, 3]
b = [4, 5, 6]
result = map(lambda x, y: x + y, a, b)
# 输出结果为迭代器对象:<map object at 0x000001>
print(result)

# 将迭代器转换为列表
result_list = list(result)
# 输出结果为列表:[5, 7, 9]
print(result_list)

在上面的示例中,map()函数将匿名函数 lambda x, y: x + y 应用于列表 ab 的对应元素上,返回一个迭代器。通过将迭代器转换为列表,我们可以获取应用函数后的结果列表。在本例中,结果列表为 [5, 7, 9],即对应位置元素相加的结果。

22.旋转列表

deque.rotatecollections 模块中 deque 类提供的一个方法,用于循环移动双向队列中的元素。

语法如下:

1
deque.rotate(n)

其中,deque 是一个双向队列对象,n 是要旋转的元素数量。当 n 为正数时,元素向右移动;当 n 为负数时,元素向左移动。

具体操作如下:

  • n 的绝对值小于等于队列长度时,元素按照指定的数量进行循环移动。
  • n 的绝对值大于队列长度时,元素会循环移动多个周期,效果与取模运算类似。

下面是一个例子:

1
2
3
4
5
6
from collections import deque

queue = deque([1, 2, 3, 4, 5])
queue.rotate(2) # 向右循环移动2个元素

print(queue) # 输出: deque([4, 5, 1, 2, 3])

在上述例子中,初始队列为 [1, 2, 3, 4, 5],通过 queue.rotate(2) 将队列中的元素向右循环移动了 2 个位置,得到的结果为 [4, 5, 1, 2, 3]

23.if name == ‘main

if __name__ == '__main__': 是 Python 中常用的条件语句,用于判断当前模块是否作为主程序运行。

当一个 Python 文件被直接运行时,即通过命令行或脚本执行时,__name__ 属性的值会被设置为 '__main__'。而当一个模块被导入到其他文件中时,__name__ 属性的值为模块的名称。

因此,if __name__ == '__main__': 的作用是用于判断当前模块是否作为主程序运行。当条件成立时,即当前模块作为主程序运行时,可以执行一些特定的代码块,通常用于测试、调试或执行特定的任务。

例如,假设有一个名为 example.py 的模块文件,其中包含如下代码:

1
2
3
4
5
6
7
8
9
def foo():
print("Hello, foo!")

def bar():
print("Hello, bar!")

if __name__ == '__main__':
foo()
bar()

当直接运行 example.py 文件时,输出结果为:

1
2
Hello, foo!
Hello, bar!

而当该模块被导入到其他文件中时,foo()bar() 函数不会自动执行,因为 __name__ 属性的值不为 '__main__'

24.进制转换

二进制(Binary)、八进制(Octal)、十进制(Decimal)和十六进制(Hexadecimal)是不同的数制系统,用于表示数值。

  • 二进制:使用 0 和 1 表示数字,以 0b0B 前缀开头,如 0b010101。在计算机中,二进制是最基本的数制,因为计算机以位(0 和 1)表示信息。在 Python 中,可以使用 0b0B 前缀来表示二进制数,例如 0b10 表示二进制的 10,其十进制值为 2。
  • 八进制:使用 0-7 的数字表示,以 0o0O 前缀开头,如 0o1234567。八进制是以 3 位二进制为一个单位进行表示,每个八进制位对应于 3 个二进制位。在 Python 中,可以使用 0o0O 前缀来表示八进制数,例如 0o10 表示八进制的 10,其十进制值为 8。
  • 十进制:使用 0-9 的数字表示,不需要前缀,如 0123456789。十进制是我们常用的十个数字的表示方式,是我们日常生活中最常见的数值表示法。
  • 十六进制:使用 0-9 和 A-F 的数字和字母表示,以 0x0X 前缀开头,如 0x123456789ABCDEF。十六进制是以 4 位二进制为一个单位进行表示,每个十六进制位对应于 4 个二进制位。在 Python 中,可以使用 0x0X 前缀来表示十六进制数,例如 0x10 表示十六进制的 10,其十进制值为 16。

不同进制的数值表示法在计算机科学和编程中具有不同的应用场景。例如,二进制常用于处理位运算和存储二进制数据,八进制和十六进制常用于表示内存地址或颜色值。

Python 提供了内置函数 bin()oct()int()hex() 来在不同进制之间进行转换。

以下是一些示例代码片段,展示了在不同进制之间进行转换的示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
# 十进制转二进制
decimal = 10
binary = bin(decimal)
print(binary) # 输出: 0b1010

# 十进制转八进制
decimal = 10
octal = oct(decimal)
print(octal) # 输出: 0o12

# 十进制转十六进制
decimal = 16
hexadecimal = hex(decimal)
print(hexadecimal) # 输出: 0x10

# 二进制转十进制
binary = '0b1010'
decimal = int(binary,2)
print(decimal) #输出:10

# 八进制转十进制
octal = '0o12'
decimal = int(octal,8)
print(decimal) #输出:10

#十六进制转十进制
hexadecimal = '0xff'
decimal = int(hexadecimal,16)
print(decimal) #输出:255

25.结构体变量传递

在Python中,可以使用collections.namedtuple创建一个具有命名字段的结构体。它创建一个新的元组子类,并为每个字段分配一个名称,使得可以通过名称访问结构体的字段。

下面是一个示例代码,展示了如何创建结构体并进行变量传递:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
from collections import namedtuple

# 创建结构体
Person = namedtuple('Person', ['name', 'age', 'gender'])

# 创建结构体变量
person1 = Person(name='Alice', age=25, gender='Female')

# 传递结构体变量
def print_person_info(person):
print(f"Name: {person.name}")
print(f"Age: {person.age}")
print(f"Gender: {person.gender}")

# 调用函数打印结构体变量的信息
print_person_info(person1)

通过定义结构体,我们可以创建具有指定字段的结构体变量,并将其传递给其他函数或方法进行处理。在函数内部,可以通过结构体变量的字段名来访问和操作结构体的数据。

26.生成器函数(generator())

生成器函数是一种特殊的函数,它使用关键字 yield 来产生一个值序列。与普通函数不同的是,生成器函数在执行过程中可以暂停并保存当前的状态,然后在下一次调用时从暂停的地方继续执行,返回一个值,并再次暂停。这样可以节省内存并实现惰性计算。

生成器函数的定义方式与普通函数相似,但使用 yield 关键字来产生值,而不是使用 return 关键字。每次调用生成器函数时,会返回一个生成器对象,通过调用生成器对象的 __next__()next() 方法可以逐个获取生成器函数中的值。

以下是一个简单的生成器函数的示例:

1
2
3
4
5
6
7
8
9
10
11
12
def my_generator():
yield 1
yield 2
yield 3

# 调用生成器函数,获取生成器对象
gen = my_generator()

# 使用生成器对象的 __next__() 或 next() 方法逐个获取生成器函数中的值
print(next(gen)) # 输出: 1
print(next(gen)) # 输出: 2
print(next(gen)) # 输出: 3

在这个示例中,my_generator() 是一个生成器函数,使用 yield 语句产生了三个值:1、2 和 3。通过调用生成器函数 my_generator() 获取生成器对象 gen,然后使用 next() 函数或生成器对象的 __next__() 方法逐个获取生成器函数中的值,并将其打印出来。

生成器函数还可以接收参数,用于控制生成器函数的行为和产生不同的值序列。生成器函数可以使用循环、条件语句和其他的控制结构来动态地生成值,具有很高的灵活性和可扩展性。

需要注意的是,当生成器函数的代码执行完毕或遇到 return 语句时,会抛出 StopIteration 异常来表示生成器已经遍历完毕。因此,在使用 next() 函数或生成器对象的 __next__() 方法获取生成器对象的值时,需要注意捕获 StopIteration 异常以避免程序异常退出。

27.高阶函数

高阶函数是指可以接受函数作为参数或将函数作为返回值的函数。在Python中,函数是一等公民,因此可以像其他对象一样被传递给函数,这就是高阶函数的特性之一。

以下是一些常见的高阶函数的示例:

  1. map() 函数:接受一个函数和一个可迭代对象,将函数应用于可迭代对象的每个元素,并返回一个新的可迭代对象。示例:
1
2
3
numbers = [1, 2, 3, 4, 5]
squares = map(lambda x: x ** 2, numbers)
print(list(squares)) # 输出: [1, 4, 9, 16, 25]
  1. filter() 函数:接受一个函数和一个可迭代对象,根据函数的返回值对可迭代对象进行过滤,并返回一个新的可迭代对象。示例:
1
2
3
numbers = [1, 2, 3, 4, 5]
even_numbers = filter(lambda x: x % 2 == 0, numbers)
print(list(even_numbers)) # 输出: [2, 4]
  1. reduce() 函数:接受一个函数和一个可迭代对象,将函数应用于可迭代对象的前两个元素,然后将结果与下一个元素继续应用函数,直到遍历完所有元素并返回最终结果。示例:
1
2
3
4
5
from functools import reduce

numbers = [1, 2, 3, 4, 5]
product = reduce(lambda x, y: x * y, numbers)
print(product) # 输出: 120 (1 * 2 * 3 * 4 * 5)
  1. sorted() 函数:接受一个可迭代对象,并根据指定的排序规则对其进行排序,并返回一个新的列表。可以通过传递 key 参数来指定排序规则所依据的函数。示例:
1
2
3
4
5
6
7
numbers = [5, 2, 4, 1, 3]
sorted_numbers = sorted(numbers)
print(sorted_numbers) # 输出: [1, 2, 3, 4, 5]

words = ['apple', 'banana', 'cherry', 'date']
sorted_words = sorted(words, key=len)
print(sorted_words) # 输出: ['date', 'apple', 'banana', 'cherry']

这些只是高阶函数的一些示例,Python中还有其他许多内置的高阶函数和库中提供的高阶函数。通过使用高阶函数,可以简化代码、提高代码的可读性和灵活性,并充分发挥函数作为一等公民的优势。

28.装饰器(Decorator)

代码运行期间动态增加功能的方式,称之为“装饰器”(Decorator)。本质上,decorator就是一个返回函数的高阶函数。装饰器是一种特殊的Python函数,用于修改其他函数的行为。装饰器可以在不修改原函数代码的情况下添加额外的功能或行为。

装饰器的使用方式是通过在被装饰函数的定义之前使用 @装饰器函数名 的语法来应用装饰器。

下面是一个简单的装饰器示例,用于记录函数的执行时间:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
import time

def timing_decorator(func):
def wrapper(*args, **kwargs):
start_time = time.time()
result = func(*args, **kwargs)
end_time = time.time()
execution_time = end_time - start_time
print(f"函数 {func.__name__} 的执行时间为 {execution_time} 秒")
return result
return wrapper

@timing_decorator
def my_function():
# 函数的具体实现
pass

my_function()

在上面的示例中,timing_decorator 是一个装饰器函数,它接受一个函数作为参数,并返回一个新的函数 wrapperwrapper 函数在被装饰的函数执行前后添加了计时的逻辑,并打印出执行时间。

通过在 my_function 函数的定义之前使用 @timing_decorator,我们将 my_function 函数应用了装饰器。当我们调用 my_function 时,实际上是调用了被装饰后的 wrapper 函数,从而实现了计时的功能。

装饰器的使用使得我们可以在不修改原函数代码的情况下,灵活地添加额外的功能或行为,提高代码的可复用性和可维护性。在实际开发中,装饰器常用于日志记录、性能分析、权限控制等方面。

29.非公开函数或变量

非公开函数或变量是指在Python中使用下划线(_)作为前缀命名的函数或变量。这种命名约定表示这些函数或变量是供内部使用的,不应该被外部代码直接访问或调用。

非公开函数和变量的命名约定是一种约定俗成的规范,并不会强制限制对它们的访问。在Python中,它们仍然是可以被访问和使用的,只是开发者之间通过命名约定来暗示它们的用途和意图,建议不要在外部代码中直接使用。

以下是一个示例:

1
2
3
4
5
6
7
def _internal_function():
# 非公开函数,供内部使用
pass

public_variable = 42 # 公开变量

_internal_variable = 10 # 非公开变量

在上述示例中,_internal_function 是一个非公开函数,_internal_variable 是一个非公开变量。虽然它们可以在外部访问,但是根据命名约定,开发者应该将它们视为供内部使用的实体,避免在外部代码中直接使用。

请注意,Python并不强制限制对非公开函数或变量的访问权限,这只是一种约定俗成的规范。在编写代码时,开发者应该尊重这种约定,遵循良好的编程实践,以提高代码的可维护性和可读性。

30.正则表达式

在正则表达式中,如果直接给出字符,就是精确匹配。用\d可以匹配一个数字,\w可以匹配一个字母或数字,所以:

  • '00\d'可以匹配'007',但无法匹配'00A'
  • '\d\d\d'可以匹配'010'
  • '\w\w\d'可以匹配'py3'
  • .可以匹配任意字符,所以:
    • 'py.'可以匹配'pyc''pyo''py!'等等。

要匹配变长的字符,在正则表达式中,用*表示任意个字符(包括0个),用+表示至少一个字符,用?表示0个或1个字符,用{n}表示n个字符,用{n,m}表示n-m个字符:

来看一个复杂的例子:\d{3}\s+\d{3,8}

我们来从左到右解读一下:

  1. \d{3}表示匹配3个数字,例如'010'
  2. \s可以匹配一个空格(也包括Tab等空白符),所以\s+表示至少有一个空格,例如匹配' '' '等;
  3. \d{3,8}表示3-8个数字,例如'1234567'

综合起来,上面的正则表达式可以匹配以任意个空格隔开的带区号的电话号码。

如果要匹配'010-12345'这样的号码呢?由于'-'是特殊字符,在正则表达式中,要用'\'转义,所以,上面的正则是\d{3}\-\d{3,8}

但是,仍然无法匹配'010 - 12345',因为带有空格。所以我们需要更复杂的匹配方式。

进阶

要做更精确地匹配,可以用[]表示范围,比如:

  • [0-9a-zA-Z\_]可以匹配一个数字、字母或者下划线;
  • [0-9a-zA-Z\_]+可以匹配至少由一个数字、字母或者下划线组成的字符串,比如'a100''0_Z''Py3000'等等;
  • [a-zA-Z\_][0-9a-zA-Z\_]*可以匹配由字母或下划线开头,后接任意个由一个数字、字母或者下划线组成的字符串,也就是Python合法的变量;
  • [a-zA-Z\_][0-9a-zA-Z\_]{0, 19}更精确地限制了变量的长度是1-20个字符(前面1个字符+后面最多19个字符)。

A|B可以匹配A或B,所以(P|p)ython可以匹配'Python'或者'python'

^表示行的开头,^\d表示必须以数字开头。

$表示行的结束,\d$表示必须以数字结束。

你可能注意到了,^py也可以匹配'python',但是加上^py$就变成了整行匹配,就只能匹配'py'了。de

1.re.sub()

re.sub() 是 Python 中用于替换字符串中的匹配项的函数。它使用正则表达式模式匹配字符串中的特定模式,并将其替换为指定的内容。

re.sub(pattern, repl, string, count=0, flags=0) 的语法如下:

  • pattern:要匹配的正则表达式模式。
  • repl:用于替换匹配项的字符串或替换函数。
  • string:要进行替换操作的原始字符串。
  • count:可选参数,指定替换的最大次数。默认为 0,表示替换所有匹配项。
  • flags:可选参数,用于指定正则表达式的匹配模式。

下面是一个示例,演示如何使用 re.sub() 进行字符串替换:

1
2
3
4
5
6
7
8
import re

text = "Hello, world! How are you?"

# 将字符串中的 "world" 替换为 "Python"
new_text = re.sub(r"world", "Python", text)

print(new_text)

在这个示例中,我们使用 re.sub() 将字符串中的 “world” 替换为 “Python”。函数将匹配到的第一个 “world” 替换为 “Python”,并返回替换后的新字符串。

31.intertools

itertools 模块提供了许多用于迭代和组合的工具函数。以下是一些常用的 itertools 方法:

  1. count(start=0, step=1):生成一个无限递增的迭代器,从 start 开始,以 step 为步长。

  2. cycle(iterable):对可迭代对象进行无限循环。

  3. repeat(elem, times=None):生成一个无限重复 elem 的迭代器,如果指定了 times 参数,则重复指定次数。

  4. chain(*iterables):将多个可迭代对象连接成一个迭代器。

  5. zip_longest(*iterables, fillvalue=None):将多个可迭代对象的元素逐个配对,使用 fillvalue 填充缺失的值。

  6. combinations(iterable, r):生成可迭代对象中长度为 r 的所有组合。

  7. permutations(iterable, r=None):生成可迭代对象中长度为 r 的所有排列。

  8. product(*iterables, repeat=1):生成多个可迭代对象的笛卡尔积。

  9. groupby(iterable, key=None):将可迭代对象中相邻且相等的元素分组。

  10. accumulate(iterable, func=operator.add):对可迭代对象进行累积计算。

  11. starmap(function, iterable):将函数应用于可迭代对象中的每个元素。

  12. tee(iterable, n=2):生成多个独立的迭代器副本。

  13. islice(iterable, start, stop, step=None):对可迭代对象进行切片操作。

  14. dropwhile(predicate, iterable):跳过满足条件的元素,然后迭代剩余的元素。

  15. takewhile(predicate, iterable):迭代满足条件的元素,然后停止。

    等等

1.groupby()

groupby() 是 Python 中 itertools 模块中的一个函数,它用于对可迭代对象进行分组操作。它根据指定的键函数对可迭代对象中的元素进行分组,并返回一个迭代器,每个分组都是一个元组,包含一个键和相应的元素迭代器。

groupby(iterable, key=None) 的语法如下:

  • iterable:要分组的可迭代对象。
  • key:可选参数,用于指定分组的键函数。默认情况下,它是 None,表示按照元素的原始值进行分组。

下面是一个示例,演示如何使用 groupby() 对列表进行分组:

1
2
3
4
5
6
7
8
9
10
11
from itertools import groupby

# 示例列表
numbers = [1, 1, 2, 2, 3, 3, 4, 4, 4, 5, 5]

# 根据元素的值进行分组
groups = groupby(numbers)

# 遍历分组并打印结果
for key, group in groups:
print(f"Key: {key}, Group: {list(group)}")

输出结果为:

1
2
3
4
5
Key: 1, Group: [1, 1]
Key: 2, Group: [2, 2]
Key: 3, Group: [3, 3]
Key: 4, Group: [4, 4, 4]
Key: 5, Group: [5, 5]

在这个示例中,我们使用 groupby() 对列表 numbers 进行分组。由于未指定键函数,因此默认按照元素的原始值进行分组。然后,我们遍历每个分组并打印键和对应的元素列表。

请注意,groupby() 返回的是一个迭代器,因此需要通过遍历来访问分组结果。

2.combinations 和 combinations_with_replacement

combinationscombinations_with_replacement 都是 Python 标准库中 itertools 模块提供的用于生成组合的函数,它们的区别在于生成的组合方式不同:

  1. combinations(iterable, r): 这个函数生成给定可迭代对象中长度为 r 的所有可能组合,但不考虑元素的顺序。换句话说,它生成的组合中的元素不重复,且顺序不同的组合算作不同。
  2. combinations_with_replacement(iterable, r): 这个函数也生成给定可迭代对象中长度为 r 的所有可能组合,但允许元素重复。换句话说,它生成的组合中的元素可以重复出现,且顺序不同的组合算作不同。

下面是一个示例,说明这两个函数的区别:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
from itertools import combinations, combinations_with_replacement

data = [1, 2, 3]

# 使用 combinations 生成组合(元素不重复,顺序不同的组合)
print("Combinations:")
for r in range(1, len(data) + 1):
for comb in combinations(data, r):
print(comb)

# 使用 combinations_with_replacement 生成组合(元素可以重复,顺序不同的组合)
print("\nCombinations with Replacement:")
for r in range(1, len(data) + 1):
for comb in combinations_with_replacement(data, r):
print(comb)

在上面的示例中,我们通过两种方式生成了给定数据 [1, 2, 3] 的组合。你可以运行这段代码,观察输出结果,更好地理解这两个函数的区别。

3.product()

itertools.product 是 Python 标准库中的一个函数,用于生成多个可迭代对象的笛卡尔积。它会返回所有可能的元组组合,其中每个元组的一个元素来自于每个输入的可迭代对象。通常用于生成多个集合、列表等的所有可能组合。

以下是 itertools.product 的基本使用方法示例:

1
2
3
4
5
6
7
8
9
from itertools import product

# 生成两个可迭代对象的所有组合
colors = ['red', 'green', 'blue']
sizes = ['small', 'medium', 'large']

# 生成颜色和尺寸的所有组合
color_size_combinations = list(product(colors, sizes))
print(color_size_combinations)

输出:

1
[('red', 'small'), ('red', 'medium'), ('red', 'large'), ('green', 'small'), ('green', 'medium'), ('green', 'large'), ('blue', 'small'), ('blue', 'medium'), ('blue', 'large')]

在上述示例中,product(colors, sizes) 生成了所有颜色和尺寸的组合。

你可以将 itertools.product 用于多个可迭代对象,生成这些可迭代对象的笛卡尔积。这在处理组合问题时非常有用,比如在找到多个数组的所有可能组合时。

4.permutations()

permutations()函数是Python中itertools模块提供的一个函数,用于生成指定序列的所有可能排列。它返回一个迭代器,可以用于获取序列的不同排列组合。

以下是permutations()函数的基本使用示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
from itertools import permutations

# 创建一个序列
sequence = [1, 2, 3]

# 获取序列的所有排列
perm = permutations(sequence)

# 将排列转换为列表
perm_list = list(perm)

# 打印所有排列
for p in perm_list:
print(p)

在上面的示例中,我们首先导入permutations函数,然后创建一个包含整数1、2和3的序列。接下来,我们使用permutations()函数生成这个序列的所有排列。最后,我们将排列转换为一个列表,并打印出所有的排列组合。

输出结果将显示所有可能的排列,例如:

1
2
3
4
5
6
(1, 2, 3)
(1, 3, 2)
(2, 1, 3)
(2, 3, 1)
(3, 1, 2)
(3, 2, 1)

5.permutations()与product()的区别

permutations()product()是Python中itertools模块提供的两个函数,用于生成序列的不同组合,但它们之间有一些关键区别:

  1. 排列 vs. 组合:
    • permutations(iterable, r): 生成指定长度 r 的排列,包括了所有元素的不同顺序排列。如果不指定 r,则默认为序列的长度。每个元素仅在结果中出现一次。
    • product(*iterables, repeat=1): 生成笛卡尔积,包括了多个可迭代对象中所有可能的组合,可以包含重复的元素。
  2. 结果类型:
    • permutations()返回的结果是一个排列的迭代器,其中每个排列是一个元组。
    • product()返回的结果是笛卡尔积的迭代器,其中每个组合是一个元组。
  3. 使用场景:
    • permutations()通常用于生成不同元素的排列,例如生成字母的不同排列。
    • product()通常用于生成多个可迭代对象的所有组合,可能包含相同元素的组合。

下面是两个函数的简单示例:

1
2
3
4
5
6
7
8
9
10
11
from itertools import permutations, product

# 生成排列
perm = permutations([1, 2, 3], 2)
perm_list = list(perm)
print(perm_list) # 输出: [(1, 2), (1, 3), (2, 1), (2, 3), (3, 1), (3, 2)]

# 生成笛卡尔积
prod = product([1, 2], ['a', 'b'])
prod_list = list(prod)
print(prod_list) # 输出: [(1, 'a'), (1, 'b'), (2, 'a'), (2, 'b')]

在上面的示例中,permutations()生成了包含2个元素的排列,而product()生成了两个可迭代对象的笛卡尔积。

32数字相关

1. decimal模块

decimal模块是Python中用于高精度数学运算的模块。它提供了一种Decimal数据类型,可以用于执行浮点数运算,并且具有固定的精度,避免了浮点数运算中的精度损失问题。

在Python中,通常使用float类型来表示浮点数,但是由于浮点数的存储方式是二进制表示,导致在进行一些简单的算术运算时可能会出现精度丢失。例如:

1
2
x = 0.1 + 0.2
print(x) # 输出为 0.30000000000000004

而使用decimal模块,可以避免这种精度问题,例如:

1
2
3
4
from decimal import Decimal

x = Decimal('0.1') + Decimal('0.2')
print(x) # 输出为 0.3

decimal模块的主要特点包括:

  1. 支持大量的数学函数,例如sin、cos、exp等。
  2. 可以设置固定的精度(小数位数)。
  3. 可以进行高精度的运算,避免浮点数运算精度问题。
  4. 支持各种数值格式的输入和输出,如字符串、整数等。

以下是一个使用decimal模块的简单示例:

1
2
3
4
5
6
7
8
9
10
from decimal import Decimal

# 设置精度为2位小数
Decimal.getcontext().prec = 2

# 高精度计算
x = Decimal('1.1')
y = Decimal('2.2')
result = x + y
print(result) # 输出为 3.3

请注意,由于decimal模块提供了高精度的计算,它比普通的浮点数运算更消耗计算资源。因此,在实际应用中,建议根据实际需求来选择使用decimal模块还是普通的浮点数。如果需要更高的精度和准确性,可以考虑使用decimal模块。

2. Fraction模块

Fraction模块是Python中用于处理有理数(分数)的模块。它提供了Fraction类,可以用于表示和操作有理数,避免了浮点数运算中的精度损失问题,并且保持精确的数值。

在Python中,通常使用float类型来表示浮点数,但由于浮点数的存储方式是二进制表示,进行简单的算术运算可能会出现精度丢失问题。而使用Fraction模块可以避免这种精度问题,以及得到更准确的结果。

Fraction模块的主要特点包括:

  1. 可以表示有理数,如分数,例如 1/3、2/5 等。
  2. 可以进行有理数之间的算术运算,如加法、减法、乘法、除法等。
  3. 支持各种数值格式的输入和输出,如字符串、整数等。

以下是一个使用Fraction模块的简单示例:

1
2
3
4
5
6
7
8
9
from fractions import Fraction

# 创建分数对象
frac1 = Fraction(1, 3)
frac2 = Fraction(2, 5)

# 进行加法运算
result = frac1 + frac2
print(result) # 输出为 11/15

decimal模块不同,Fraction模块提供了精确的有理数计算,而不是高精度的十进制计算。因此,如果需要进行精确的分数运算,Fraction模块是一个很好的选择。

需要注意的是,Fraction模块仅适用于有理数,无法处理无理数(例如π和√2)。如果需要处理无理数,可以考虑使用decimal模块或其他数学计算库。

33文件

1.文件的基本操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
output = open(r'C:\spam', 'w')          # 打开输出文件,用于写
input = open('data', 'r') # 打开输入文件,用于读。打开的方式可以为'w', 'r', 'a', 'wb', 'rb', 'ab'等
fp.read([size]) # size为读取的长度,以byte为单位
fp.readline([size]) # 读一行,如果定义了size,有可能返回的只是一行的一部分
fp.readlines([size]) # 把文件每一行作为一个list的一个成员,并返回这个list。其实它的内部是通过循环调用readline()来实现的。如果提供size参数,size是表示读取内容的总长。
fp.readable() # 是否可读
fp.write(str) # 把str写到文件中,write()并不会在str后加上一个换行符
fp.writelines(seq) # 把seq的内容全部写到文件中(多行一次性写入)
fp.writeable() # 是否可写
fp.close() # 关闭文件。
fp.flush() # 把缓冲区的内容写入硬盘
fp.fileno() # 返回一个长整型的”文件标签“
fp.isatty() # 文件是否是一个终端设备文件(unix系统中的)
fp.tell() # 返回文件操作标记的当前位置,以文件的开头为原点
fp.next() # 返回下一行,并将文件操作标记位移到下一行。把一个file用于for … in file这样的语句时,就是调用next()函数来实现遍历的。
fp.seek(offset[,whence]) # 将文件打开操作标记移到offset的位置。whence为0表示从头开始计算,1表示以当前位置为原点计算。2表示以文件末尾为原点进行计算。
fp.seekable() # 是否可以seek
fp.truncate([size]) # 把文件裁成规定的大小,默认的是裁到当前文件操作标记的位置。
for line in open('data'):
print(line) # 使用for语句,比较适用于打开比较大的文件
with open('data') as file:
print(file.readline()) # 使用with语句,可以保证文件关闭
with open('data') as file:
lines = file.readlines() # 一次读入文件所有行,并关闭文件
open('f.txt', encoding = 'latin-1') # Python3.x Unicode文本文件
open('f.bin', 'rb') # Python3.x 二进制bytes文件
# 文件对象还有相应的属性:buffer closed encoding errors line_buffering name newlines等

34collections

collections 是 Python 中的一个模块,提供了一些额外的数据类型和数据结构,用于在处理数据时扩展标准数据类型的功能。以下是一些常见的 collections 类型和它们的主要功能:

  1. Counter:用于计数可迭代对象中元素的出现次数,并返回一个字典,其中键是元素,值是计数。
1
2
3
4
5
6
7
from collections import Counter

# 创建一个计数器对象
counter = Counter([1, 2, 2, 3, 3, 3, 4, 4, 4, 4])

# 访问元素的计数
print(counter[2]) # 输出 2
  1. defaultdict:是字典的一个子类,允许为字典的值指定默认数据类型。
1
2
3
4
5
6
7
8
9
10
from collections import defaultdict

# 创建一个默认字典,值的默认类型为 int
my_dict = defaultdict(int)

# 如果访问不存在的键,会自动初始化为默认值
my_dict['a'] += 1 # 等同于 my_dict['a'] = my_dict['a'] + 1

print(my_dict['a']) # 输出 1
print(my_dict['b']) # 输出 0,因为 'b' 不存在于字典中
  1. deque:是双端队列的实现,提供了高效的插入和删除操作,适合用于队列和栈。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
from collections import deque

# 创建一个双端队列
my_deque = deque([1, 2, 3])

# 在左侧添加元素
my_deque.appendleft(0)

# 在右侧添加元素
my_deque.append(4)

# 弹出左侧元素
left_element = my_deque.popleft()

print(my_deque) # 输出 deque([0, 1, 2, 3, 4])
print(left_element) # 输出 0
  1. namedtuple:用于创建带字段名的元组,可提高代码的可读性。
1
2
3
4
5
6
7
8
9
10
from collections import namedtuple

# 创建一个名为 'Person' 的命名元组,包含 'name' 和 'age' 两个字段
Person = namedtuple('Person', ['name', 'age'])

# 创建一个 Person 对象
person = Person(name='Alice', age=30)

print(person.name) # 输出 'Alice'
print(person.age) # 输出 30
  • classmethod somenamedtuple._make(iterable),类方法从存在的序列或迭代实例创建一个新实例

    1
    2
    3
    t = [11, 22]
    Point._make(t)
    Point(x=11, y=22)

35MATH

1.三角函数-计算正弦、余弦、正切、余切

在 Python 中,你可以使用 math 模块来进行正弦(sine)、余弦(cosine)、正切(tangent)和余切(cotangent)等数学运算。以下是它们的基本用法:

首先,确保你已经导入了 math 模块:

1
import math

然后,你可以使用以下函数进行这些运算:

  1. 正弦(sine):math.sin(x)

    正弦函数返回给定角度 x 的正弦值,其中 x 应该以弧度为单位。如果你有角度而不是弧度,你可以使用 math.radians() 函数将角度转换为弧度。

    示例:

    1
    2
    3
    4
    5
    import math

    angle_in_radians = math.radians(30) # 将角度转换为弧度
    sine_value = math.sin(angle_in_radians)
    print(sine_value)
  2. 余弦(cosine):math.cos(x)

    余弦函数返回给定角度 x 的余弦值,也需要以弧度为单位的输入。

    示例:

    1
    2
    3
    4
    5
    import math

    angle_in_radians = math.radians(45) # 将角度转换为弧度
    cosine_value = math.cos(angle_in_radians)
    print(cosine_value)
  3. 正切(tangent):math.tan(x)

    正切函数返回给定角度 x 的正切值,同样需要以弧度为单位的输入。

    示例:

    1
    2
    3
    4
    5
    import math

    angle_in_radians = math.radians(60) # 将角度转换为弧度
    tangent_value = math.tan(angle_in_radians)
    print(tangent_value)
  4. 余切(cotangent):1 / math.tan(x)

    余切函数返回给定角度 x 的余切值,可以通过 1 / math.tan(x) 来计算。

    示例:

    1
    2
    3
    4
    5
    import math

    angle_in_radians = math.radians(75) # 将角度转换为弧度
    cotangent_value = 1 / math.tan(angle_in_radians)
    print(cotangent_value)

请注意,这些函数都要求输入的角度是以弧度为单位的,因此在进行计算之前,你可能需要使用 math.radians() 函数将角度转换为弧度。这些函数返回浮点数值,表示对应的三角函数值。

2.三角函数–根据正弦、余弦、正切、余切计算角度

math 模块中的正弦、余弦、正切和余切等函数用于计算三角形中的角度,通常是通过已知边长和角度来解决三角形的问题。这些函数可以帮助你计算三角形的角度,但需要具备足够的已知信息来进行计算。

以下是一些常见的用法示例:

  1. 计算角的正弦值(Sine):

    如果你知道一个三角形的某个角的正弦值以及对边的长度,你可以使用反正弦函数 math.asin() 来计算这个角度。例如,如果你知道正弦值为 0.5,对边长度为 5,你可以这样计算角度:

    1
    2
    3
    4
    5
    6
    7
    8
    import math

    sine_value = 0.5
    opposite_side_length = 5

    angle_in_radians = math.asin(sine_value)
    angle_in_degrees = math.degrees(angle_in_radians)
    print(angle_in_degrees)
  2. 计算角的余弦值(Cosine):

    类似地,如果你知道一个角的余弦值以及邻边的长度,你可以使用反余弦函数 math.acos() 来计算这个角度。

    1
    2
    3
    4
    5
    6
    7
    8
    import math

    cosine_value = 0.866 # 余弦值
    adjacent_side_length = 5

    angle_in_radians = math.acos(cosine_value)
    angle_in_degrees = math.degrees(angle_in_radians)
    print(angle_in_degrees)
  3. 计算角的正切值(Tangent):

    如果你知道一个角的正切值以及对边的长度,你可以使用反正切函数 math.atan() 来计算这个角度。

    1
    2
    3
    4
    5
    6
    7
    8
    import math

    tangent_value = 1.732 # 正切值
    opposite_side_length = 5

    angle_in_radians = math.atan(tangent_value)
    angle_in_degrees = math.degrees(angle_in_radians)
    print(angle_in_degrees)
  4. 计算角的余切值(Cotangent):

    类似地,如果你知道一个角的余切值以及邻边的长度,你可以计算角度。

    1
    2
    3
    4
    5
    6
    7
    8
    import math

    cotangent_value = 2.0 # 余切值
    adjacent_side_length = 5

    angle_in_radians = math.atan(1 / cotangent_value)
    angle_in_degrees = math.degrees(angle_in_radians)
    print(angle_in_degrees)

上述示例假设你已知某个角的三角函数值以及相关边的长度。通常,要计算一个三角形的角,你需要已知至少一个角的三角函数值和相关边的长度,或者你需要其他相关信息,如其他已知角度或边长。然后,你可以使用这些函数来解决问题。

3.三角函数-知道边求角度

如果你已知三角形的三条边的长度,你可以使用三角函数的反函数来计算对应的角度。以下是计算三角形角度的一般步骤:

  1. 确保你有三角形的三个边的长度。
  2. 使用余弦定理计算任一角的余弦值。
  3. 使用反余弦函数 math.acos() 来计算该角的弧度值。
  4. 可选:将弧度值转换为度数。

这里是一个示例,假设你已知三角形的三边长度 abc,并且你想计算对应于边 a 的角度:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import math

# 已知边长
a = 5.0
b = 4.0
c = 3.0

# 使用余弦定理计算角A的余弦值
cos_A = (b**2 - c**2 - a**2) / (-2 * b * c)

# 使用反余弦函数计算弧度值
angle_A_radians = math.acos(cos_A)

# 将弧度值转换为度数
angle_A_degrees = math.degrees(angle_A_radians)

print("Angle A (degrees):", angle_A_degrees)

这个示例中,我们使用余弦定理计算了角 A 的余弦值,然后使用反余弦函数 math.acos() 计算了角 A 的弧度值,最后将弧度值转换为度数。

请注意,如果你想计算其他角的度数,可以通过类似的方式计算。根据需要,你可以替换 abc 的值,以计算其他角的度数。

36. Numpy

NumPy (Numerical Python) 是一个Python库,用于处理和执行科学计算和数值运算。它提供了一个强大的多维数组对象(通常称为NumPy数组或ndarray)和许多用于操作这些数组的函数。NumPy是数据科学和机器学习领域的核心工具之一,它可以用于执行各种数学、统计和数据处理任务。

以下是一些常见的NumPy功能和用法:

  1. 创建NumPy数组:使用 numpy.array() 函数可以从Python列表或元组创建NumPy数组。

    1
    2
    3
    import numpy as np

    arr = np.array([1, 2, 3, 4, 5])
  2. 数组操作:NumPy提供了各种操作数组的函数,包括索引、切片、重塑、合并和分割等。

    1
    2
    3
    4
    5
    6
    7
    # 切片操作
    subset = arr[2:4]

    # 数组合并
    arr1 = np.array([1, 2, 3])
    arr2 = np.array([4, 5, 6])
    result = np.concatenate((arr1, arr2))
  3. 数学运算:NumPy支持向量化操作,可以对整个数组执行数学运算,而不需要显式循环。

    1
    2
    3
    4
    a = np.array([1, 2, 3])
    b = np.array([4, 5, 6])

    result = a + b # 数组加法
  4. 统计和线性代数:NumPy包括许多统计函数和线性代数操作,如均值、方差、矩阵乘法等。

    1
    2
    mean = np.mean(arr)
    dot_product = np.dot(arr1, arr2)
  5. 随机数生成:NumPy提供了生成随机数的函数,可以用于模拟、实验和统计分析。

    1
    2

    random_numbers = np.random.rand(5) # 生成5个随机数
  6. 广播:NumPy允许不同形状的数组进行运算,通过广播机制自动扩展数组的维度。

    1
    2
    3
    4
    a = np.array([1, 2, 3])
    b = 2

    result = a * b # 数组与标量相乘,广播b到与a相同的形状
  7. 文件输入/输出:NumPy支持读取和写入数组数据到磁盘。

    1
    2
    np.save('data.npy', arr)  # 保存数组到文件
    loaded_arr = np.load('data.npy') # 从文件加载数组

这只是NumPy的一些功能和用法的概述。NumPy在数据科学、数值计算、机器学习等领域具有广泛的应用,因为它提供了高效的数据结构和操作,以及丰富的数学和统计函数。

1. inner与outer

numpy.inner()numpy.outer() 是 NumPy 中用于进行向量和矩阵运算的两个不同的函数,它们有不同的用途和行为:

  1. **numpy.inner()**:

    numpy.inner(a, b) 函数计算两个数组的内积(dot product)。对于一维数组,这是标准的点积运算。对于多维数组,它会将最后一个轴上的元素相乘并求和。

    1
    2
    3
    4
    5
    6
    import numpy as np

    a = np.array([1, 2, 3])
    b = np.array([4, 5, 6])

    result = np.inner(a, b) # 结果为 1*4 + 2*5 + 3*6 = 32

    对于多维数组,numpy.inner() 会按照特定的规则进行内积运算。

  2. **numpy.outer()**:

    numpy.outer(a, b) 函数计算两个数组的外积(outer product)。外积是将第一个数组的每个元素与第二个数组的每个元素相乘而得到的矩阵。

    1
    2
    3
    4
    5
    6
    import numpy as np

    a = np.array([1, 2, 3])
    b = np.array([4, 5, 6])

    result = np.outer(a, b)

    这将生成一个2D矩阵,其元素是两个输入数组中的元素相乘的结果:

    1
    2
    3
    array([[ 4,  5,  6],
    [ 8, 10, 12],
    [12, 15, 18]])

总结:

  • numpy.inner() 用于计算两个数组的内积,结果是一个标量或者按一定规则计算多维数组的内积。
  • numpy.outer() 用于计算两个数组的外积,结果是一个矩阵,其中的元素是两个输入数组中的元素相乘的结果。

2. numpy.poly

numpy.poly 是 NumPy 中的一个模块,用于处理多项式的系数和操作多项式。它提供了多种用于创建、操作和分析多项式的函数。

以下是一些 numpy.poly 模块中常用的函数和用法:

  1. **numpy.poly1d**:

    numpy.poly1d(c) 创建一个一维多项式,其中 c 是多项式的系数列表。这个函数可以将系数转换为多项式对象,从而可以进行多项式的操作。

    1
    2
    3
    4
    5
    6
    7
    import numpy as np

    coefficients = [1, 2, 3] # 多项式系数
    poly = np.poly1d(coefficients)

    # 使用多项式对象进行多项式运算
    result = poly(2) # 计算多项式在 x=2 处的值
  2. **numpy.polyadd**:

    numpy.polyadd(p1, p2) 计算两个多项式 p1p2 的和。

    1
    2
    3
    4
    5
    6
    import numpy as np

    p1 = np.poly1d([1, 2, 3])
    p2 = np.poly1d([4, 5])

    result = np.polyadd(p1, p2) # 计算 p1 + p2
  3. **numpy.polysub**:

    numpy.polysub(p1, p2) 计算两个多项式 p1p2 的差。

    1
    2
    3
    4
    5
    6
    import numpy as np

    p1 = np.poly1d([1, 2, 3])
    p2 = np.poly1d([4, 5])

    result = np.polysub(p1, p2) # 计算 p1 - p2
  4. **numpy.polymul**:

    numpy.polymul(p1, p2) 计算两个多项式 p1p2 的乘积。

    1
    2
    3
    4
    5
    6
    import numpy as np

    p1 = np.poly1d([1, 2, 3])
    p2 = np.poly1d([4, 5])

    result = np.polymul(p1, p2) # 计算 p1 * p2
  5. **numpy.polydiv**:

    numpy.polydiv(p1, p2) 计算多项式 p1 除以多项式 p2 的商和余数。

    1
    2
    3
    4
    5
    6
    import numpy as np

    p1 = np.poly1d([1, 2, 3])
    p2 = np.poly1d([4, 5])

    quotient, remainder = np.polydiv(p1, p2)

这些是 numpy.poly 模块中的一些常用函数,用于处理多项式。多项式在科学计算、工程和数据分析中经常用到,这些函数使得多项式的创建和操作变得更加方便。

3. nump.roots

numpy.roots 是 NumPy 中的一个函数,用于计算多项式的根(或零点)。给定一个多项式的系数,numpy.roots 可以返回该多项式的根。根是使多项式等于零的值。

以下是 numpy.roots 函数的用法示例:

1
2
3
4
5
6
7
8
9
import numpy as np

# 定义多项式的系数(从高次到低次)
coefficients = [1, -6, 11, -6]

# 计算多项式的根
roots = np.roots(coefficients)

print("多项式的根:", roots)

在这个示例中,我们定义了一个多项式的系数 [1, -6, 11, -6],这对应于多项式 x^3 - 6x^2 + 11x - 6。然后,我们使用 np.roots() 计算了这个多项式的根。运行这段代码会得到多项式的根:

1
多项式的根: [3. 2. 1.]

这表示多项式有三个根,分别是 3、2 和 1。

注意,多项式的次数由系数的数量确定。对于一个 n 次多项式,将需要 n+1 个系数。多项式的根可以是实数或复数,具体取决于多项式的系数。

4.numpy.polyint

numpy.polyint 是 NumPy 中的一个函数,用于对多项式进行不定积分。它接受一个多项式的系数作为输入,并返回其不定积分(即原函数)的系数。

以下是 numpy.polyint 函数的用法示例:

1
2
3
4
5
6
7
8
9
import numpy as np

# 定义多项式的系数(从高次到低次)
coefficients = [1, 2, 3]

# 计算多项式的不定积分
integral_coefficients = np.polyint(coefficients)

print("多项式的不定积分系数:", integral_coefficients)

在这个示例中,我们定义了一个多项式的系数 [1, 2, 3],这对应于多项式 x^2 + 2x + 3。然后,我们使用 np.polyint() 计算了这个多项式的不定积分的系数。运行这段代码会得到多项式的不定积分的系数:

1
多项式的不定积分系数: [0.33333333 1.         3.         0.        ]

这个结果表示多项式的不定积分系数为 [0.33333333, 1, 3, 0],这对应于不定积分的多项式 0.33333333x^3 + x^2 + 3x + C,其中 C 是积分常数。

numpy.polyint 可以帮助你计算多项式的不定积分,这在数学和工程计算中经常用到。

5.numpy.polyder

numpy.polyder 是 NumPy 中的一个函数,用于计算多项式的导数。给定一个多项式的系数,numpy.polyder 可以返回其导数的系数。

以下是 numpy.polyder 函数的用法示例:

1
2
3
4
5
6
7
8
9
import numpy as np

# 定义多项式的系数(从高次到低次)
coefficients = [3, 2, 1]

# 计算多项式的导数
derivative_coefficients = np.polyder(coefficients)

print("多项式的导数系数:", derivative_coefficients)

在这个示例中,我们定义了一个多项式的系数 [3, 2, 1],这对应于多项式 3x^2 + 2x + 1。然后,我们使用 np.polyder() 计算了这个多项式的导数的系数。运行这段代码会得到多项式的导数的系数:

1
多项式的导数系数: [6 2]

这个结果表示多项式的导数系数为 [6, 2],这对应于多项式的一阶导数 6x + 2

numpy.polyder 可以帮助你计算多项式的导数,这在微积分和工程计算中经常用到。

6.numpy.polyval

numpy.polyval 是 NumPy 中的一个函数,用于计算多项式函数在给定点的值。它接受两个参数:多项式的系数和点的值,并返回多项式在给定点的函数值。

以下是 numpy.polyval 函数的用法示例:

1
2
3
4
5
6
7
8
9
10
import numpy as np

# 定义多项式的系数(从高次到低次)
coefficients = [1, 2, 3]

# 计算多项式在 x=2 处的值
x = 2
result = np.polyval(coefficients, x)

print(f"多项式在 x={x} 处的值:{result}")

在这个示例中,我们定义了一个多项式的系数 [1, 2, 3],这对应于多项式 x^2 + 2x + 3。然后,我们使用 np.polyval() 计算了这个多项式在 x=2 处的值。运行这段代码会得到多项式在给定点的值:

1
多项式在 x=2 处的值:11

这表示多项式在 x=2 处的值为 11。

numpy.polyval 对于计算多项式函数在特定点的值非常方便,这在数学和工程计算中经常用到。

7.numpy.polyfit

numpy.polyfit 是 NumPy 中的一个函数,用于拟合多项式到一组数据点。它接受输入数据点的 x 坐标、y 坐标以及所需的多项式的次数,然后返回多项式的系数,这些系数可以用于描述拟合的多项式函数。

以下是 numpy.polyfit 函数的用法示例:

1
2
3
4
5
6
7
8
9
10
11
import numpy as np

# 输入数据点
x = np.array([1, 2, 3, 4, 5])
y = np.array([2, 3, 6, 10, 15])

# 使用 numpy.polyfit 进行多项式拟合
degree = 2 # 拟合多项式的次数
coefficients = np.polyfit(x, y, degree)

print("拟合多项式的系数:", coefficients)

在这个示例中,我们有一组数据点 (x, y),并希望用一个二次多项式来拟合这些数据点。我们通过设置 degree 变量为 2 来指定拟合多项式的次数。然后,我们使用 np.polyfit() 函数进行拟合,它返回了拟合多项式的系数。运行这段代码会得到拟合多项式的系数:

1
拟合多项式的系数: [ 1.  -1.   1.]

这表示拟合的多项式为 1*x^2 - 1*x + 1

您可以根据数据和所需的拟合多项式的次数来使用 numpy.polyfit 来拟合数据并得到多项式的系数。这在数据分析、曲线拟合等领域非常有用。

8.numpy.concatenate

numpy.concatenate 是 NumPy 中用于连接(拼接)数组的函数。它允许您将两个或多个数组沿指定的轴连接在一起,创建一个新的数组。

以下是 numpy.concatenate 函数的基本用法:

1
2
3
4
5
6
7
8
9
10
import numpy as np

# 创建两个数组
arr1 = np.array([1, 2, 3])
arr2 = np.array([4, 5, 6])

# 使用 numpy.concatenate 连接数组
result = np.concatenate((arr1, arr2))

print("连接后的数组:", result)

在这个示例中,我们首先创建了两个NumPy数组 arr1arr2,然后使用 np.concatenate() 函数将它们连接在一起。默认情况下,np.concatenate() 将数组沿着第一个轴(轴索引为0)连接。

运行这段代码会得到连接后的数组:

1
连接后的数组: [1 2 3 4 5 6]

您还可以指定连接的轴,以便在不同的方向上连接数组。例如,您可以将它们连接在行方向(轴0)或列方向(轴1)上。

1
2
3
4
5
# 在行方向上连接数组
result_row = np.concatenate((arr1, arr2), axis=0)

# 在列方向上连接数组
result_col = np.concatenate((arr1, arr2), axis=1)

numpy.concatenate 是一个非常有用的函数,可以在数据处理中用于合并不同的数据集或数组。您可以通过指定轴来控制连接的方向。

37. Calendar模块

在Python中,有一个名为calendar的标准库模块,用于处理日期和日历信息。calendar模块提供了各种函数和类,可以用于生成、格式化和操作日历信息。

以下是一些calendar模块中常用的功能和类:

  1. **calendar.month(year, month)**:

    这个函数用于生成指定年份和月份的日历。它返回一个多行字符串,表示指定月份的日历。

    1
    2
    3
    4
    5
    6
    7
    import calendar

    year = 2023
    month = 8

    cal = calendar.month(year, month)
    print(cal)

    这会生成并打印出2023年8月的日历。

  2. **calendar.month_namecalendar.day_name**:

    这两个变量是字符串列表,分别包含了月份名称和星期几的名称。例如,calendar.month_name[1] 返回 “January”,calendar.day_name[3] 返回 “Wednesday”。

  3. calendar.TextCalendar

    这是一个类,用于生成文本日历。您可以使用它来生成指定年份和月份的日历,并以文本形式输出。

    1
    2
    3
    4
    5
    6
    7
    import calendar

    year = 2023
    month = 8

    cal = calendar.TextCalendar(calendar.SUNDAY)
    print(cal.formatmonth(year, month))

    这会生成并打印出2023年8月的文本日历。

  4. calendar.HTMLCalendar

    这是一个类,用于生成HTML格式的日历。它与TextCalendar类类似,但生成的日历以HTML表格的形式呈现。

    1
    2
    3
    4
    5
    6
    7
    import calendar

    year = 2023
    month = 8

    cal = calendar.HTMLCalendar(calendar.SUNDAY)
    print(cal.formatmonth(year, month))

    这会生成并打印出2023年8月的HTML日历。

calendar模块还包括其他函数和类,用于处理日期、计算日期差异、确定星期几等。这些功能使得在Python中处理日期和日历信息变得相对容易。根据具体需求,您可以选择适合您应用程序的方法和类。

1.给定日期计算周几

calendar 模块可以帮助您计算星期几,特别是给定日期的星期几。要计算星期几,您可以使用 calendar.weekday(year, month, day) 函数,它返回一个整数,其中0代表星期一,1代表星期二,以此类推,6代表星期日。

以下是如何使用 calendar 模块计算给定日期的星期几的示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
import calendar

# 指定日期
year = 2023
month = 8
day = 27 # 日期

# 使用 calendar.weekday() 计算星期几
weekday_index = calendar.weekday(year, month, day)

# 根据索引获取星期几的名称
weekdays = ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"]
weekday_name = weekdays[weekday_index]

print(f"{year}-{month:02d}-{day:02d}{weekday_name}")

在这个示例中,我们首先指定了一个日期(2023年8月27日),然后使用 calendar.weekday() 函数计算星期几的索引。接着,我们创建了一个包含星期几名称的列表 weekdays,并根据索引获取了星期几的名称。

运行这段代码会输出:

1
2023-08-27 是 Sunday

这表示2023年8月27日是星期日。您可以根据需要更改日期来计算不同日期的星期几。

38.HTML Parser

HTMLParser 是 Python 标准库中的一个模块,用于解析HTML文档。它是一个基于事件的解析器,允许您在解析HTML文档时注册回调函数来处理不同的HTML标记和事件。

要使用 HTMLParser,您需要导入它并创建一个自定义的子类,该子类重写了 HTMLParser 中的方法,以处理HTML文档中的不同部分。以下是一个简单的示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
from html.parser import HTMLParser

# 创建一个自定义的HTML解析器子类
class MyHTMLParser(HTMLParser):
def handle_starttag(self, tag, attrs):
print(f"开始标记: {tag}, 属性: {attrs}")

def handle_endtag(self, tag):
print(f"结束标记: {tag}")

def handle_data(self, data):
print(f"数据: {data}")

# HTML文档示例
html_doc = """
<html>
<head>
<title>示例页面</title>
</head>
<body>
<h1>欢迎使用HTMLParser</h1>
<p>这是一个示例HTML文档。</p>
</body>
</html>
"""

# 创建解析器对象
parser = MyHTMLParser()

# 解析HTML文档
parser.feed(html_doc)

在这个示例中,我们首先导入了 HTMLParser 模块,并创建了一个名为 MyHTMLParser 的自定义子类,该子类继承了 HTMLParser。然后,我们在子类中重写了 handle_starttaghandle_endtaghandle_data 方法,以分别处理开始标记、结束标记和数据。

接着,我们创建了一个HTML文档的示例,并使用 MyHTMLParser 解析器对象来解析该文档。当解析器遇到HTML标记或文本数据时,将调用相应的回调函数来处理它们,然后我们在这些回调函数中打印了相应的信息。

运行这段代码会输出HTML文档中的标记和数据:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
开始标记: html, 属性: []
开始标记: head, 属性: []
开始标记: title, 属性: []
数据: 示例页面
结束标记: title
结束标记: head
开始标记: body, 属性: []
开始标记: h1, 属性: []
数据: 欢迎使用HTMLParser
结束标记: h1
开始标记: p, 属性: []
数据: 这是一个示例HTML文档。
结束标记: p
结束标记: body
结束标记: html

这个示例演示了如何使用 HTMLParser 解析HTML文档并处理其中的标记和数据。您可以根据需要进一步扩展 MyHTMLParser 类来执行特定的操作,例如提取链接、获取文本内容等。

1. handle_data

handle_dataHTMLParser 模块中的一个方法,用于处理HTML文档中的文本数据。当解析器遇到文本数据时,它会调用 handle_data 方法,并将文本数据作为参数传递给该方法。

以下是 handle_data 方法的基本用法:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
from html.parser import HTMLParser

# 创建一个自定义的HTML解析器子类
class MyHTMLParser(HTMLParser):
def handle_data(self, data):
if data.strip():
print(f"文本数据: {data}")

# HTML文档示例
html_doc = """
<html>
<head>
<title>示例页面</title>
</head>
<body>
<h1>欢迎使用HTMLParser</h1>
<p>这是一个示例HTML文档。</p>
</body>
</html>
"""

# 创建解析器对象
parser = MyHTMLParser()

# 解析HTML文档
parser.feed(html_doc)

在这个示例中,我们定义了一个自定义的HTML解析器子类 MyHTMLParser,并重写了 handle_data 方法。当解析器遇到HTML文档中的文本数据时,将调用此方法,并将文本数据作为参数传递给它。

在示例中,我们的解析器对象 parser 解析了一个包含HTML文本的示例文档。当文本数据被解析时,handle_data 方法会被调用,我们在该方法中打印了文本数据。

运行这段代码会输出文档中的文本数据:

1
2
3
文本数据: 示例页面
文本数据: 欢迎使用HTMLParser
文本数据: 这是一个示例HTML文档。

这个示例演示了如何使用 handle_data 方法来处理HTML文档中的文本数据。您可以在 handle_data 方法中执行特定的操作,例如对文本数据进行处理、提取或分析,具体取决于您的需求。

2.handle_comment

handle_commentHTMLParser 模块中的一个方法,用于处理HTML文档中的注释内容。HTML注释是一种特殊的文本标记,通常用于在HTML文档中添加注释或说明性信息,这些注释对于浏览器渲染页面时通常是不可见的。

HTMLParser 解析HTML文档时遇到注释时,它会调用 handle_comment 方法,并将注释内容作为参数传递给该方法。

以下是一个示例,演示如何使用 handle_comment 方法来处理HTML文档中的注释:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
from html.parser import HTMLParser

# 创建一个自定义的HTML解析器子类
class MyHTMLParser(HTMLParser):
def handle_comment(self, data):
print(f"注释内容: {data}")

# HTML文档示例
html_doc = """
<html>
<head>
<title>示例页面</title>
</head>
<body>
<h1>欢迎使用HTMLParser</h1>
<!-- 这是一个示例注释 -->
<p>这是一个示例HTML文档。</p>
<!-- 这是另一个示例注释 -->
</body>
</html>
"""

# 创建解析器对象
parser = MyHTMLParser()

# 解析HTML文档
parser.feed(html_doc)

在这个示例中,我们创建了一个自定义的HTML解析器子类 MyHTMLParser,并重写了 handle_comment 方法。当解析器遇到HTML文档中的注释时,handle_comment 方法会被调用,并将注释内容作为参数传递给它。

运行这段代码会输出HTML文档中的注释内容:

1
2
注释内容: 这是一个示例注释
注释内容: 这是另一个示例注释

这个示例演示了如何使用 handle_comment 方法来处理HTML文档中的注释。您可以在 handle_comment 方法中执行特定的操作,例如记录注释或提取注释中的信息,具体取决于您的需求。

第三方库

1.二维码(myqr)

MyQR 是一个用于生成二维码的 Python 库,它提供了许多功能,可以用于生成不同类型的二维码,包括包含链接、文本、名片等多种类型的二维码。以下是关于如何使用 MyQR 的详细介绍:

  1. 安装 MyQR:

    首先,您需要安装 MyQR 库。您可以使用以下命令来安装:

    1
    pip install myqr
  2. 生成包含链接的二维码:

    下面是一个示例,演示如何生成包含链接的二维码:

    1
    2
    3
    4
    5
    6
    7
    8
    from MyQR import myqr

    # 设置参数
    url = "https://www.example.com" # 替换为您的链接
    output_file = "example_qrcode.png" # 输出的二维码文件名

    # 生成二维码
    myqr.run(url, save_name=output_file)
  3. 生成包含文本的二维码:

    您可以使用 myqr.run() 函数生成包含文本的二维码。例如:

    1
    2
    3
    4
    5
    6
    7
    8
    from MyQR import myqr

    # 设置参数
    text = "Hello, World!" # 替换为您的文本
    output_file = "text_qrcode.png" # 输出的二维码文件名

    # 生成文本二维码
    myqr.run(words=text, save_name=output_file)
  4. 生成名片二维码:

    MyQR 也支持生成包含名片信息的二维码,用于联系信息共享。以下是一个示例:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    from MyQR import myqr

    # 设置名片信息
    name = "John Doe"
    title = "Software Engineer"
    phone = "123-456-7890"
    email = "john.doe@example.com"

    # 输出的名片文件名
    output_file = "business_card_qrcode.png"

    # 生成名片二维码
    myqr.run(
    f"BEGIN:VCARD\nVERSION:3.0\nFN:{name}\nORG:{title}\nTEL:{phone}\nEMAIL:{email}\nEND:VCARD",
    save_name=output_file
    )
  5. 更多选项:

    MyQR 还提供了许多其他选项,用于自定义生成的二维码的外观,包括颜色、形状、边距等。您可以在生成二维码时使用这些选项来满足您的需求。

    您可以查看 MyQR 的官方文档以了解更多详细信息和选项:MyQR 官方文档

这些示例涵盖了一些常见的用法,但 MyQR 还具有更多功能和选项,可以根据您的具体需求生成不同类型和样式的二维码。希望这个介绍能帮助您入门使用 MyQR 库。


Python学习杂记
http://www.okko.tk/2023/09/03/Python学习杂记/
作者
ZhJy
发布于
2023年9月3日
许可协议