一、什么是「条件表达式」
先分清三个长得很像的词,不然后面一定打结:
- 布尔值:只有两个——
True(真)和False(假)。它是计算机回答「是 / 不是」的唯一方式。 - 条件:一句能回答「是 / 不是」的话。比如「年龄满 18 了吗」「分数够 60 吗」,答案非真即假。
- 条件表达式:Python 里一个专门的写法,用一行完成「如果……就……否则……」的二选一,长相是
A if 条件 else B。它才是这一篇的主角。
为了把这三样讲清楚,正文分三块走:
| 要解决的问题 | 用到的写法 | |
|---|---|---|
| 第一块(第二、三、四节) | 怎么「问」出一个条件 | 比较运算符 == != > < >= <= + 逻辑运算符 and/or/not |
| 第二块(第五节) | 拿到条件后,怎么「二选一」 | 条件表达式 A if 条件 else B |
| 第三块(第六节起) | 把它用到真实代码里 | 赋值、打印、f-string、函数返回值、嵌套 |
二、写出一个条件:比较运算
比较运算符用来「问一句话」,答案只有 True 或 False。一共六个:
| 运算符 | 读作 | 例子 | 结果 |
|---|---|---|---|
== | 等于吗 | 5 == 5 | True |
!= | 不等于吗 | 5 != 3 | True |
> | 大于吗 | 8 > 5 | True |
< | 小于吗 | 2 < 7 | True |
>= | 大于或等于吗 | 3 >= 3 | True |
<= | 小于或等于吗 | 3 <= 5 | True |
print(5 == 5) # True 相等
print(5 == '5') # False 一个是数字,一个是文字,不相等
print(5 != 3) # True 不相等
print(8 > 5) # True
print(3 >= 3) # True 大于等于,「等于」也算
print(3 <= 5) # True
print(type(5 == 5)) # <class 'bool'> 结果是真假值,不是数字
接着是四个新手一定会踩的坑,每一个都值得单独记住。
坑 1:一条等号是「放进去」,两条等号才是「问一句」。
x = 5 # 一条等号:把 5 放进 x(赋值)
print(x == 5) # 两条等号:问「x 是不是 5」(比较)→ True
坑 2:小数不能直接用 == 比相等。
print(0.1 + 0.2) # 0.30000000000000004
print(0.1 + 0.2 == 0.3) # False ← 看着该相等,其实不等
print(round(0.1 + 0.2, 2) == 0.3) # True 先四舍五入再比
原因是小数在计算机里是近似存的,0.1 + 0.2 会比 0.3 大那么一丁点。要比较小数,先用 round() 收一收。
坑 3:字符串比的是「字典顺序」,不是长度,也不是数值。
print('a' < 'b') # True a 排在 b 前面
print('apple' < 'banana') # True 按首字母顺序
print('10' < '9') # True ← 坑!比的是首字符 '1' 和 '9'
print(10 < 9) # False 数字比才是我们习惯的结果
print('a' < 'B') # False 大写字母的编号比小写小
print('hello' == 'HELLO') # False 区分大小写
坑 4:类型不同,多数就不相等。
print(1 == 1.0) # True 整数 1 和小数 1.0 数值上相等
print('1' == 1) # False 字符串和数字不相等
print(True == 1) # True 布尔值本质上就是 1 和 0
Python 还支持「连着写」的比较,读起来跟数学课本一样:
age = 20
print(18 <= age < 60) # True 这就是「18 到 60 之间」
score = 85
print(60 <= score < 90) # True
print(1 < 3 < 5 < 7) # True 可以接好几个
print(18 <= age and age < 60) # True 等价写法,但更长
0 < age < 150,比写两个条件再用 and 连起来更短、更不会错。课程思政|工匠精神与严谨求实 · 别拿等号赌小数
看到 0.1 + 0.2 == 0.3 得到 False,很多人第一反应是「计算机坏了」。其实是我们想当然——小数在机器里是近似存的,差着那么一丁点。写代码最怕凭感觉,错的往往就藏在那些「本该相等」里。比较小数改用 round() 或允许一点误差,先看清数据的真面目,再下判断。
三、把条件串起来:and / or / not
一个条件不够用时,用三个逻辑运算符把几个条件拼成一个:and 要求「都对」,or 只要「有一个对」,not 是「反过来说」。
| A | B | A and B | A or B | not A |
|---|---|---|---|---|
| True | True | True | True | False |
| True | False | False | True | False |
| False | True | False | True | True |
| False | False | False | False | True |
print((5 > 3) and (2 < 4)) # True 两个都对
print((5 > 3) and (2 > 4)) # False 有一个不对,结果就不对
print((5 > 3) or (2 > 4)) # True 至少一个对
print((5 < 3) or (2 > 4)) # False 两个都不对
print(not (5 == 5)) # False 把 True 反过来
print(not (5 < 3)) # True
优先级是 not > and > or,不按这个顺序加括号,结果会跟你以为的不一样:
print(not True and False) # False 先算 not True → False,再 False and False
print(not (True and False)) # True ← 加了括号,先算括号里面
print(not False or True) # True 先算 not False → True
print(not (False or True)) # False ← 加了括号,结果整个反过来
短路求值:and 的左边已经是假,右边根本不会执行;or 的左边已经是真,右边也不会执行。
def hello():
print('[hello 被执行了]')
return True
print(False and hello()) # 只打印 False,hello 根本没跑
print(True or hello()) # 只打印 True,hello 也没跑
还有一个 Python 的特点:and 和 or 交出来的不是 True/False,而是参与运算的那个值本身。
print(6 and 3) # 3 前面是真,交出后面那个
print(0 and 3) # 0 前面是假,直接交出它
print(6 or 3) # 6 前面是真,直接交出它
print(0 or 3) # 3 前面是假,只好给后面那个
print('' or '默认') # 默认
print(0 or '' or '最后一个') # 最后一个 一路找下去,交出第一个非假值
利用这一点,可以给「空值」兜底:
name = input('请输入名字:') # 用户直接回车时,name 是空字符串 ''
print('你好,' + (name or '匿名用户'))
四、「真」和「假」到底怎么算
在 Python 里,任何一个值都能被当成条件用。它给出的答案由 bool() 决定。下面这些是全部的「假值」:
| 假值 | 是什么 |
|---|---|
False | 布尔假 |
None | 空无一物(没有值) |
0、0.0 | 零 |
'' | 空字符串 |
[]、()、{}、set() | 空列表、空元组、空字典、空集合 |
for v in [False, None, 0, 0.0, '', [], (), {}, set()]:
print(repr(v), '->', bool(v))
# False -> False None -> False 0 -> False 0.0 -> False
# '' -> False [] -> False () -> False {} -> False set() -> False
除了上面这些,其余全部算真。有几种「看起来像假的、其实是真的」最容易骗到人:
print(bool('0')) # True ← 字符串里有字符,就是真
print(bool('False')) # True ← 名字叫 False,可它是字符串,还是真
print(bool(' ')) # True 一个空格也算有内容
print(bool('None')) # True 同上
print(bool([0])) # True 列表里有一个元素(哪怕元素是 0)
print(bool(-1)) # True 非零数值都是真
print(bool(0.0001)) # True
len():if items: 就够了,非空为真、空为假。items = []
if items: # 等价于 if len(items) > 0:
print('有东西')
else:
print('空') # 会走这里
五、重头戏:A if 条件 else B
前面都在准备「条件」。现在看主角——条件表达式,长相是(下面三处都要换成你自己的东西):
# 长相:成立取哪边 if 条件 else 不成立取哪边
值1 if 条件 else 值2
读法是:条件成立,就取 A;条件不成立,就取 B。注意 if 在中间,不在开头——这是它跟 if 语句最大的区别。
同一件事,两种写法对照着看最清楚:
price = 25
# 写法一:if / else 语句(四行)
if price >= 20:
discount = 5
else:
discount = 0
print(discount) # 5
# 写法二:条件表达式(一行)
discount2 = 5 if price >= 20 else 0
print(discount2) # 5
写的时候记三句话:先写「成立时要什么」,再写 if 条件,最后写 else 和「不成立时要什么」。
age = 20
print('成年' if age >= 18 else '未成年') # 成年
x = -7
print(x if x > 0 else -x) # 7 相当于取绝对值
a, b = 3, 9
print(a if a > b else b) # 9 相当于取较大值
AI 助手小贴士|「if/else 改三元」是条件表达式的核心功,用 AI 对答案。
打开任意 AI 对话工具(网页版或 App 都可以),试试这样问:出 5 道改写题:每题给一段 if/else,让我改写成条件表达式;我改完你逐题对答案
课程思政|科技自立自强 · 让 AI 当陪练
条件表达式 A if 条件 else B 一行搞定二选一,拿它去问 AI「这两种写法一样吗」,几秒就能对完答案。这正是 AI 最好的用处——当陪练,帮你把没把握的地方练熟。但别把它的输出原样贴上就交,工具可以先用别人的,本事必须长在自己身上。哪天真要独立写程序,替你答题的是你的脑子,不是对话框。
六、条件表达式能放在哪些位置
它是「一个值」,所以凡是能写表达式的地方都能放。下面五个位置从最常用到最少见。
① 当变量的值(最常用)
score = 75
level = '及格' if score >= 60 else '不及格'
print(level) # 及格
② 直接打印出来
score = 75
print('通过' if score >= 60 else '没通过') # 通过
③ 塞进 f-string 里——注意里面那层的引号要用另一种,不然会打架
age = 17
print(f"{age} 岁,{'成年' if age >= 18 else '未成年'}") # 17 岁,未成年
score = 75
print(f'及格率:{100 if score >= 60 else 0}%') # 及格率:100%
④ 当函数的返回值——写在一行里特别清爽
def safe_div(a, b):
return a / b if b != 0 else '除数不能为 0'
print(safe_div(10, 2)) # 5.0
print(safe_div(10, 0)) # 除数不能为 0
⑤ 当列表里的元素(这一条用到了列表——第 16 篇《列表》里会讲列表推导式。现在只要看懂「条件表达式能塞进方括号里」就行)
scores = [55, 90, 72]
flags = ['过' if s >= 60 else '挂' for s in scores]
print(flags) # ['挂', '过', '过']
七、条件不必是「比较」
条件表达式里的「条件」,不一定要写成 >、== 这种比较。按第四节讲的,任何值都能直接当真假用:
items = []
print('有东西' if items else '空了') # 空了
print('有东西' if [1] else '空了') # 有东西
n = 0
print('非零' if n else '零') # 零
s = ''
print('非空' if s else '空字符串') # 空字符串
is_vip = True
print('打折' if is_vip else '原价') # 打折
print('打折' if not is_vip else '原价') # 原价
playlist = ['夜曲', '晴天']
print('有夜曲' if '夜曲' in playlist else '没有') # 有夜曲
a, b, c = 3, 9, 5
print('a 最大' if a > b and a > c else 'a 不是最大') # a 不是最大
len()。八、多个岔路:嵌套的条件表达式
条件表达式可以嵌套,排成一串来处理「多档」判断:
s = 72
g = '优' if s >= 90 else '良' if s >= 80 else '及格' if s >= 60 else '不及格'
print(g) # 及格
它之所以能这么排,是因为条件表达式是右结合的——从右往左配对,把 else 后面那一整串又当成一个新的条件表达式。看证据:
x = 5
print(1 if x > 10 else 2 if x > 3 else 3) # 2
x = 1
print(1 if x > 10 else 2 if x > 3 else 3) # 3
# 从右往左配对:x > 10 不成立 → 去看右边整串「2 if x > 3 else 3」
上面那行成绩等级虽然能跑,但一眼看不出几个岔路。这时候加括号或者换行对齐,可读性立刻不一样:
s = 72
g = ('优' if s >= 90
else '良' if s >= 80
else '及格' if s >= 60
else '不及格')
print(g) # 及格
而同一件事用 if / elif / else 写,是长这样:
s = 72
if s >= 90:
g = '优'
elif s >= 80:
g = '良'
elif s >= 60:
g = '及格'
else:
g = '不及格'
print(g) # 及格
if / elif / else。三行以上的条件表达式,过两天自己都看不懂。真正适合它的是「只有一个岔路」的情况。九、老写法「条件 and A or B」的坑
网上和一些老代码里常能看到用 and / or 来「二选一」的写法。它在大多数情况下对,但有一个致命例外:
a = 0
print(True and a or 5) # 5 ← 错!你想要的其实是 0
print(a if True else 5) # 0 ← 这样才对
为什么错?按第三节讲的,True and a 交出来的是 a,也就是 0;接着算 0 or 5——因为 0 是假值,or 就跳到后面给 5。只要 A 本身是假值(0、空字符串、空列表……),这个老写法就一定出错。
条件表达式的语义是「选」:条件为真,就直接拿 A,A 是 0 也照样拿 0。
那 or 什么时候能用?当你要的就是「兜底」的语义时,它又短又好使:
name = input('请输入名字:') # 用户直接回车时,name 是空字符串 ''
print(name or '匿名用户') # 匿名用户
or 更清爽。课程思政|诚信与职业操守 · 看着对,不等于对
网上流传的 条件 and A or B 看着很聪明,可只要 A 是 0、空串这类假值,结果立刻翻车。代码对不对,不以「看着像」为准,要以跑出来的结果为准。做报表、算数据也一样,别拿一个「大概没问题」的结果交上去——你省下的那点核对工夫,最后都要由信你的人来还。对自己交出去的东西负责,就是职业操守的起点。
十、最容易搞混的几组
把这几个东西放在一起看一遍,考试和写作业时就不会卡:
| 容易混的一对 | 区别 |
|---|---|
= / == | 一条是「放进去」(赋值),两条是「问一句」(比较) |
if 语句 / 条件表达式 | 语句要换行和缩进、管「做哪件事」;表达式是一行、管「取哪个值」 |
条件 and A or B / A if 条件 else B | 前者在 A 是假值时出错,后者永远正确 |
True / 'True' | 前者是布尔值,后者是四个字符组成的字符串 |
0、''、[] / '0'、' '、[0] | 左边是假值;右边都是真值,看第一列的清单 |
print(True) # True 布尔值
print('True') # True 字符串,四个字符
print(bool('True')) # True 非空字符串就算真
print(bool('False')) # True ← 名字骗人,它不是假的
print(1 == True) # True 布尔值本质上是 1 和 0
print('1' == True) # False 字符串和布尔值不相等
十一、四个能直接跑的小例子
1. 判断奇偶——% 取余数,余数是 0 就是偶数
n = int(input('请输入一个整数:'))
print(f'{n} 是' + ('偶数' if n % 2 == 0 else '奇数'))
# 输入 7 → 7 是奇数
2. 取绝对值——负数就取它的相反数
x = -7
print(x if x >= 0 else -x) # 7
3. 今天穿什么——三个岔路,用嵌套的条件表达式
temp = 28
clothes = '短袖' if temp >= 28 else '薄外套' if temp >= 18 else '毛衣' if temp >= 10 else '羽绒服'
print(f'{temp} 度:穿 {clothes}') # 28 度:穿 短袖
4. 游戏昵称兜底——昵称空着就提醒,别让程序傻傻地欢迎空名字
nickname = input('请输入游戏昵称:')
msg = '欢迎回来,' + nickname if nickname else '你还没起昵称哦'
print(msg)
# 输入 皮卡丘 → 欢迎回来,皮卡丘
# 直接回车 → 你还没起昵称哦
5. 看月份报季节——嵌套写法的日常用法。中国人把一年最热的那段叫「三伏天」、最冷的叫「三九天」,季节感特别强;按公历月份粗分四季可以这样写:
month = 8
season = ('春' if 3 <= month <= 5 else
'夏' if 6 <= month <= 8 else
'秋' if 9 <= month <= 11 else '冬')
print(f'{month} 月:{season}天')
输出:
8 月:夏天
从里往外读:先看是不是春天,不是再看夏天……一路问下去,总有一个兜底的 else。写完拿边界试一试:3 月是春天、6 月是夏天、9 月是秋天、12 月是冬天,各归各位。
AI 助手小贴士|三元写法不是越省越好,让 AI 摆一个反面教材。
打开任意 AI 对话工具(网页版或 App 都可以),试试这样问:给一个嵌套两层以上的条件表达式的难读例子,再给等价的 if/elif 版本,对比解释为什么可读性更重要
十二、常见问题(报错手册)
1. 忘了写 else
x = 5
print('正' if x > 0)
# SyntaxError: expected 'else' after 'if' expression
条件表达式必须有 else——它的职责就是「二选一」,只有一个选项就没意义了。如果你想要的只是「条件成立时做点什么,不成立时什么也不做」,那要用 if 语句,不是条件表达式。
2. 把语句当表达式用
x = 5
r = pass if x > 0 else 0
# SyntaxError: invalid syntax
pass、import、x = 1 这些是「语句」,不是「值」,塞不进条件表达式。里面只能放能算出一个结果的东西:数字、字符串、变量、函数调用、算术式……
3. 用 if …: … else … 想去掉换行
x = 5
if x > 0: '正' else '负'
# SyntaxError: invalid syntax
if …: … else … 是语句,必须换行加缩进。想一行搞定,就用条件表达式 '正' if x > 0 else '负'。
4. 用了中文标点
print('正' if 5 > 0 else '负')
# SyntaxError: invalid character '(' (U+FF08)
print(‘正’ if True else ‘负’)
# SyntaxError: invalid character '‘' (U+2018)
中文输入法下的全角括号 () 和全角引号 ‘’ “” Python 都不认。代码里的括号和引号必须切到英文半角。
5. 判断符号写错
x = 5
if x = 5:
print('ok')
# SyntaxError: invalid syntax. Maybe you meant '==' or ':=' instead of '='?
Python 的报错信息很贴心,会直接提示「你大概想写 ==」。看到这句就把等号改成两个。
6. 字典不能比大小
print({'a': 1} >= {'a': 1, 'b': 2})
# TypeError: '>=' not supported between instances of 'dict' and 'dict'
print({'a': 1} == {'a': 1, 'b': 2}) # False 只能判相等
字典只能判断「相等 / 不相等」(比的是键值对是否完全一样),比不了大小。列表、元组、集合是可以比大小的。
7. 变量还没定义就用
print(score if score >= 60 else 0)
# NameError: name 'score' is not defined
条件表达式会先算条件,条件里用到的变量必须已经赋过值。
8. 结果类型一会儿一变
def f(v):
return v if v > 0 else '未知'
print(f(3), f(-1)) # 3 未知
print(type(f(3)), type(f(-1))) # <class 'int'> <class 'str'>
不报错,但同一个函数有时返回数字、有时返回字符串,调用方很容易踩坑。两个分支尽量给同一种类型,比如都返回字符串。
9. 里面塞函数调用也能跑,但不建议
x = 5
print('正') if x > 0 else print('负') # 能跑,输出「正」
两条分支都是「打印」,结果一样,但读代码的人一眼看不出这里到底是要「取一个值」还是「做一件事」。这种情况老老实实写 if / else 语句。
10. 写成 x += 1 if x > 0 else 0 有点绕
x = 5
x += 1 if x > 0 else 0 # 实际是 x += (1 if x > 0 else 0)
print(x) # 6
能跑,但因为条件表达式的优先级很低,容易看错。想表达这个意思,加上括号 x += (1 if x > 0 else 0) 会清楚得多。
AI 助手小贴士|三元写法省行数,但可能牺牲可读性。正好让 AI 改写一遍,再客观点评两版谁更好读——这种「正反对比」最能建立判断力。
打开任意 AI 对话工具(网页版或 App 都可以),试试这样问:把下面这段 if/else 改写成条件表达式,然后客观评价:改写后是更易读还是更难读了?什么情况下不该用条件表达式?<粘贴代码>
十三、随堂自测(10 题)
点击选项即可判分,选错的题会立刻展开解析。做完可以看到正确率和错题清单,也可以重新答题。
1条件表达式 A if 条件 else B,在什么情况下取 A?
- A. 条件为假时
- B. 条件为真时
- C. 永远取 A
- D. 由 A 自己的真假决定
if 在中间,跟 if 语句的位置不一样;A 和 B 本身是真是假不影响选择。2print(5 == '5') 会输出什么?
- A.
False - B.
True - C. 报错
- D.
None
'5',类型不同,用 == 判断是不相等。想按数值比,要先用 int() 转换。3print(not True and False) 的输出是?
- A.
True - B.
None - C. 报错
- D.
False
not > and,所以先算 not True 得 False,再算 False and False 得 False。写成 not (True and False) 结果才会是 True。4下面哪个值在判断时算「假」?
- A.
0 - B.
'0' - C.
[0] - D.
' '
False、None、0、0.0、''、[]、()、{}、set()。带引号的 '0'、' ' 都是非空字符串,[0] 里有元素,全算真。5print(bool('False')) 的输出是?
- A.
False - B.
True - C. 报错
- D.
'False'
'False' 是字符串,里面有五个字符,属于非空字符串,算真。只有空的 '' 才是假。名字叫 False 不代表它就是假值。6a = 0 时,老写法 True and a or 5 的结果是多少?
- A.
True - B.
5,因为 a 是假值被 or 跳过 - C.
0 - D. 报错
True and a 先交出 a(即 0),接着 0 or 5 因为 0 是假值就跳到了 5。这正是这个老写法的漏洞;换成 a if True else 5 才能得到正确的 0。7level = '及格' if score >= 60 else '不及格' 这行代码里,省略 else 会怎样?
- A. 能跑,不成立时返回
None - B. 能跑,不成立时返回
False - C. 报
NameError - D. 报
SyntaxError: expected 'else' after 'if' expression
else,它是语法硬性要求,缺了就报 SyntaxError。如果只是「成立时做点事、不成立时什么都不做」,那就该用 if 语句。8print(0.1 + 0.2 == 0.3) 会输出什么?
- A.
True - B. 报错
- C.
False - D.
0.5
0.1 + 0.2 实际是 0.30000000000000004,比 0.3 大一点点,所以不相等。比较小数先用 round() 收一收。9成绩要分成「优秀 / 良好 / 及格 / 不及格」四档,最合适的写法是?
- A. 一行里塞三个嵌套的条件表达式
- B. 用
and、or拼出来 - C. 用
if / elif / else语句 - D. 用
try / except包起来
if / elif / else——嵌套的条件表达式虽然能跑,但三行以上读起来非常费劲。条件表达式的长处是「只有一个岔路」。10scores = [55, 90, 72],想让 print(flags) 输出 ['挂', '过', '过'],flags 该怎么写?
- A.
['过' if s < 60 else '挂' for s in scores] - B.
['挂' if s >= 60 else '过' for s in scores] - C.
['挂' if s < 60 else '过' for s in scores] - D.
['过' if s >= 60 for s in scores]
s < 60 当条件,成立取「挂」、不成立取「过」。选项 D 省了 else,会直接报 SyntaxError。