一个对编码有所追求的人,想必被些问题困扰过。由于这些问题很晦涩,多种写法都是等价的,很少人会把它摆上台面认真的讨论,下面我来分享一下我的思索。
一个函数只应有一个 return 吗?——即对又错。没有意外情况只应有一个 return,意外情况要提前 return (导致多个 return )。举例:
students = dict(...)
# 正确的写法
def get_studen_age(studen_name): # 需求:若学生不存在返回-1
student = students.get(studen_name, None)
if student is None: # 意外情况
return -1
student.access_count += 1 # 需求:增加访问计数
return student.age
# 错误的写法[1]
def get_studen_age(studen_name):
student = students.get(studen_name, None)
if student is None: # 意外情况
return -1 # 错误情况应该尽早返回,代码可读性更佳
else:
student.access_count += 1
return student.age
# 错误的写法[2]
def get_studen_age(studen_name):
student = students.get(studen_name, None)
if student is None: # 意外情况
student_age = -1
else:
student.access_count += 1
student_age = student.age
return student_age # 错上加错,只有一个 return,营造没有错误情况的假象
什么时候应该提前 return,什么时候应该用 else 语句?——正如上面的例子所说,意外情况才要提前 return,否则写在 else 语句里。这又引入了另一个问题:怎么定义意外情况?有一个衡量的方法:if 条件... : [THEN] else [ELSE] 如果在普遍情况下[THEN]部分和[ELSE]部分执行的频度一致,说明没有意外情况,否则[THEN]部分和[ELSE]部分两者中执行频度较低的一方可判定为意外情况(通常为错误处理)。举例:
# 正确的写法
def min(a, b):
if a < b:
r = a
else:
r = b
# 普遍情况下[r = a]和[r = b]执行的频度(运行的机会)是一致的,这里没有意外情况
return r
# 错误的写法
def min(a, b):
if a < b:
return a # 这里不该应该是意外
return b
1
crb912 2018-04-29 02:00:46 +08:00 via Android 1
任何函数,只有要返回值,都有且仅有一次 return。你虽然前面的代码有多个 return,但处于 if 构建的分支中(有无 else 都一样)。
我探讨几个问题吧。 1.你"#错误的写法[1]"和"#正确的写法",这两个例子有区别吗? 我的看法: 没任何区别,无非多了一个 else。写不写 else 都可以,纯属看个人爱好。反而,理论上,写 else 代码逻辑更清晰点,别人一目了然。方便粗心的程序员阅读你的代码。所以"错误的写法"真的错误吗?不见得,而且我认为它是一种不错的方式。 2."错误的写法[2]"又哪里错了吗? 当 if 成立,它立马 return 了错误值-1,难道它没有满足你说的"提前 return"?早知道,此时 else 的语句是不会执行的。 |
2
autoxbc 2018-04-29 09:21:00 +08:00
卫语句的讨论是周经了,估计又要火一帖
|
3
roy2220 OP @crb912 感谢讨论。每个人对代码可读性的理解不一样,其实这个问题没有的唯一正确的答案。上面所说的"正确"、"错误"并非指功能实现上,而且是风格上的。你指出的第 1 点主要是例子 1 的意外情况只有一个不太明显,如果例子 1 的意外情况很多,都用 if else 的写法,处理正常情况的逻辑会被嵌套得很深,不能一眼找出正常逻辑的部分
|
4
roy2220 OP @crb912 关于你的第二点,其实是我的描述不对,我所定义的"尽早返回"应该是直截了断,不应该留下 else 部分
|
5
crb912 2018-04-29 11:16:48 +08:00 via Android
关于要不要 else,我看过书里这么讲的:
The else isn't needed,but it does help the casual reader understand the intent. —— 《 C++ Primer Plus 》第六版 p308. |
6
roy2220 OP @crb912 如果真的有一些简单武断的原则,只要竭力去遵守就能写出好代码,那满世界都是优秀程序员了,因为这太简单就能做到了。但现实并不是那么简单,动态地权衡和取舍才能做出好决定,不要盲目地相信各种原则(例如 DRY ?),它们通常都隐含着应用情景,无视应用情景妄想一招鲜,不是懒就是傻
|
7
woscaizi 2018-04-30 10:26:51 +08:00
实际代码中多个 return 没什么不妥吧,把逻辑处理好就可以。拙见。
|
8
roy2220 OP @woscaizi 光把逻辑写对还不够,可读性很重要,本主题的核心就是 return 与代码的可读性
|
10
roy2220 OP @woscaizi 所以说这本身就是个很主观的问题。本主题的定位人群是认为 return 和 else 可读性不一致、想在两者寻找一个平衡的人,你大可无视本主题,它和你没什么关系
|