首页 > Python基础教程 >
-
Python 设计和历史的 27 个问题(2)
为什么Python没有属性赋值的“with”语句?
Python有一个 'with' 语句,它封装了块的执行,在块的入口和出口调用代码。有些语言的结构是这样的:
with obj:
a = 1 # equivalent to obj.a = 1
total = total + 1 # obj.total = obj.total + 1
在Python中,这样的结构是不明确的。
其他语言,如ObjectPascal、Delphi和C++ 使用静态类型,因此可以毫不含糊地知道分配给什么成员。这是静态类型的要点 -- 编译器 总是 在编译时知道每个变量的作用域。
Python使用动态类型。事先不可能知道在运行时引用哪个属性。可以动态地在对象中添加或删除成员属性。这使得无法通过简单的阅读就知道引用的是什么属性:局部属性、全局属性还是成员属性?
例如,采用以下不完整的代码段:
def foo(a):
with a:
print(x)
该代码段假设 "a" 必须有一个名为 "x" 的成员属性。然而,Python中并没有告诉解释器这一点。假设 "a" 是整数,会发生什么?如果有一个名为 "x" 的全局变量,它是否会在with块中使用?如您所见,Python的动态特性使得这样的选择更加困难。
然而,Python 可以通过赋值轻松实现 "with" 和类似语言特性(减少代码量)的主要好处。代替:
function(args).mydict[index][index].a = 21
function(args).mydict[index][index].b = 42
function(args).mydict[index][index].c = 63
写成这样:
ref = function(args).mydict[index][index]
ref.a = 21
ref.b = 42
ref.c = 63
这也具有提高执行速度的副作用,因为Python在运行时解析名称绑定,而第二个版本只需要执行一次解析。
为什么 if/while/def/class语句需要冒号?
冒号主要用于增强可读性(ABC语言实验的结果之一)。考虑一下这个:
if a == b
print(a)
与
if a == b:
print(a)
注意第二种方法稍微容易一些。请进一步注意,在这个FAQ解答的示例中,冒号是如何设置的;这是英语中的标准用法。
另一个次要原因是冒号使带有语法突出显示的编辑器更容易工作;他们可以寻找冒号来决定何时需要增加缩进,而不必对程序文本进行更精细的解析。
为什么Python在列表和元组的末尾允许使用逗号?
Python 允许您在列表,元组和字典的末尾添加一个尾随逗号:
[1, 2, 3,]
('a', 'b', 'c',)
d = {
"A": [1, 5],
"B": [6, 7], # last trailing comma is optional but good style
}
有几个理由允许这样做。
如果列表,元组或字典的字面值分布在多行中,则更容易添加更多元素,因为不必记住在上一行中添加逗号。这些行也可以重新排序,而不会产生语法错误。
不小心省略逗号会导致难以诊断的错误。例如:
x = [
"fee",
"fie"
"foo",
"fum"
]
这个列表看起来有四个元素,但实际上包含三个 : "fee", "fiefoo" 和 "fum" 。总是加上逗号可以避免这个错误的来源。
允许尾随逗号也可以使编程代码更容易生成。
公众号【Python猫】, 本号连载优质的系列文章,有喵星哲学猫系列、Python进阶系列、好书推荐系列、技术写作、优质英文推荐与翻译等等,欢迎关注哦。