访问所有types的文字工作属性,但不是`int`; 为什么?

我已经读过,python中的所有东西都是一个对象,因此我开始尝试不同的types,并在其上调用__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 
  • 为什么something .__str__()除了int之外还有其他所有的东西?
  • 123不是inttypes的对象吗?

你需要parens:

 (4).__str__() 

问题是词法分析器认为“4” 将会是一个浮点数。

另外,这工作:

 x = 4 x.__str__() 

所以你认为你可以跳舞浮点?

1233.14一样多,“问题”在于语言的语法规则; parsing器认为我们即将定义一个浮点数 – 而不是一个带有尾随方法调用的int

如果我们用圆括号包装数字,我们将得到预期的行为,如下所示。

 >>> (123).__str__() '123' 

或者如果我们简单地在123之后添加一些空格:

 >>> 123 .__str__() '123' 

它不适用于123.__str__()123后面的被解释为某个部分声明的浮点的小数点

 >>> 123.__str__() File "", line 1 123.__str__() ^ SyntaxError: invalid syntax 

parsing器尝试将__str__()解释为数字序列,但是显然失败了 – 我们得到一个SyntaxError,基本上说parsing器偶然发现了一些没有想到的东西。


当查看123.__str__() ,pythonparsing器可以使用3个字符并将这3个字符解释为一个整数 ,也可以使用4个字符并将其解释为浮点的开始

 123.__str__() ^^^ - int 
 123.__str__() ^^^^- start of floating-point 

就像一个小孩子想要尽可能多的蛋糕一样,parsing器是贪婪的,想立刻吞下尽可能多的东西 – 即使这并不总是最好的想法 – 就像后者(“更好”)select。

当它后来认识到__str__()不能被解释为浮点小数点时 ,它已经太晚了; SyntaxError

注意

  123 .__str__() # works fine 

在上面的代码片段中, 123 (注意空格)必须被解释为一个整数,因为没有数字可以包含空格。 这意味着它在语义上等价于(123).__str__()

注意

  123..__str__() # works fine 

因为一个数最多可以包含一个小数点 ,这意味着它等价于(123.).__str__()


对于语言律师来说

本部分包含相关文字的词汇定义。

词法分析 – 2.4.5浮点文字

 floatnumber ::= pointfloat | exponentfloat pointfloat ::= [intpart] fraction | intpart "." exponentfloat ::= (intpart | pointfloat) exponent intpart ::= digit+ fraction ::= "." digit+ exponent ::= ("e" | "E") ["+" | "-"] digit+ 

词法分析 – 2.4.4整数文字

 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" 

4

 4 .__str__() 

否则,词法分析器将把这个expression式分解成标记"4.""__str__""("")" ,即第一个标记被解释为一个浮点数。 词法分析器总是试图build立最长的标记。

实际上(增加不可读性…):

 4..hex() 

也是有效的。 它给出'0x1.0000000000000p+2' – 但那么这是一个浮动,当然…