Python 运算符优先级和增强赋值,包括序列
Python operator precedence with augmented assignment including sequence
跟进我有下面的。这些在 Python 中是否相同?
a += b[1] / 2
和
a += (b[1] / 2)
前提是:
a
之前已经定义为 float
b
是一个元组列表
b[1]
是一个只有一个元素的元组
同样,如果满足以下条件,我也有兴趣了解行为:
a
之前已经定义为 float
b
是一个浮点数列表
Python 如何解析表达式的规则在 Python grammar 中定义。请注意 类型 是不相关的 。事实上 Python 是 dynamically 类型,所以这意味着在解析和分析表达式时,变量的类型是 unknown.事实上,一个变量在整个过程中具有不同的值(具有不同的类型),并且一行可以被评估多次,变量每次都带有不同类型的值。
如果我们看一下语法,我们会看到:
expr: xor_expr ('|' xor_expr)*
xor_expr: and_expr ('^' and_expr)*
and_expr: shift_expr ('&' shift_expr)*
shift_expr: arith_expr (('<<'|'>>') arith_expr)*
arith_expr: term (('+'|'-') term)*
<b>term: factor (('*'|'@'|'/'|'%'|'//') factor)*</b>
factor: ('+'|'-'|'~') factor | power
power: atom_expr ['**' factor]
atom_expr: ['await'] atom trailer*
atom: ('(' [yield_expr|testlist_comp] ')' |
'[' [testlist_comp] ']' |
'{' [dictorsetmaker] '}' |
NAME | NUMBER | STRING+ | '...' | 'None' | 'True' | 'False')
testlist_comp: (test|star_expr) ( comp_for | (',' (test|star_expr))* [','] )
trailer: '(' [arglist] ')' | <b>'[' subscriptlist ']'</b> | '.' NAME
“订阅”(b[1]
中的[1]
因此在生产规则中定义trailer
,如果我们看语法,这只能是 factor
的乘积,所以这意味着 /
运算符优先于订阅。
所以这意味着:
a += b[1] / 2
相当于:
a += ((b[1]) / 2)
请注意,由于 Python 是动态类型的,因此解析(和分析)步骤不会保证表达式 有意义 。例如,一个元组不能被二除。所以这将导致 TypeError
:
>>> (2.0, 4.0) / 2
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: unsupported operand type(s) for /: 'tuple' and 'int'
然而,对于 numpy
数组,这是有道理的:
>>> from numpy import array
>>> array([2.0, 4.0])/2
array([1., 2.])
跟进
a += b[1] / 2
和
a += (b[1] / 2)
前提是:
a
之前已经定义为 floatb
是一个元组列表b[1]
是一个只有一个元素的元组
同样,如果满足以下条件,我也有兴趣了解行为:
a
之前已经定义为 floatb
是一个浮点数列表
Python 如何解析表达式的规则在 Python grammar 中定义。请注意 类型 是不相关的 。事实上 Python 是 dynamically 类型,所以这意味着在解析和分析表达式时,变量的类型是 unknown.事实上,一个变量在整个过程中具有不同的值(具有不同的类型),并且一行可以被评估多次,变量每次都带有不同类型的值。
如果我们看一下语法,我们会看到:
expr: xor_expr ('|' xor_expr)* xor_expr: and_expr ('^' and_expr)* and_expr: shift_expr ('&' shift_expr)* shift_expr: arith_expr (('<<'|'>>') arith_expr)* arith_expr: term (('+'|'-') term)* <b>term: factor (('*'|'@'|'/'|'%'|'//') factor)*</b> factor: ('+'|'-'|'~') factor | power power: atom_expr ['**' factor] atom_expr: ['await'] atom trailer* atom: ('(' [yield_expr|testlist_comp] ')' | '[' [testlist_comp] ']' | '{' [dictorsetmaker] '}' | NAME | NUMBER | STRING+ | '...' | 'None' | 'True' | 'False') testlist_comp: (test|star_expr) ( comp_for | (',' (test|star_expr))* [','] ) trailer: '(' [arglist] ')' | <b>'[' subscriptlist ']'</b> | '.' NAME
“订阅”(b[1]
中的[1]
因此在生产规则中定义trailer
,如果我们看语法,这只能是 factor
的乘积,所以这意味着 /
运算符优先于订阅。
所以这意味着:
a += b[1] / 2
相当于:
a += ((b[1]) / 2)
请注意,由于 Python 是动态类型的,因此解析(和分析)步骤不会保证表达式 有意义 。例如,一个元组不能被二除。所以这将导致 TypeError
:
>>> (2.0, 4.0) / 2
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: unsupported operand type(s) for /: 'tuple' and 'int'
然而,对于 numpy
数组,这是有道理的:
>>> from numpy import array
>>> array([2.0, 4.0])/2
array([1., 2.])