第01节 Python的基础语法

1.Python语言

1.1 语言特点和风格

python 复制代码
一、语言特点
1.面向对象:面向对象、跨平台性好的解释性语言。
2.强大的标准库:语言核心包括数字、字符串、列表、字典、文件等常用类型和函数,
  标准库包括系统管理、网络通信、文本处理、数据库接口、图形系统、XML处理等额外功能。
3.社区提供大量第三区模块:覆盖科学计算、人工智能、机器学习、Web开发、数据库接口、图形系统等领域。
4.文件命名:文件命名不能出现"-",不然后面导包导不进去。
# 版本方面
# python2.0:不支持中文(不推荐)
# python2.6/2.7:过渡版本,支持python2.0以及部分python3.0语法和函数
# python3.0:主流版本,支持中文,不兼容python2.0。

二、语言风格
# 单行注释采用"#"开头
"""
多行注释采用三个单引号' ' '(推荐),或者三个双引号" " "
"""
'''
Python 的代码块不使用大括号 {} 来控制类,函数以及其他逻辑判断。
python 最具特色的就是用缩进来写模块。建议只用空格(不要混用空格和Tab)。
缩进的空白数量是可变的,但是所有代码块语句必须包含相同的缩进空白数量,这个必须严格执行。
'''
# 正确示例如下:
if age >= 18:
    print("你已成年")
else:
    print("你还未成年")

# 错误示例如下:
name = "小王"
    print("多行注释") #错误,缩进导致编译报错

# TODO 注释:用于标记需要去做的工作
# TODO(作者/右键) 需要做的功能xxxx

不使用python命令直接执行".py"文件的方法:使用 shebang 符号 "#!",示例如下:
#! /usr/bin/python3
./xxx.py

# 代码顺序结构示意图:
1.shebang
2.import 模块
3.全局变量
4.函数定义
5.执行代码

pycharm工具快捷键
# alt + shift + 鼠标左键:纵向选择
# ctrl + shift + F10:运行当前python文件
# ctrl + enter:快速向下插入一行
# alt + P:启用通义灵码快捷键
# ctrl + D:快速复制当前行
# ctrl + shift + ↑/↓:快速向上/向下移动当前行

1.2 关键字与代码规范

python 复制代码
代码规范官方文档:https://peps.python.org/pep-0008/。常用的代码规范如下:
# 每个缩进级别使用4个空格,Python不允许混合使用制表符和空格进行缩进。
# 每行限制为最多79个字符。
# 核心Python发行版中的代码应始终使用UTF-8
# import 通常应该在单独的行上,多个导入的分组顺序:标准库导入;相关第三方导入;本地应用程序/库特定的导入。
# "__all__"之类的字段放在doc注释之后,import语句之前。
# 单引号字符串和双引号字符串是一样。
# 代码后写注释时,注释应由至少两个空格分隔 声明。它们应该以 # 和单个空格开头。
# 切勿使用字符 'l' (小写字母el),'O' (大写 字母oh) 或 "i" (大写字母眼睛) 作为单个字符变量 名字。
# 类名通常应使用CapWords约定。
# 常量名: 用下划线分隔单词的大写字母。
# 方法名、变量名:应为小写,单词之间用 必要时下划线以提高可读性。
# 函数和方法参数:总是使用self作为实例方法的第一个参数。总是使用cls对于类方法的第一个参数。
关键字
# python中的关键字
import keyword
print(keyword.kwlist)  # 打印所有的关键字
['False', 'None', 'True', 'and', 'as', 
 'assert', 'async', 'await', 'break', 'class', 
 'continue', 'def', 'del', 'elif', 'else', 
 'except', 'finally', 'for', 'from', 'global', 
 'if', 'import', 'in', 'is', 'lambda', 
 'nonlocal', 'not', 'or', 'pass', 'raise', 
 'return', 'try', 'while', 'with', 'yield']
pass: 开发程序时不希望立刻编写分支内部的代码,可以使用pass作为一个占位符来保证代码结构正确。类似于java注释中的 TODO 。
global: 全局变量,定义在函数体外可以省略此关键字,全局变量不允许直接修改。
    如果需要修改,则需要在函数内部使用golabal关键字声明后再修改。命名时以"g_"或"gl_"做前缀。
is: 判断对象的地址是否相同,相当于id(x)==id(y)。与"=="不同的是,"=="比较的是值,"is"比较的是地址。

2.数据类型

2.1 变量

python 复制代码
# 变量:只允许使用数字、字母、下划线,且不能以数字开头。
# 变量严格区分大小写:name和Name是两个变量。
# 变量的命名规则:一个单词用小写字母,多个单词用"_"连接,驼峰命名法也可以但不推荐。
# 变量在函数中的传递:调用函数时,本质上传递的是实参对应的数据引用而非实参本身,即传递的是实参的内存地址。

# 变量赋值(python在运行时才推导出变量的类型)
# 类型:int,示例:
age = 18
# 类型:float,示例:
float_number = 3.14
# 类型:bool,有两个值:True和False。当用数字表示布尔类型时,遵循"非0即真"的原则。示例:
boolean = True
# 类型:str,示例:
name = "小王"        
# 类型:complex。等价于 2 + 3j,示例:
d = complex(2, 3)    # 输出: (2+3j)
# 其他
type():判断变量类型的函数,比如:type(name)返回str。
print(isinstance(name, str)):判断变量name是否是str类型,返回True或False。
print(name, age, float_number, boolean) #输出:小王 18 3.14 True

2.2 列表

python 复制代码
# 列表(List):是可变的(mutable),创建后可以修改(增删改元素)。
numbers = [1, 2, 3, 4, 5]
numbers.append(6)
print(numbers)

# 创建列表
numbers = []      # 初始化一个空列表
numbers = list()  # 列表创建或其他类型转化成列表,类似于int(xxx)
numbers = [10, True, 'abc', 10.3]
# 其他方式创建列表,语法:[表达式 for 变量 in 列表]
numbers = [i for i in range(1, 10)]
print(numbers)  #输出:[1, 2, 3, 4, 5, 6, 7, 8, 9]
numbers = [i**2 for i in range(1, 10)]
print(numbers)  #输出:[1, 4, 9, 16, 25, 36, 49, 64, 81]
name_list = ["zhaoyi", "zhaoyi", "qianer", "sunsan", "lisi", "wangwu"]

# 取值和取索引
name = name_list[0]   # 获取第一个元素
name = name_list[-1]  # 获取倒数第一个元素
idx = name_list.index("zhaoyi")  # 如果字符串不存在则报错,存在多个则返回第一个的下标

# 添加
# 向指定位置插入数据,如果此位置有数据则会后移,如果此位置大于数组最大长度,则会追加到数组最后一位
name_list.insert(0, "赵公明")
# 向数组末尾追加数据,如果追加的数据类型是列表,则会把列表当成一个整体追加到末尾。
name_list.append("wangxiaoer")
# 向数组末尾追加数据,如果追加的数据类型是列表,则会把列表中的每个元素分表追加到末尾。
tmp_list = ["孙悟空", "猪八戒"]
name_list.extend(tmp_list)
name_list += tmp_list  # 列表之间的"+="操作本质上是在执行extend()方法,不会修改变量的引用。但"+="不能拆开,否则相当于普通的赋值语句。

# 删除:如果元素不存在则会报错
name_list.remove("wangwu")
# 把list当成栈操作,移除并返回最后一个元素
name_list.pop()  
name_list.pop(2)   # 移除指定下标对应的元素
name_list.clear()  # 清空数组中所有的内容,清空后name_list = []
del name_list[0]   # 删除指定的元素
del name_list      # 删除整个数组,与clear不同的是,del会从内存中摧毁整个list,name_list变成未定义的属性

# 修改
name_list[1] = "wangzhaojun"

# 查询与统计
len(name_list):统计列表中的元素总数。
name_list.count("zhaoyi"):统计某个元素出现的个数。
'xx' in name_list:xx元素是否在列表中出现过,返回True或False。
'xx' not in name_list:xx元素是否没在列表中出现过,返回True或False。
print(f'列表的值是:{name_list}')

# 对列表排序
sortedNumbers = sorted(numbers)
name_list.reverse():反转,会改变原列表值的顺序
# name_list[::-1]也可以进行反转,但此反转不会改变原列表值的顺序
name_list.sort():排序,默认升序
name_list.sort(reverse=True):排序,设置为倒序

# 列表的遍历:
for name in name_list:
    print("我的名字是 %s" % name)
for i in range(0, len(name_list))):
    print(f"我的名字是 {name_list[i]}}")
# 或者用while i<len(name_list), 与for类似。

# 过滤列表:用于过滤序列,保留满足条件的元素
evenNumbers = list(filter(lambda x: x % 2 == 0, numbers))

# 映射列表:用于对可迭代对象的每个元素应用一个函数,生成新的结果
squared = list(map(lambda x: x**2, numbers))

# 列表的嵌套:二维数组
name_list = [
    ['赵毅', '倩儿', '孙山'], 
    ['李思', '周武']
]
# 查找
print(name_list)        # 整个列表嵌套:[['赵毅', '倩儿', '孙山'], ['李思', '周武']]
print(name_list[1])     # 第二行列表:['李思', '周武']
print(name_list[1][0])  # 第二行第一列的值:李思
# 遍历与列表相同,不过需要两个for循环依次变量外层和内层。

2.3 元组

python 复制代码
# 元组(Tuple):是不可变的(immutable),创建后不能修改(无法增删改元素),适合作为常量或字典的键。
empty_tuple = ():定义空元组
t_tuple = tuple():定义或转化为元组
single_tuple = (5,):定义只包含一个元素的元组。注意:"single_tuple=(5)"的类型是int,它不是元组。
point_tuple = (1, 2, 'abc')
print(point_tuple[0])

# 元组的操作和列表(数组)一样:此处省略了很多方法....
tuple(name_list):将列表转化成元组。
list(point_tuple):将元组转成列表。

# 使用枚举函数,语法:enumerate(可迭代对象, start=0)
for index, item in enumerate(numbers):
    print(f"{index}: {item}")
    
# 注意:元组作为函数返回值或接收元组返回值时,"("和")"可以省略。示例如下:
temp, wetness = measure()  # measure()返回值:return temp, wet。注意接收元组的变量个数要和返回值中的元组中元素的个数一致。
# 变量之间的交换简洁写法:a,b = (b,a) 或 a,b = b,a

2.4 字典

python 复制代码
# 字典:key可以是字符串、数字或其他类型,字典保存的数据是无序集合。
person = {"name": "王昭君", "age": 18}
print(person)  #输出:{'name': '王昭君', 'age': 18}
print(person["name"] +  "今年" + str(person["age"]) + "岁。")
# 快速创建字典,语法:{key: value for key, value in 列表}
squareDict = {i: i**2 for i in range(1, 10)}
# 字典的创建
dict.fromkeys(keys, value):返回一个新的字典,其中的键来自指定的 keys(嵌套除外),所有键的值为指定的 value。
# 字典的复制
new_dict = dict.copy():返回一个新字典,内容与原字典相同,修改新字典不会影响到原字典值(字典嵌套除外)。

# 取值
my_name = person["name"]      # 此用法:key不存在时会报错
my_name = person.get("name")  # 此用法:key不存在时会返回 None(类型:<class 'NoneType'>)。
all_keys = person.keys()      # 获取所有的key
all_vals = person.values()    # 获取所有的value
all_item = person.items()     # 所有(key, value)元素组列表

# 增加/修改
person["height"] = 1.65    # 如果key不存在则会添加
person["name"] = "杨玉环"   # 如果key存在则会修改
person.setdefault("name", "李白")  # 如果key存在则不会修改,key不存在则会新建键值对
temp_dict = {"sex": "男", "weight": "60"}
person.update(temp_dict)    # 将字典temp_dict合并到字典person。

# 删除
del person["name"]  # 如果key不存在则程序会报错
person.pop("name")  # 如果key不存在则程序会报错
person.popitem()    # 随机删除一个键值对,如果字典为空调用此方法会报错
person.clear()      # 清空字典
del person          # 摧毁整个person字典

# 字典的遍历
for key in person:
    print("%s - %s" % (key, person[key]))
for key in person.keys():
    print("%s -- %s" % (key, person[key]))
for val in person.values():
    print("value=%s" % val)
for item in person.items():
    print("%s --- %s" % (item[0], item[1]))
for key, value in person.items():
    print("%s --- %s" % (key, value))

2.5 字符串

python 复制代码
# 字符串本质上是多个字符组成的数组,可以用数组的方式获取单个字符
# 字符串的定义格式
# (1) 单引号形式。示例:s1 = 'abc'
# (2) 双引号形式。示例:s2 = "abc"
# (3) 三引号形式。示例:s3 = '''abc'''或s3 = """abc""", 三引号形式可以换行。

# 字符串拼接
first = "沉鱼落雁人已去,"
second = "空余悲秋西风凉。"
print(first + second)

# 字符串格式化
# %s: 字符串。
# %d: 有符号十进制整数。%06d: 输出的整数显示位数,不足的地方用0补全。
# %f: 浮点数。%.02f: 小数点后只显示两位。
# %%: 输出%。
hisName = "霍去病"
hisAge = 22
print(f"他是{hisName},封狼居胥时年{hisAge}岁。")
print("他是%s,封狼居胥时年%d岁。" %(hisName, hisAge))

# 示例字符串
word_str = "I am Amily, I am playing a game."
len(word_str):统计字符串长度
word_str.count("am"):统计某个字符串出现的次数,如果没有则返回 0。
word_str.index("abc"):统计某个子字符串出现的位置,如果找不到则会报错

# 判断类方法
word_str.isspace(): 是否只包含空白字符,包括:空格、\r、\m、\t等等。
word_str.isalpha(): 是否包含字符且所有字符都是字母
word_str.isalnum(): 是否包含字符且所有字符都是数字或字母
word_str.isdecimal(): 是否只包含数字,全角数字。注:不能判断小数。
word_str.isdigit(): 是否只包含数字,全角数字、(1)、\u00b2。注:不能判断小数和负数。
word_str.isnumeric(): 是否只包含数字,全角数字、(1)、\u00b2、汉字数字。注:不能判断小数和负数。
word_str.istitle(): 是否为标题,每个单词的首字母是否都大写
word_str.islower(): 是否每个字符都是小写
word_str.isupper(): 是否每个字符都是大写

# 比较方法或方式
is: 比较是否为同一个对象,类似于Java中比较内存地址。字符串长度大于4096时会在堆内存中开辟新地址,两个字符串不会相等。
==: 比较字符串内容是否相等,无论字符串长度长度。原理:先比较长度,再比较hash,再比较内容。
# 示例如下:
print(str1 == str2)  # 比较内容
print(str1.lower() == str2.lower())  # 转化成小写字母后比较
print(str1.upper() == str2.upper())  # 转化成大写字母后比较
print(str1.casefold() == str2.casefold())  # 比较字符串不区分大小写
算数运算符:根据ASCII的顺序进行比较
print("apple" <= "banana")   # True,按ascii序比较
re.fullmatch():模式匹配,正则匹配
示例如下:
import re
pattern = r"Python 3\.\d+\.\d+"
print(bool(re.fullmatch(pattern, "Python 3.9.0")))  # True
print(bool(re.fullmatch(pattern, "Python 3.8.5")))  # True
# 特殊字符的比较:德语
print("straße".casefold() == "STRASSE".casefold())  # True

# 查找和替换方法
word_str.startswith(str): 检查字符串是否以str开头。
# 示例如下:
print("Hello world".endswith("world"))          # True,区分大小写
print("Hello world".endswith(("world", "CC")))  # 支持元组,有一个匹配则返回True
word_str.endswith(str): 检查字符串是否以str结尾。
print("Hello world".startswith("Hello"))        # True,区分大小写
print("HELLO WORLD".startswith(("HE", "AA")))   # 支持元组,有一个匹配则返回True
# find()方法的start和end的范围是"包左不包右的",即数学上的"[start, end)"。
word_str.find(str, start=0, end=len(string)): 检查子串并返回索引值,如果字符串中没有此子串则返回-1。
word_str.rfind(str, start=0, end=len(string)): 类似于find(),不过从右边开始查找,查找最后一次出现的子串。
word_str.index(str, start=0, end=len(string)): 类似于find(),不过查找不到会报错。
word_str.rindex(str, start=0, end=len(string)): 类似于find(),不过右边开始查找。
# replace()会返回新的字符串,不会修改原有字符串
word_str.replace(old_str, new_str, num=string.count(old_str)): 把字符串中的old_str替换成new_str,如果指定num,则替换次数不超过num次。

# 文本对齐
word_str.ljust(width, fillchar): 使字符串左对齐,总长度变成width,不足的宽度用fillchar字符代替。
word_str.rjust(width, fillchar): 使字符串右对齐,总长度变成width,不足的宽度用fillchar字符代替。
word_str.center(width, fillchar): 使字符串中间对齐,总长度变成width,不足的宽度用fillchar字符代替。

# 去除空白符
word_str.lstrip(): 去除字符串左边(开头)的所有空白符。
word_str.rstrip(): 去除字符串右边(末尾)的所有空白符。
word_str.strip(): 去除字符串两边(开始和末尾)的所有空白符。

# 拆分和连接
word_str.split(str, num): 以str拆分字符串为(num+1)个子串。str为可选项,不传值则默认为"\r,\t,\n,空格";num为可选项,拆分后的长度小于num会报错。
# 注意:str1.split('')会报错:ValueError: empty separator。不允许使用''拆分,因为字符串本身就是数组。
word_str.splitlines(): 按照"\n"进行拆分并返回一个数组。
str.join(list): 以str作为分隔符连接list中所有的字符串并合并为一个新字符串,参数只能是容器。
word_str.partition(str): 把字符串拆分为3个元素的元素(str前面, str, str后面),str不存在时会拆分成(word_str, '', '')。
word_str.rpartition(str): 类似于partition(),不过是从右边拆分。

# 字符串/列表/元组的切片,语法:str[开始索引:结束索引:步长],正序时步长默认是1,倒序时不确定(尽可能写上步长)
# 字符串本质上是数组,正序时索引从0开始,倒序时索引从-1开始。
num_str = "0123456789"
# 1.截截取子字符串:"2345"
new_str = num_str[2:6]
# 2.截截取子字符串:"23456789"
new_str = num_str[2:]
# 3.截截取子字符串:"012345"
new_str = num_str[0:6]
# 4.截取完整的字符串
new_str = num_str[:]
new_str = num_str[::]
# 5.从开始位置到结束(包括最后一位),每隔一个字符截取字符串,即:"02468"
new_str = num_str[::2]
# 6.从索引 1 开始,每隔一个取一个,即:"13579"
new_str = num_str[1::2]
# 7.截取从2至倒数第一位(不包含)的字符串,即:"2345678"
new_str = num_str[2:-1]
# 8.截取字符串末尾两个字符,即:"89"
new_str = num_str[-2:]
# 9.字符串的逆序,即:"9876543210"
new_str = num_str[::-1]
# 10.字符串的逆序+每个一步截取一个。即:"97531"
new_str = num_str[-1::-2]
print(new_str)

# 字符串的本质:
# (1) 当字符串长度小于等于4096时,字符串保存在常量池中且只保留一份,其他相同值的字符串引用都指向此地址;
# (2) 当字符串长度大于4096时,每个字符串都会在堆内存中重新开辟空间,各自创建一个新的字符串。
str1 = 'a' * 4096
str2 = "a" * 4096
print(id(str1), id(str2))   # 2457305402496 2457305402496
print(str1 is str2)         # True,比较内存地址
print(str1 == str2)         # True,比较内容
str1 = 'a' * 4097
str2 = "a" * 4097
print(id(str1), id(str2))   # 2593005936832 2593005940992
print(str1 is str2)         # False,比较内存地址
print(str1 == str2)         # True,比较内容
# 拼接方法的比较
str1 = "abc"
str3 = "".join(['a', 'b', 'c'])  # 新对象
print(id(str1), id(str3))   # 2582459675216 2582459683536
print(str1 is str2)         # False,比较内存地址
print(str1 == str3)         # True,比较内容

2.6 集合(Set)

python 复制代码
# set的特点:元素是无序的且元素值是唯一的

# 1.set的创建
set1 = set()
set2 = {12, 'aa', True, '45'}
# 此种方式创建的是一个空字典而非一个空集合,打印集合类型即可验证
set3 = {}
print(type(set1), type(set2), type(set3))

# 2.set的添加元素
set1.add('abc')

# 3.set的删除元素
set1.remove('abc')

2.7 容器类型的公共操作

python 复制代码
# +:合并,适用于:字符串、列表、元组
# *:复制,适用于:字符串、列表、元组
# in/not in:元素是否存在,适用于:字符串、列表、元组、字典、集合
# max():返回容器中的最大值,适用于:字符串、列表、元组、字典、集合
# min():返回容器中的最小值,适用于:字符串、列表、元组、字典、集合
# len():返回容器的长度或大小,适用于:字符串、列表、元组、字典、集合

# +:合并,适用于:字符串、列表、元组
print('abc' + 'def')                # abcdef
print(['a', 'b', 'c'] + [4, 5, 6])  # ['a', 'b', 'c', 4, 5, 6]
print(('a', 'b', 'c') + (4, 5, 6))  # (1, 2, 3, 4, 5, 6)

# *:复制,适用于:字符串、列表、元组
print('-' * 2)              # --
print(['a', 2, 3.0] * 2)    # ['a', 2, 3.0, 'a', 2, 3.0]
print(('a', 2, 3.0) * 2)    # ('a', 2, 3.0, 'a', 2, 3.0)

# in/not in:元素是否存在,适用于:字符串、列表、元组、字典、集合
print('abc' not in 'abcdef')            # False
print('a' in ['ab', 'cde', 1, 2.0])     # False
print(1 in {'ab', 'cde', 1, 2.0})       # True
print('a' in {'a': 1, 'b': 2, 'c': 3})  # True
print(1 in {'ab', 'cde', 1, 2.0})       # True

# max()/min():返回容器中的最大值,适用于:字符串、列表、元组、字典、集合
print(max('abcdef'))    # f,字符串的最大值是根据字母的ASCII码进行排序
print(max([1, 2, 3]))   # 3
print(max(('ab', 'cd', 'abc'))) # cd
print(max({'ab': 1, 'cd': 2, 'abc': 3}))  # cd
print(max({'ab', 'cd', 'abc'})) # cd

# len():返回容器的长度或大小,适用于:字符串、列表、元组、字典、集合
print(len('abcdef'))                # 6
print(len([1, 2, 3]))               # 3
print(len(('ab', 'cd', 'abc')))     # 3
print(len({'ab': 1, 'cd': 2, 'abc': 3}))  # 3
print(len({'ab', 'cd', 'abc'}))     # 3

2.8 推导式

python 复制代码
"""
推导式:也叫解析式,python特有语法,用于简化代码编写,适用于:列表、元组和字典
格式1:变量名 = [表达式 for in 容器类型]
格式2:变量名 = [表达式 for in 容器类型 if 判断条件]
格式3:变量名 = [表达式 for in 容器类型 for in 容器类型]
"""

# 格式1:变量名 = [表达式 for in 容器类型]。示例:定义0~9的数字列表
list1 = [i for i in range(10)]
# 推导过程:
list1 = []
for i in range(10):
    list1.append(i)
# ==> 赋值表达式:list1 = for i in range(10),list1存取所有的i值
# ==> 转化成数组:list1 = [i for i in range(10)]

# 格式2:变量名 = [表达式 for in 容器类型 if 判断条件]。示例:定义0~9的奇数列表
list2 = [i for i in range(10) if i % 2 != 0]
list2 = [i for i in range(0, 10, 2)]
# ==> 推导过程:
list2 = []
for i in range(10):
    if i % 2 != 0:
        list2.append(i)
# ==> 赋值表达式:list2 = for i in range(10),list2存取所有的i值
# ==> 转化成数组:list2 = [i for i in range(10) if i % 2 != 0]

# 格式3:变量名 = [表达式 for in 容器类型 for in 容器类型]
"""
# result = [expression for item1 in iterable1 for item2 in iterable2]
# 等价于:
result = []
for item1 in iterable1:
    for item2 in iterable2:
        result.append(expression)
"""
# 生成笛卡尔积(所有组合):生成两个列表的所有可能组合
colors = ['红', '绿', '蓝']
sizes = ['S', 'M', 'L']
# 生成所有颜色和尺码的组合:[('红', 'S'), ('红', 'M'), ('红', 'L'), ('绿', 'S')...]
combinations = [(color, size) for color in colors for size in sizes]
# 生成乘法表:二维数组
multiplication_table = [[i * j for j in range(1, 6)] for i in range(1, 6)]
# 生成二维网格坐标(3行4列):[(0, 0), (0, 1), (0, 2), (0, 3), (1, 0), (1, 1)...]
coordinates = [(x, y) for x in range(3) for y in range(4)]
# 扩展:字典/集合
set1 = {i for i in range(10)}  # 集合set
dict2 = {i: i * i for i in range(10)}  # dict
dict3 = {i: i * i for i in range(10) if i % 2 != 0}  # dict

# 扩展:元组
# 此方式生成的是一个生成器表达式,生成器表达式是一个惰性求值的表达式,只有在使用时才会计算结果,且只能遍历(用)一次
set1 = (i for i in range(10))
# 元组的推导式比较特殊,需要经过tuple()进行转化,如下:
set2 = tuple(i for i in range(10))  # (0, 1, 2, 3, 4, 5, 6, 7, 8, 9)

2.9 运算赋值与转义符号

python 复制代码
# 运算符执行顺序:(),x[i],x.attribute,**,~,正负号,*/+-,>>或<<,&^|,比较,is/in/not/and/or,逗号。
+-*/:加减乘除。
//:取整除,返回除法的整数部分
%:取余数,取模。
**:幂,次方。比如:2**3=8。

# 加法:字符串+字符串
word_str = "hello " + "world"
# 加法:元组+元组
(1, 2)+(3, 4)  # 结果:(1, 2, 3, 4)
# 加法:列表+列表
[1, 2]+[3, 4]  # 结果:[1, 2, 3, 4]
# 乘法:字符串*数字
"-" * 10  # 表示显示10个"-",打印结果:----------。
# 乘法:列表*数字
[1, 2]*3  # 结果:[1, 2, 1, 2, 1, 2]
# 乘法:元组*数字
(1, 2)*3  # 结果:(1, 2, 1, 2, 1, 2)
# 除法:除法遇到除不尽的结果时(如:10/3),结果默认保留16位,前15位正确,第16位不确定。

# 比较(关系)运算符
==:相等
!=:不相等
>:大于
<:小于
>=:大于或等于
<=:小于或等于

# 赋值运算符
=:赋值运算符。示例:c=a+b; e,f=3,4。
+=:加法赋值运算符。示例:c+=a 等效于 c=c+a。
-=:减法运算符。示例:c-=a 等效于 c=c-a。
*=:乘法赋值运算符。示例:c*=a 等效于 c=c*a。
/=:除法赋值运算符。示例:c/=a 等效于 c=c/a。
//=:取整值赋值运算符。示例:c//=a 等效于 c=c//a。
%=:取模(余数)赋值运算符。示例:c%=a 等效于 c=c%a。
**:幂赋值运算符。示例:c**=a 等效于 c=c**a。

# 逻辑运算符
and: 与,相当于"&&"。示例:if age>0 and age<18 。
or:  或,相当于"||"。示例:if score<60 or score>90。
not: 非,条件不满足。 示例:if not is_true 。# is_true=False时if语句执行

# 转义符号
\\:反斜杠符号。
\':单引号。
\":双引号。
\n:换行。
\t:横向制表符。
\r:回车符。

# 成员运算符
in: 是否存在,存在则返回True否则返回False。
not in: 是否不存在,不存在则返回True否则返回False。
# 以下是示例:
字符串:"a" in "abcd"  # True
列表:"1" in [1, 2, 3]  # False
字典:"name" in {"name": "zhangsan", "age": 20}  # True,只比较key。

# 类似于三元运算符的操作
name = word_str if len(word_str) > 0 else "other_str"

3.流程控制

3.1 if 判断语句

python 复制代码
# 条件语句,语法:if 语句: else:
score = 85
if score >= 90:
    print("你很优秀")
elif score >= 60:
    print("你及格了")
else:
    print("你没及格,下次加油")

3.2 while 循环语句

python 复制代码
# 循环语句:while,语法:while 条件:
while age < 18:
    print(f"你还未成年,今年{age}岁")
    age += 1
# 整个for循环执行完后执行else,如果通过break退出了循环则不会再执行else后的代码。
else:
    # 其他逻辑

3.3 for 循环语句

python 复制代码
# 循环语句:for,语法:for 循环变量 in 循环列表:
for i in range(1, 10):
    print(i)
# 循环语句:for,语法:for 循环变量 in 循环列表:# 业务代码 else: # 业务代码
find_name = "lisi"
for name in ["zhang", "lisi", "wang"]:
    if name == find_name:
        print("找到了[%s]" % find_name)
        break
# 整个for循环执行完后执行else,如果通过break退出了循环则不会再执行else后的代码。
else:
    print("没有找到[%s]" % find_name)

# 关键字[break]:条件满足时,跳出整个循环。
# 关键字[continue]:条件满足时跳出当次循环,继续执行下一次循环。
    
# range() 函数
r = range(1, 5)     # 范围:[1, 5), 即:[1,2,3,4], 步长默认为1
r = range(5)        # 等同于range(0, 5), 即:[0,1,2,3,4], 起始值默认是1, 步长默认是1
r = range(5, 2)     # 范围:[5, 2), 从5到2,很显然没有值
r = range(0, 5, 2)  # 范围:[0, 5), 步长为2, 即:[0,2,4]
r = range(5, 1, -1) # 范围:[5, 1)倒序, 步长为-1, 即:[5,4,3,2]
for i in r:
    print(i, end=',')

3.4 死循环

python 复制代码
# 死循环的方式
(1) while 1==1:
(2) while 1: #即条件为"0,'',None"这三个值外,默认都是True,所以会死循环

4.函数

4.1 函数的定义与使用

python 复制代码
# 导入模块,可以使用模块中的方法
import math
print(math.sqrt(16))

# 函数定义(defined):def 函数名(参数列表):
def add(a, b): return a + b
# 函数调用:函数定义必须在使用之前
sum = add(1, 2)

# 函数定义:def 函数名(参数列表指定缺省值):
def print_info(a, b=0, c=0):  # 如果传递b,则b的值默认为0
# 函数调用:如果想给具体的缺省参数传值,需要指定参数名
print_info(10, c=20)

# 函数定义:def 多值函数名(*args, **kwargs): 一个"*"表示可以接收一个元组,两个"**"表示可以接收一个字典。
def multi_val(*nums, **dict_val):  # 具体的逻辑
# 函数调用:python会自动识别参数是元组还是字典
multi_val(1,2,3, name="zhaoyi", age=18)
# 函数调用:如果想指定对应的元组和字典,则需要拆包
gl_nums = {1, 2, 3}
gl_dict = {"name": "zhangsan", "age": 19}
multi_val(*gl_nums, **gl_dict)

# 函数的返回值:返回一个值的情况
sum = add(1, 2)
# 函数的返回值:返回多个值的情况
def calc(a, b):
    sum = a + b
    sub = a - b
    mul = a * b
    div = a / b
    return sum, sub, mul, div
# 返回值:一个变量接收(<class 'tuple'>)
val = calc(10, 5)
# 返回值:多个变量接收
a, b, c, d = calc(10, 5)
print(val, type(val))
print(a, b, c, d)

# 函数的说明文档:一般写在函数的第一行且必须是三引号形式。可以通过help()或ctrl+q查看函数的帮助文档。
def add_calc(a, b):
    """
    功能描述:接收两个整数,计算它们的值
    :param a: 第一个整数
    :param b: 第二个整数
    :return: 返回相加的结果
    """
    return a + b
# 查看函数的帮助文档
help(add_calc)

# 文件操作,语法:with open("文件名", "模式") as 文件对象:
with open("text.txt", "w") as file:
    file.write("hello world!")
with open("text.txt", "r") as file:
    print(file.read())

4.2 变量的作用域

python 复制代码
"""
变量分为:全局变量和局部变量。变量的使用遵循就近原则,即先用最近的变量,找不到再找父类,一直往上找,直到object父类。
全局变量的定义:global 变量名
局部变量的定义:变量名 = 值
"""

global a
global c
a = 10
b = 10
c = 10

def first_func():
    # a虽然是全局变量,但函数内部重新定义a,a会被认为是函数内的局部变量,局部变量的修改不会影响全局变量的值
    a = 20
    # b是函数外的局部变量,函数内部重新定义b,b会被认为是函数内部的局部变量,函数内局部变量的修改不会影响函数外局部变量的值
    b = 20
    # 修改全局变量:必须使用global关键字后赋值才能修改全局变量的值
    global c
    c = 20
    print(f'函数方法重新赋值后a的值是{a}, b的值是{b}, c的值是{c}')

# 调用函数。注意:python或默认加上"if __name__ == "__main__":"
# 打印:a=10, b=10, c=10
print(f'调用函数前,全局变量a的值是{a}, b的值是{b}, c的值是{c}')
first_func()  # 打印:a=20, b=20, c=20
# 打印:a=10, b=10, c=20
print(f'调用函数后,全局变量a的值是{a}, b的值是{b}, c的值是{c}')

4.3 函数的参数

python 复制代码
# 示例
def user_info(name, age, gender):
    print(f'用户名是{name}, 年龄是{age}, 性别是{gender}')

# 位置参数:参数的位置和数据类型要和函数定义的参数保持一致,不能多也不能少。
user_info('张三', 18, '男')  # 正确
user_info('张三', '男', 18)  # 正确,但打印的年龄和性别会乱
# user_info('张三', 18)                        # 错误,参数个数不一致
# user_info('张三', '男', 18, '1561234567')    # 错误,参数个数不一致

# 关键字参数:采用键值对的方式传参,参数个数需要保持一致,位置不需要。
user_info(name='张三', age=18, gender='男')  # 正确
user_info(gender='男', age=18, name='张三')  # 正确
# user_info(name='张三', age=18)    # 错误,参数个数不一致

# 关键参数和位置参数混合使用时,位置参数要保持一致,关键参数不需要。
user_info('张三', 18, gender='男')  # 正确
user_info('张三', gender='男', age=18)   # 正确
# user_info(gender='男', '张三',  age=18)  # 错误,位置参数不能放在关键参数后面

# 缺省参数:也叫默认参数。当未传入此参数时,使用该参数的默认值;当传入此参数时,使用传入的参数值。
def user_info(name, age, gender='未知'):
    print(f'用户名是{name}, 年龄是{age}, 性别是{gender}')
user_info('张三', 18)  # gender未传递,默认值为"未知"

# 不定长参数:不定长参数在形参列表中必须放到最后,有两种类型:*args和**kwargs。
# *args:不定长位置参数,*args会接收所有位置参数,并封装成一个元组。
# **kwargs:不定长关键参数,**kwargs会接收所有关键参数,并封装成一个字典。
def user_info(name, age, *args, **kwargs):
    print(f'用户名是{name}, 年龄是{age}, 爱好是{args}, 喜欢的人是{kwargs}')
# 调用后打印:用户名是张三, 年龄是18, 爱好是('音乐', '电影', '舞蹈'), 喜欢的人是{'cn': '李清照', 'usa': '香农', 'jp': '绫濑遥'}
user_info('张三', 18, '音乐', '电影', '舞蹈', cn='李清照', usa='香农', jp='绫濑遥')

# 注意:默认参数和不定长位置参数一起用时,默认参数在不定长参数前面时必须设置值(否则它会取不定长的第一个参数值作为默认值),默认参数在定长参数后面时不设置值取默认值。
def user_info(name, age, gender='未知', *args):
    print(f'用户名是{name}, 年龄是{age}, 性别是{gender}, 爱好是{args}')
# 调用后的打印:用户名是张三, 年龄是18, 性别是音乐, 爱好是('电影', '舞蹈')
user_info('张三', 18, '音乐', '电影', '舞蹈')
def user_info(name, age, *args, gender='未知'):
    print(f'用户名是{name}, 年龄是{age}, 性别是{gender}, 爱好是{args}')
# 调用后的打印:用户名是张三, 年龄是18, 性别是未知, 爱好是('音乐', '电影', '舞蹈')
user_info('张三', 18, '音乐', '电影', '舞蹈')

4.4 函数的引用传递

python 复制代码
"""
函数的引用传入问题:在Python中,所有的传递都是引用传递,即:传递的都是地址值。
可变的类型:list、字典、集合。
不可变的类型:bool、int、float、字符串。
区分可变和不可变类型的依据:在不改变地址的情况下,是否可以对元素值做修改。如果可以则为可变类型,否则为不可变类型。
可变与不可变的区别:不可变类型的值改变时,会重新开辟内存空间存储值;可变类型值改变时,不会开辟新的内存空间存储值。
"""

a = 1234567890
b = 1234567890
# bool、int、float、字符串类型为不可变类型,地址值相同
print(id(a), id(b))

# 可变类型:值被修改时,指向的内存地址不变。
name_list = ['张珊', '李思', '王武']
name_list[1] = '赵毅'
# 可变类型如果改了指向,则地址值会改变,比如修改指向:
name_list = ['赵毅', '倩儿', '孙山']

4.5 常用的函数

python 复制代码
# 常用的函数(以下面的变量为例)
name = "李太白"
age = 24
weight = 75.8
# print(变量):将变量名打印到控制台
print(name)
# type(变量):显示变量的类型,比如:int、bool、str等
type(age)
# input(字符串):接收从控制台输入的数据,接收的到数据全部是字符串类型
passwd = input("请输入密码:")
# int(字符串/数字):将变量转换成int类型。如果变量是字符串类型的小数(比如:"2.5")或者非数字则会报错
a = int("24")  # int(2.9)=2(默认取整数部分)
# float(字符串/数字):将变量转换成float类型。如果变量是整数则会转换成小数(比如:"2"会变成2.0)
b = float("2.5")

# 常用的函数:random
import random
# random(): 生成[0.0, 1.0)的随机浮点数,返回float类型(小数点后17位)
print(f'随机浮点数:{random.random()}')
# uniform(a, b): 生成[a, b]范围内的随机浮点数,返回float类型
print(f'随机浮点数:{random.uniform(1, 10)}')
# randint(a, b): 生成[a, b]范围内的整数,返回int类型
print(f'随机整数:{random.randint(1, 10)}')
# randrange(start, stop, step): 生成[a, b)范围内的整数,返回int类型。比如步长为2时会生成奇数
print(f'随机整数:{random.randrange(1, 10, 2)}')
# choice(seq): 从序列中随机选择一个元素,返回序列元素类型
print(f'随机单个元素:{random.choice(str1)}')
# choices(population, k): 从序列中随机选择k个元素(可重复),返回list类型
print(f'随机重复元素:{random.choices(str1, k=4)}')
# sample(population, k): 从序列中随机选择k个不重复元素,返回list类型。如果population小于k则会报错:Sample larger than population or is negative
print(f'随机不重复元素:{random.sample(str1, 4)}')
# shuffle(x):将序列顺序打乱,返回None类型,此函数会改变原序列
random.shuffle(list1)
print(f'打乱顺序:{list1}')

4.6 异常的处理

python 复制代码
    
# 异常处理,语法:try: except:
try:
    print(1 / 0)
except Exception as e:
    print(e) #输出:division by zero
else:
    # 没有异常才会执行的代码
finally:
    # 无论是否有异常,都会执行的代码
    
# 异常的抛出
def validate_data(passwd):
    if  len(passwd) < 6:
        raise Exception("密码长度不能小于6位")
    else:
        print("密码长度合法")

4.7 类型转换函数

python 复制代码
"""
数据类型转换所用到的函数如下:
int(变量名或变量值):把值转成 int。适用于:int,float,整型字符串,True和False。注意:浮点型字符串会报错。
float(变量名或变量值):把值转成 float。适用于:int,float,整型字符串,浮点型字符串,True和False。
str(变量名或变量值):把值转成 str。适用于:所有类型。
bool(变量名或变量值):把值转成 bool。适用于:所有类型,除"0,'',None"三个返回False外,其他均返回True。
eval(变量名或变量值):去掉最外面的引号,剩下的内容是什么酒转成什么。简单理解:eval()=int()+float()+str()+bool()。
"""

# 示例1:int(变量名或变量值)类型转换
print('int(变量名或变量值)类型转换:')
print(int(123))         # 123
print(int(123.456))     # 123
print(int('123'))       # 123
# print(int('123.456')) # 报错
print(int(True))        # 1
print(int(False))       # 0

# 示例2:float(变量名或变量值)类型转换
print('float(变量名或变量值)类型转换:')
print(float(123))           # 123.0
print(float(123.456))       # 123.456
print(float('123'))         # 123.0
print(float('123.456'))     # 123.456
print(float(True))          # 1.0
print(float(False))         # 0.0

# 示例3:str(变量名或变量值)类型转换
print('str(变量名或变量值)类型转换:')
print(str(123))         # "123"
print(str(123.456))     # "123.456"
print(str('123.456'))   # "123.456"
print(str(True))        # "True"
print(str(False))       # "False"

# 示例4:bool(变量名或变量值)类型转换
print('bool(变量名或变量值)类型转换:')
print(bool(123))        # True
print(bool(123.456))    # True
print(bool('abc'))      # True
print(bool(-1))         # True
print(bool(0))          # False
print(bool(None))       # False
print(bool(''))         # False

# 示例5:eval(变量名或变量值)类型转换
print('eval(变量名或变量值)类型转换:')
print(eval('123'), type(eval('123')))           # 123 <class 'int'>
print(eval('123.456'), type(eval('123.456')))   # 123.456 <class 'float'>
print(eval('-1'), type(eval('-1')))             # -1 <class 'int'>
print(eval('True'), type(eval('True')))         # True <class 'bool'>
# 基本的数学计算
num = eval("1 + 1")
# 字符串操作(其他类型也同样适用)
strLine = eval("'*' * 50")
# 函数执行(完整的程序也可以执行)
func = eval("abs(-1)")
# 开发时不能直接使用eval(),因为eval()执行任意代码,可能会有安全风险。示例:
eval("__import__('os').system('ls')")  # 执行系统命令,相当于:"import  os; os.system('ls')"

4.8 匿名函数(lambda表达式)

python 复制代码
"""
lambda表达式:又叫匿名函数
注意点:
(1)匿名函数中不能使用while/for循环,只能编写单行表达式或函数调用。
(2)匿名函数中返回结果的return关键字会被强制省略,默认返回表达式或函数调用结果。
(3)匿名函数中也可以不返回结果,比如:lambda : print('hello')。
"""
# 语法形式:lambda 参数列表: 单行函数体或函数调用
get_sum = lambda a, b: a + b  # get_sum等价于:def get_sum(a, b): return a + b
print(get_sum(1, 2))

# 匿名函数的演化推断(个人理解):
# 1.原函数
def get_sum(a, b):
    return a + b
# 2.定义变量存储原函数:my_sum就表示原函数的内容
my_sum = get_sum
# 3.1 简化get_sum函数:由于是匿名函数,所以省略了函数名
my_sum = (a, b): return a + b
# 3.2 简化get_sum函数:默认会返回结果,所以return也可以省略
my_sum = (a, b): a + b
# 3.3 简化get_sum函数:声明成lambda表达式,参数的括号没啥作用也可以省略。
my_sum = lambda a, b: a + b

4.9 递归函数

python 复制代码
"""
递归函数:自己调用自己的情况就叫递归。
递归函数的特点:必须有"出口"(避免死循环)、必须有"规律"(适合重复调用),调用次数不能过多。
"""

# 阶乘计算:计算5的阶乘
def factorial(n):
    # 出口:n的阶乘最小值为1,即n=1返回1不再向下计算
    if n == 1:
        return 1
    # 规律:n的阶乘 = n*(n-1)的阶乘。
    return n * factorial(n - 1)
# 获取结果
print(factorial(5))

# 斐波那契数列
def fib(month):
    # 出口:斐波那契数列最小值是2
    if month <= 2:
        return 1
    # 规律:斐波那契数列 = 上一个数 + 上上一个数
    return fib(month-1) + fib(month-2)
# 获取结果
print(fib(12))

# 斐波那契数列的for循环实现
fib_list = [1, 1]
def fib_for(month):
    for i in range(2, month):
        fib_list.append(fib_list[i-1] + fib_list[i-2])
    return fib_list
# 计算结果("-1"代表最后一个月的值)
print(fib_for(12)[-1])

4.10

python 复制代码
"""
Python 解释器内置了很多函数和类型,任何时候都能使用。以下按字母顺序给出列表。
"""
# breakpoint(*args, **kws):此函数会在调用位置进入调试器。

# 内置函数 dir(标识符/数据):查看对象内的所有属性及方法。
示例:dir(obj),返回obj所有的属性及方法。返回值中的"__方法名__"表示python提供的内置方法/属性,如下所示:
__new__(cls, *args, **kwargs): 创建对象时,会被自动调用此方法为对象分配内存空间并返回对象引用,是object基类提供的内置的静态方法。
__init__(self): 对象被初始化时,会被自动调用。创建对象时,先分配空间后调用初始化方法设置初始值,初始化方法用来定义一个类具有哪些属性。
__del__(self): 对象被从内存中销毁前,会被自动调用。
__str__(self):返回对象的描述信息(字符串),print()函数输出时使用。

"""
数学相关函数
abs(x):返回一个数字的绝对值。 如果参数是一个复数,则返回它的模。
pow(base, exp, mod=None):返回 base 的 exp 次幂。
complex(num/string):将特定的字符串或数字转换为一个复数,或基于特定的实部和虚部创建一个复数。
round(number, ndigits=None):返回 number 舍入到小数点后 ndigits 位精度的值(四舍五入)。
sum(iterable, /, start=0):从 start 开始自左向右对 iterable 的项求和并返回总计值。
"""


"""
常用函数
len(s):返回对象的长度(元素个数)。
max(arg1, arg2, *args, key=None):返回可迭代对象中最大的元素,或者返回两个及以上实参中最大的。
min(arg1, arg2, *args, key=None):返回可迭代对象中最小的元素,或者返回两个及以上实参中最小的。
next(iterator, default):通过调用 iterator 的 __next__() 方法获取下一个元素。如果迭代器耗尽,则返回给定的 default
help(request):生成属性/对象/方法等的帮助信息。
input(prompt):接收控制台输入并返回字符串,prompt为提示符不会被接收。
open(file, mode='r', encoding=None):打开 file 并返回对应的 file object。 如果该文件不能被打开,则引发 OSError。
print(*objects, sep=' ', end='\n', file=None, flush=False):将 objects 打印输出至file指定的文本流,以sep分隔并在末尾加上end。
range(start, stop, step=1):返回一个不可变的序列类型,即一个步长为step的范围。
reversed(seq):返回一个反向的 iterator。
sorted(iterable, /, *, key=None, reverse=False):排序。
slice(start, stop, step=None):创建切片对象。slice(5)等价于 [0:5] 或 [:5]。
"""

"""
集合处理函数
all(iterable):如果 iterable 的所有元素均为真值(不包含 0, '', None 这三个值)或可迭代对象为空)则返回 True。
any(iterable):如果 iterable 的任一元素为真值(不包含 0, '', None 这三个值)则返回 True。 如果可迭代对象为空,返回 False
"""


"""
转化函数
bool(object):返回布尔值,即 True 或 False 中的一个。
dict(**kwarg):构建一个新的字典。
set(iterable):返回一个新的 set 对象
enumerate(iterable, start=0):返回一个枚举对象。iterable 必须是一个序列,或 iterator,或其他支持迭代的对象。
eval(expression):返回被求值表达式的求值结果,语法错误将作为异常被报告。
exec(object):支持动态执行 Python 代码。 object 必须是字符串或者代码对象。
float(num/string):返回基于一个数字或字符串构建的浮点数。
hex(x):将整数转换为带前缀 "0x" 前缀的小写十六进制数字符串。
oct(x):将整数转换为带前缀 "0o" 的八进制数字符串。
int(num/string):返回基于一个数字或字符串构建的整数。
iter(object, sentinel):返回一个 iterator 对象。
property(fget=None, fset=None, fdel=None, doc=None):返回 property 属性。
tuple(iterable):构建一个元组,tuple 实际上是一个不可变的序列类型,
# 转化成元组的函数
zip(*iterables, strict=False):在多个迭代器上并行迭代,从每个迭代器返回一个数据项组成元组。示例:
for item in zip([1, 2, 3], ['sugar', 'spice', 'everything nice', 'xxx']):
    print(item)
# 打印如下:
(1, 'sugar')
(2, 'spice')
(3, 'everything nice')
"""


"""
字符相关函数
chr(i):返回 Unicode 码位为整数 i 的字符的字符串格式。例如,chr(97) 返回字符串 'a',chr(8364) 返回字符串 '€'。这是 ord() 的逆函数。
ord(c):对表示单个 Unicode 字符的字符串,返回代表它 Unicode 码点的整数。例如 ord('a') 返回整数 97, ord('€') (欧元符号)返回 8364 。这是 chr() 的逆函数。
format(value, format_spec=''):将 value 转换为"格式化后"的形式,格式由 format_spec 进行控制。
"""


"""
类与对象相关函数
@classmethod:把一个方法封装成类方法。
@staticmethod:将方法转换为静态方法。
super(type, object_or_type=None):返回一个代理对象,它会将方法调用委托给 type 的父类或兄弟类。 这对于访问已在类中被重写的继承方法很有用。
delattr(object, name):该函数会删除对象中指定的属性,字符串name必须是对象object的某个属性的名称。 例如,delattr(x, 'foobar') 等价于 del x.foobar。
setattr(object, name, value):函数会将值赋给对象中的属性。如 setattr(x, 'foobar', 123) 等价于 x.foobar = 123。
getattr(object, name, default):函数会将获取对象中的属性值。例如,getattr(x, 'foobar') 等同于 x.foobar。
hasattr(object, name):对象object是否有name属性,有则返回True,否则返回False。
id(object):返回对象在内存中的地址。
hash(object):返回该对象的哈希值(如果它有的话)。哈希值是整数。
isinstance(object, classinfo):如果 object 参数是 classinfo 参数的实例,或者是其 (直接、间接或 虚拟) 子类的实例则返回 True;否则返回False。
issubclass(class, classinfo):如果 class 是 classinfo 的子类(直接、间接或 虚的 ),则返回 True;否则返回False。类将视为自己的子类。
vars(object):返回模块、类、实例或任何其他具有 __dict__ 属性的对象的 __dict__ 属性。
filter(function, iterable):使用 iterable 中 function 返回真值的元素构造一个迭代器。
# 查看参数是否可以调用
callable(object):如果 object 参数是可调用的则返回 True,否则返回 False。
test_fun = lambda a, b : a + b
print(callable(test_fun))   # True
"""
相关推荐
BoBoZz192 小时前
GradientBackground 比较不同类型的背景渐变着色模式与坐标转换
python·vtk·图形渲染·图形处理
540_5402 小时前
ADVANCE Day32
人工智能·python·机器学习
yue0082 小时前
C# 字符串倒序
开发语言·c#
STLearner2 小时前
AAAI 2026 | 图基础模型(GFM)&文本属性图(TAG)高分论文
人工智能·python·深度学习·神经网络·机器学习·数据挖掘·图论
强子感冒了2 小时前
Java学习笔记:String、StringBuilder与StringBuffer
java·开发语言·笔记·学习
低保和光头哪个先来2 小时前
场景6:对浏览器内核的理解
开发语言·前端·javascript·vue.js·前端框架
小北方城市网2 小时前
Python + 前后端全栈进阶课程(共 10 节|完整版递进式|从技术深化→项目落地→就业进阶,无缝衔接基础课)
大数据·开发语言·网络·python·数据库架构
程序员JerrySUN2 小时前
OP-TEE + YOLOv8:从“加密权重”到“内存中解密并推理”的完整实战记录
android·java·开发语言·redis·yolo·架构
阿里嘎多学长3 小时前
2025-12-30 GitHub 热点项目精选
开发语言·程序员·github·代码托管