首页 » 父与子的编程之旅:与小卡特一起学Python » 父与子的编程之旅:与小卡特一起学Python全文在线阅读

《父与子的编程之旅:与小卡特一起学Python》21.4 数字格式化

关灯直达底部

打印数字时,我们希望对数字如何显示有一些控制:

  • 显示多少位小数;

  • 使用常规记法还是 E 记法;

  • 是否增加前导或末尾的 0;

  • 是否在数字前面显示正负号(+ 或 -)。

利用格式字符串,Python 为我们提供了充分的灵活性,不仅可以完成这些工作,甚至还可以做更多事情!

例如,如果你在使用一个天气预报程序,你想看到下面哪一个结果呢?是这样:

Today/'s High: 72.45672132, Low 45.4985756  

还是这样:

Today/'s High: 72, Low: 45  

适当地显示数字对很多程序来说都很重要。

下面先来看一个例子。假设我们想要打印一个有两位小数的浮点数。试着在交互模式中执行以下命令:

>>> dec_number = 12.3456>>> print /'It is %.2f degrees today./' % dec_numberIt is 12.35 degrees today  

print 语句中间包含一个格式字符串。不过这一次没有直接使用 %f,而是使用了 %.2f。这就告诉 Python 要采用浮点数格式,而且小数点后面要显示两位。(注意,Python 非常聪明,它会正确地把数字四舍五入为两位小数,而不是直接去掉多余的数位。)

这个字符串后面,第二个 % 字符告诉 Python 接下来就是要打印的数。这个数要采用格式字符串中描述的格式来打印。再看几个例子就能明白了。

你的记性不错,卡特! % 符号确实用作取余操作符(整数除法中求余数),这是我们在第 3 章中学过的,不过它也用于指示格式字符串。Python 能够区分出你是指取余还是格式字符串。

整数:%d%i

要把某项内容打印成整数,可以使用 %d%i 格式字符串。(我不知道为什么会有两个,不过用哪个都可以。)

>>> number = 12.67>>> print /'%i/' % number12  

注意,这一次数字没有四舍五入。它被截断(truncated,表示“直接切断”)了。如果是四舍五入,我们会看到 13 而不是 12。使用整数格式化时,数字会被截断,不过使用浮点数格式化时,数字则会四舍五入。

这里要注意以下 3 个方面。

  • 字符串中不要求有其他文本,可以只包含格式字符串。

  • 即使是浮点数,也可以把它打印为整数。这可以通过格式字符串实现。

  • Python 会把值截断为上一个最大整数1。不过,这与 int 函数(在第 4 章见过)不同,因为格式字符串不会像 int 那样创建一个新的值,而只是改变值显示的方式。

1原文这里是“下一个最小整数”,这是不对的。例如,13.2 会截断为 13,也就是上一个最大整数,而下一个最小整数应当是 14,13.2 当然不会截断为 14。——译者注

刚刚我们用整数格式打印 12.67,结果 Python 打印出了 12。不过变量 number 的值并没有改变。可以检查一下:

>>> print number12.67  

number 的值并没有改变。我们只是使用格式字符串采用不同的方式打印。

浮点数:%f%F

打印小数时,可以在格式字符串中使用大写或小写的 f(%f%F):

>>> number = 12.3456>>> print /'%f/' % number12.345600  

如果只使用 %f,数字会显示为有 6 位小数。如果在 f 前面加上 .n,这里 n 可以是任意整数,就会把数字四舍五入为指定的小数位数:

>>> print /'%.2F/' % number12.35  

可以看到它把数字 12.3456 四舍五入到小数点后前两位:12.35。

如果指定的小数位比数中实际的小数位还要多,Python 会用 0 来填充(pad):

>>> print /'%.8f/' % number12.34560000  

这个数的小数点后面只有 4 位,但我们要求有 8 位小数,所以另外 4 位会用 0 来填充。

如果是负数,%f 总会显示 -号。如果希望数字总会显示正负号(即使它是一个正数),可以在 % 后面加一个 + 号(如果列表中既有正数也有负数,这对于列表的对齐也很有好处):

>>> print /'%+f/' % number+12.345600  

如果希望包含正负数的列表对齐,但是不希望看到正数带 + 号,可以在 % 后面使用一个空格代替 +:

>>> number2 = -98.76>>> print /'% .2f/' % number2-98.76>>> print /'% .2f/' % number 12.35 

输出中的 12 前面有一个空格,所以,尽管 98 前面有负号而 12 前面没有正负号,这两个数也能对齐。

E 记法:%e%E

我们在第 3 章讨论过 E 记法,前面说过我会告诉你如何使用 E 记法来打印数字。好吧,现在就来介绍这个内容。

>>> number = 12.3456>>> print /'%e/' % number1.234560e+01  

要使用 %e 格式字符串打印 E 记法。它总是打印 6 位小数,除非你另作要求。

如果要打印更多或更少的小数位,可以在 % 后面使用 .n,就像打印浮点数时一样:

>>> number = 12.3456>>> print /'%.3e/' % number1.235e+01>>> print /'%.8e/' % number1.23456000e+01  

%.3e 四舍五入为 3 位小数,%.8e 增加了一些 0 来填充不足的小数位。

小写或大写 e 都是可以的,你在格式字符串中使用什么大小写形式,输出时也会显示同样的大小写:

>>> print /'%E/' % number1.234560E+01  

自动浮点数或 E 记法:%g%G

如果你希望 Python 自动选择浮点数记法或 E 记法,可以使用 %g 格式字符串。同样,如果使用大写,输出中就会得到一个大写的 E:

>>> number1 = 12.3>>> number2 = 456712345.6>>> print /'%g/' % number112.3>>> print /'%g/' % number24.56712e+08  

注意到了吗? Python 会为大数自动选择 E 记法,而对较小的数使用浮点数记法。

如何打印百分号

你可能很想知道,既然百分号(%)对格式字符串来说是一个特殊的字符,那么怎么打印 % 呢?

嗯,Python 有时候很聪明,它能确定你什么时候使用 % 符号开始一个格式字符串,以及什么时候只是想打印一个百分号。可以试试这个命令:

>>> print /'I got 90% on my math test!/'I got 90% on my math test!  

在这个例子中,字符串外面没有第二个 %,也没有需要格式化的变量,所以 Python 认为这个 % 只是字符串中的一个普通字符。

但是如果你在打印格式化字符串时想打印一个百分号,就需要输入两个百分号,就像你曾经用两个反斜线来打印一个反斜线一样。我们说第一个百分号对第二个百分号进行了转义,就像在本章前面的术语箱中提到的一样:

>>> math = 75.4>>> print /'I got %.1f%% on my math test/' % mathI got 75.4% on my math test  

第一个 % 表示格式化字符串。两个 %% 在一起告诉 Python,你希望打印出一个 % 字符。引号外面的 % 告诉 Python 你需要将后面的变量打印出来。

多个格式化字符串

如果你想在一个 print 语句中放入多个格式化字符串,该怎么办呢?你可以这样做:

>>> math = 75.4>>> science = 82.1>>> print /'I got %.1f in math and %.1f in science/' % (math, science)  

你可以在 print 语句中放入任意多个格式化字符串,后面跟一个变量元组(tuple)。还记得吗?元组和列表很像,只是它使用的是圆括号而不是方括号,而且元组是不可变的。这是 Python 显得很挑剔的一个地方,这里你必须使用元组,而不能使用列表。除非只有一个变量需要格式化,这时才可以不用元组。(你在很多例子中已经见过了。)请确保(引号内的)格式化字符串的数量和(引号外的)变量数量相同,否则程序会报错。

存储格式化数字

有时你不想直接打印出格式化的数字,而是希望把它存储在一个字符串中以备以后使用。这很容易,可以不打印,把它直接赋给一个变量,如下:

>>> my_string = /'%.2f/' % 12.3456>>> print my_string12.35>>> print /'The answer is/', my_stringThe answer is 12.35  

这里没有直接打印格式化数字,我们把它赋给变量 my_string。再将 my_string 与其他一些文本结合,并打印整个句子。

对于 GUI 和其他图形程序(如游戏)来说,将格式化数字存储为字符串非常有用。一旦有一个对应格式化字符串的变量名,就可以采用你希望的任何方式来显示:可以显示在文本框中,显示在对话框中,或者显示在游戏屏幕上。