讲解
运算符是对值做计算的符号。算术运算符前面已经见过:+、-、*、/、//、%、**。比较运算符返回布尔值:==(相等)、!=(不等)、>、>=、<、<=。Python 有一个贴心特性:比较可以链式书写,1 < x < 10 就是数学里的意思,等价于 (1 < x) and (x < 10)——这在很多语言里是写不出来的。要特别提醒 == 和 is 的区别:== 比较值是否相等,is 比较是不是同一个对象。日常几乎总是用 ==;is 只用于 None、True、False 这类单例的判断。
赋值运算符 = 之外还有一族复合赋值:+=、-=、*=、/=、//=、%=、**=,score += 10 等价于 score = score + 10。Python 3.8 还引入了「海象运算符」:=,允许在表达式里赋值,常见于 while 循环和推导式中,比如 while (line := f.readline()): 一行完成读取和判空。注意 Python 没有 ++ 和 -- 自增自减,写 n += 1 即可。
逻辑运算符 and、or、not 上一节讲过;身份运算符 is、is not 和成员运算符 in、not in 也是高频工具:in 可以判断元素是否在列表、元组、集合里,子串是否在字符串里,键是否在字典里,一行 if 'error' in log 顶别的语言一个函数调用。最后记住运算符优先级的大致顺序:括号最高,然后 **,然后乘除取余,然后加减,然后比较,最后 not、and、or。拿不准就加括号——括号永远不会错。
示例
# 链式比较:Python 特色
x = 7
print('1 < x < 10:', 1 < x < 10)
print('10 <= x < 20:', 10 <= x < 20)
# == 比较值,is 比较身份
a = [1, 2]
b = [1, 2]
c = a
print('a == b(值相等):', a == b)
print('a is b(同一对象):', a is b)
print('a is c:', a is c)
# 复合赋值(Python 没有 ++)
n = 10
n += 5
n *= 2
print('复合赋值结果:', n)
# 海象运算符 :=(Python 3.8+)
data = 'Python'
if (length := len(data)) > 3:
print(f'{data} 的长度是 {length},大于 3')
# 成员运算符 in:字符串、列表、字典通吃
print('子串:', 'thon' in 'Python')
print('元素:', 2 in [1, 2, 3])
print('字典键:', 'name' in {'name': '小明'})
print('not in:', 9 not in [1, 2, 3])
# 优先级:括号最可靠
print('先乘后加:', 2 + 3 * 4)
print('加括号:', (2 + 3) * 4)
print('and 优先于 or:', True or False and False)
常见坑
- 混用 == 和 is:小整数和短字符串因解释器缓存,is 偶尔「碰巧」为 True,换个大数字就翻车。比较值永远用 ==,is 只留给 None 等单例。
- 写 n++:Python 没有自增运算符,n++ 会被解析成 n + (+空),报语法错误。写 n += 1。
- 在 and/or 链里期待纯布尔值:'' or [] 返回 [],不是 False。要布尔值就包一层 bool()。
- 以为 in 对字典查的是值:'小明' in {'name': '小明'} 是 False,in 查的是键。查值要用 '小明' in d.values()。
小结
== 比值、is 比身份;比较可链式;复合赋值替代 ++;in 是万能成员判断。下一节学习程序和用户对话:输入与输出。