Fil*_*efp 52 python language-lawyer python-2.7 python-3.x
我已经读过python中的所有东西都是一个对象,因此我开始尝试不同的类型并调用__str__
它们 - 起初我感到非常兴奋,但后来我感到困惑.
>>> "hello world".__str__()
'hello world'
>>> [].__str__()
'[]'
>>> 3.14.__str__()
'3.14'
>>> 3..__str__()
'3.0'
>>> 123.__str__()
File "<stdin>", line 1
123.__str__()
^
SyntaxError: invalid syntax
Run Code Online (Sandbox Code Playgroud)
something.__str__()
除了"一切"之外还要工作int
?123
不是一个对象类型的int
?Ned*_*der 88
你需要parens:
(4).__str__()
Run Code Online (Sandbox Code Playgroud)
问题是词法分析员认为"4".将成为一个浮点数.
此外,这有效:
x = 4
x.__str__()
Run Code Online (Sandbox Code Playgroud)
Fil*_*efp 49
123
就像一个对象一样3.14
,"问题"在于语言的语法规则; 解析器认为我们要定义一个float - 而不是一个带尾随方法调用的int.
如果我们将数字括在括号中,我们将得到预期的行为,如下所示.
>>> (123).__str__()
'123'
Run Code Online (Sandbox Code Playgroud)
或者如果我们只是在之后添加一些空格123
:
>>> 123 .__str__()
'123'
Run Code Online (Sandbox Code Playgroud)
它不工作的原因123.__str__()
是,点下面的123
解释为小数点一些部分宣布浮点.
>>> 123.__str__()
File "", line 1
123.__str__()
^
SyntaxError: invalid syntax
Run Code Online (Sandbox Code Playgroud)
解析器试图解释__str__()
为一个数字序列,但显然失败-我们得到的SyntaxError基本上说解析器在的东西,没想到偶然.
当在寻找123.__str__()
蟒解析器可以使用任一3个字符和解释这些3个字符为整数,或者它可以使用4个字符和解释这些作为开始一个的浮点.
123.__str__()
^^^ - int
Run Code Online (Sandbox Code Playgroud)
123.__str__()
^^^^- start of floating-point
Run Code Online (Sandbox Code Playgroud)
正如一个小孩子想要在他们的盘子上尽可能多的蛋糕,解析器是贪婪的,并且想尽可能多地吞下 - 即使这并不总是最好的想法 - 如后者选择("更好")替代方案.
当它后来意识到它__str__()
决不能被解释为浮点的小数时,它已经太晚了; SyntaxError.
注意
Run Code Online (Sandbox Code Playgroud)123 .__str__() # works fine
在上面的代码片段中,
123
(注意空格)必须解释为整数,因为没有数字可以包含空格.这意味着它在语义上等同于(123).__str__()
.
注意
Run Code Online (Sandbox Code Playgroud)123..__str__() # works fine
以上也有效,因为一个数字最多可以包含一个小数点,这意味着它等价于
(123.).__str__()
.
本节包含相关文字的词汇定义.
floatnumber ::= pointfloat | exponentfloat
pointfloat ::= [intpart] fraction | intpart "."
exponentfloat ::= (intpart | pointfloat) exponent
intpart ::= digit+
fraction ::= "." digit+
exponent ::= ("e" | "E") ["+" | "-"] digit+
Run Code Online (Sandbox Code Playgroud)
integer ::= decimalinteger | octinteger | hexinteger | bininteger
decimalinteger ::= nonzerodigit digit* | "0"+
nonzerodigit ::= "1"..."9"
digit ::= "0"..."9"
octinteger ::= "0" ("o" | "O") octdigit+
hexinteger ::= "0" ("x" | "X") hexdigit+
bininteger ::= "0" ("b" | "B") bindigit+
octdigit ::= "0"..."7"
hexdigit ::= digit | "a"..."f" | "A"..."F"
bindigit ::= "0" | "1"
Run Code Online (Sandbox Code Playgroud)
Sve*_*ach 41
在以下后面添加一个空格4
:
4 .__str__()
Run Code Online (Sandbox Code Playgroud)
否则,将词法分析器这个表达式分成令牌"4."
,"__str__"
,"("
和")"
,即第一令牌被解释为一个浮点数.词法分析器总是尝试构建最长的令牌.
实际上(增加不可读性......):
4..hex()
Run Code Online (Sandbox Code Playgroud)
也是有效的.它给了'0x1.0000000000000p+2'
- 但是当然它是一个漂浮物,当然......