1 Python 文件内容读取相关函数
-
read()
- 功能:一次性读取文件的全部内容
- 返回值:字符串类型,包含文件所有内容
- 示例:
python
运行
with open("file.txt", "r") as f: content = f.read() # 读取整个文件内容
-
readline()
- 功能:每次读取文件的一行内容
- 返回值:字符串类型,包含当前行的内容(包含换行符)
- 特点:多次调用会依次读取下一行,读到文件末尾返回空字符串
- 示例:
python
运行
with open("file.txt", "r") as f: line1 = f.readline() # 读取第一行 line2 = f.readline() # 读取第二行
-
readlines()
- 功能:读取文件所有行内容
- 返回值:列表类型,列表中的每个元素是文件的一行内容(包含换行符)
- 示例:
python
运行
with open("file.txt", "r") as f: lines = f.readlines() # 得到包含所有行的列表
-
补充说明:
- 以上三个函数均用于读取文件内容,只是读取方式和返回结果不同
- 关闭文件使用
close()
方法,而非选项中的readclose()
(该方法不存在) - 推荐使用
with
语句操作文件,可自动处理文件关闭,无需手动调用close()
这些函数适用于不同的读取场景,可根据实际需求选择使用:读取整个文件用read()
,逐行处理用readline()
,需要一次性获取所有行并处理用readlines()
。
2 math.floor()
函数
1. math.floor()
的核心功能
math.floor(x)
是数学中的向下取整函数,用于返回小于或等于输入值 x
的最大整数。
例如:
math.floor(5.5)
返回5
(小于 5.5 的最大整数)math.floor(-2.3)
返回-3
(小于 -2.3 的最大整数)math.floor(7)
返回7
(整数的向下取整是其本身)
2. Python 2.x 与 Python 3.x 的返回值差异
-
Python 2.x:
math.floor()
返回 float 类型
例如:math.floor(5.5)
的结果是5.0
(浮点数) -
Python 3.x:
math.floor()
返回 int 类型
例如:math.floor(5.5)
的结果是5
(整数)
3. 实际使用示例
python
运行
import math
# Python 3.x 环境下
print(math.floor(5.5)) # 输出:5(int类型)
print(math.floor(-3.2)) # 输出:-4(int类型)
print(math.floor(10)) # 输出:10(int类型)
4. 注意点
- 该函数属于
math
模块,使用前需先导入import math
。 - 向下取整与 “四舍五入” 不同,它总是向更小的方向取整(即使小数部分小于 0.5)。
- 版本差异主要影响返回值的类型,不改变取整的逻辑结果。
这种差异是 Python 2 到 Python 3 升级过程中对数据类型规范化的一部分,让函数返回更符合直觉的整数类型。
3 元组的定义是通过逗号 ,
来标识的,而不是单纯的括号 ()
在 Python 中,元组的定义是通过逗号 ,
来标识的,而不是单纯的括号 ()
。例如:
(1, 2)
是元组(因为有逗号)([1, 2])
只是用括号包裹了一个列表,括号在这里仅起到分组作用,不会改变内部数据的类型,所以它仍然是列表[1, 2]
而列表是不可哈希的(因为列表是可变类型,其内容可以被修改),不能作为字典的键。
如果想让它成为元组,需要添加逗号:
python
运行
dicts[(1, 2)] = 'abc' # 正确,(1, 2) 是元组(可哈希)
dicts[([1, 2],)] = 'abc' # 正确,元组内包含列表(但元组本身可哈希)
所以题目中 ([1, 2])
本质是列表,导致代码报错。核心区别在于:括号本身不决定是否为元组,逗号才是元组的关键标识。
4 list元素可以重复,set集合不行
在 Python 中:
list
确实是列表,它是有序的、可修改的序列,允许包含重复元素。例如:[1, 2, 2, 3]
是一个有效的列表。
set
是集合,它是无序的、不可修改的(但可以添加 / 删除元素),并且不允许包含重复元素。如果尝试添加重复元素,集合会自动去重。例如:{1, 2, 2, 3}
最终会变成 {1, 2, 3}
。
这是列表和集合的核心区别之一,也是 Python 中两种常用数据结构的重要特性。
5 Python 中不可变数据类型及字符串的特性
1. 不可变数据类型的核心特性
不可变数据类型是指:对象创建后,其内存中的值不能被直接修改。若要 "修改",需创建新的对象并赋值,原对象保持不变。
Python 中常见的不可变类型包括:
- 字符串(
str
) - 整数(
int
)、浮点数(float
)、布尔值(bool
) - 元组(
tuple
,仅当元素均为不可变类型时整体不可变) - 冻结集合(
frozenset
)
2. 字符串不可变的具体表现
字符串的不可变性体现在:
- 无法通过索引直接修改单个字符(如
s[0] = 'H'
报错) - 无法删除单个字符(如
del s[0]
报错) - 所有字符串方法(如
replace()
、upper()
)均返回新字符串,不改变原字符串
示例:
python
运行
s = "hello"
s_new = s.replace('h', 'H') # 返回新字符串"Hello"
print(s) # 原字符串仍为"hello",未被修改
3. 报错类型及原因
当尝试修改字符串的元素时,会触发 TypeError
,错误信息为:
'str' object does not support item assignment
(字符串对象不支持元素赋值)
原因:
字符串在内存中以固定序列存储,其地址(内存引用)与值绑定。若允许修改,会破坏 Python 对字符串的优化机制(如字符串驻留机制),同时影响依赖字符串不可变性的场景(如作为字典的键)。
4. 如何 "间接修改" 字符串
虽然不能直接修改,但可通过以下方式生成新字符串实现类似 "修改" 的效果:
- 切片拼接:
python
运行
s = "hello" s_new = "H" + s[1:] # 用新字符拼接原字符串的切片,结果为"Hello"
- 列表转换:先转为可变的列表,修改后再转回字符串:
python
运行
s = "hello" s_list = list(s) # 转为列表['h','e','l','l','o'] s_list[0] = "H" # 修改列表元素 s_new = "".join(s_list) # 转回字符串"Hello"
5. 不可变类型的优势
- 安全性:作为字典键或集合元素时,值不会意外被修改,避免哈希冲突。
- 性能优化:Python 可对不可变对象进行缓存(如小整数池、字符串驻留),减少内存占用。
- 线程安全:多线程环境下,无需担心不可变对象被并发修改。
6. 与可变类型的对比
类型 | 可变 / 不可变 | 能否直接修改元素 | 示例操作 |
---|---|---|---|
字符串(str) | 不可变 | 不能 | s[0] = 'a' 报错 |
列表(list) | 可变 | 能 | lst[0] = 'a' 正常执行 |
元组(tuple) | 不可变 | 不能 | tpl[0] = 'a' 报错 |
字典(dict) | 可变 | 能 | dct['key'] = 'val' 正常执行 |
理解这一特性,有助于避免编写错误代码,同时更合理地选择数据类型(如需要频繁修改用列表,作为键或需要稳定值用字符串 / 元组)。
6 可调用对象(callable)
在 Python 中,可调用对象(callable) 是指可以像函数一样通过 ()
语法执行的对象。简单来说,就是可以在对象后面加括号进行调用的实体。
常见的可调用对象:
-
函数(function)
用def
定义的普通函数或lambda
匿名函数,例如:python
运行
def add(a, b): return a + b add(1, 2) # 可调用,返回3 f = lambda x: x*2 f(3) # 可调用,返回6
-
类(class)
类本身是可调用的,调用时会创建实例(触发__init__
方法):python
运行
class Person: def __init__(self, name): self.name = name p = Person("Alice") # 调用类创建实例
-
类的实例(instance)
如果类定义了__call__
方法,其实例也可被调用:python
运行
class Counter: def __call__(self): print("被调用了") c = Counter() c() # 可调用,输出"被调用了"(因为定义了__call__)
-
其他可调用类型
如内置函数(print()
、len()
)、方法(类或实例的方法)、生成器函数等。
不可调用的对象:
不可调用对象是指不能通过 ()
语法执行的对象,大多数基础数据类型都属于此类,例如:
- 数值(
int
、float
):123()
会报错 - 字符串(
str
):"hello"()
会报错 - 列表(
list
):[1,2,3]()
会报错 - 字典(
dict
):{"a":1}()
会报错 - 普通类实例(未定义
__call__
方法):python
运行
class A: pass a = A() a() # 报错,因为A未定义__call__
如何判断对象是否可调用?
可以使用内置函数 callable()
检查:
python
运行
print(callable(add)) # True(函数可调用)
print(callable(Person)) # True(类可调用)
print(callable(123)) # False(整数不可调用)
print(callable(a)) # False(未定义__call__的实例)
核心区别:可调用对象本质上实现了 Python 的 “调用协议”(通常是通过定义 __call__
方法),而不可调用对象则没有这种能力。