第五章 数字

5.1 数字类型
  数字提供了标量贮存和直接访问。它是不可更改类型,也就是说变更数字的值会生成新的对象。当然,这个过程无论对程序员还是对用户都是透明的,并不会影响软件的开发方式。python 支持多种数字类型:整型、长整型、布尔型、双精度浮点型、十进制浮点型和复数。

如何更新数字对象
  因为实际上你并没有更新该对象的原始数值。这是因为数值对象是不可改变对象。Python 的对象模型与常规对象模型有些不同。你所认为的更新实际上是生成了一个新的数值对象,并得到它的引用。
在学习编程的过程中, 我们一直接受这样的教育, 变量就像一个盒子, 里面装着变量的值。在Python 中, 变量更像一个指针指向装变量值的盒子。 对不可改变类型来说, 你无法改变盒子的内容, 但你可以将指针指向一个新盒子。每次将另外的数字赋给变量的时候,实际上创建了一个新的对象并把它赋给变量.(不仅仅是数字,对于所有的不可变类型,都是这么回事)
anInt += 1
aFloat = 2.718281828
如何删除数字对象
  按照Python 的法则, 你无法真正删除一个数值对象, 你仅仅是不再使用它而已。如果你
实际上想删除一个数值对象的引用, 使用 del 语句(参见3.5.6 小节)。 删除对象的引用之
后, 你就不能再使用这个引用(变量名), 除非你给它赋一个新值。如果试图使用一个已经被
删除的对象引用, 会引发NameError 异常。
del anInt
del aLong, aFloat, aComplex

5.3 双精度浮点数
Python 中的浮点数类似C 语言中的double 类型, 是双精度浮点数,可以用直接的十进制或科学计数法表示。每个浮点数占8 个字节(64 比特),完全遵守IEEE754 号规范(52M/11E/1S),其中52 个比特用于表示底,11 个比特用于表示指数(可表示的范围大约是正负10 的308.25次方), 剩下的一个比特表示符号。这看上去相当完美,然而,实际精度依赖于机器架构和创建Python 解释器的编译器。浮点数值通常都有一个小数点和一个可选的后缀e(大写或小写,表示科学计数法)。在e和指数之间可以用正(+)或负(-)表示指数的正负(正数的话可以省略符号)。下面是一些典型的浮点数值的例子:
0.0   -777.   1.6   -5.555567119   96e3 * 1.0
4.3e25   9.384e-23   -2.172818   float(12)   1.000000001
3.1416   4.2E-10   -90.   6.022e23   -1.609E-19

5.4 复数

下面是Python 语言中有关复数的几个概念:
?? 虚数不能单独存在,它们总是和一个值为 0.0 的实数部分一起来构成一个复数。
?? 复数由实数部分和虚数部分构成
?? 表示虚数的语法: real+imagj
?? 实数部分和虚数部分都是浮点数
?? 虚数部分必须有后缀j 或J。
下面是一些复数的例子:
64.375+1j   4.23-8.5j   0.23-8.55j   1.23e-045+6.7e+089j
6.23+1.5j   -1.23-875J 0+1j   9.80665-8.31441J   -.0224+0j

表 5.1 复数属性
  属性 描述
    num.real 该复数的实部
    num num.imag 该复数的虚部
    num.conjugate() 返回该复数的共轭复数

>>> aComplex = -8.333-1.47j
>>> aComplex
(-8.333-1.47j)
>>> aComplex.real
-8.333
>>> aComplex.imag
-1.47
>>> aComplex.conjugate()
(-8.333+1.47j)
表5.1 描述了复数的所有属性

5.5.1 混合模式运算符
  也许你还记得, 过去将两个数相加时, 你必须努力保证操作数是合适的类型。自然而然的,加法总是使用 + 号, 然而在计算机语言看来这件事没那么简单,因为数字又有很多不同的类型。
  当两个整数相加时, + 号表示整数加法, 当两个浮点数相加时, + 表示浮点数加法, 依此类推。在Python 中, 甚至非数字类型也可以使用 + 运算符。举例来说, 字符串A + 字符串B 并不表示加法操作, 它表示的是把这两个字符串连接起来, 生成一个新的字符串。关键之处在于支持 + 运算符的每种数据类型, 必须告诉Python, + 运算符应该如何去工作。 这也体现了重载概念的具体应用。

  首先,如果两个操作数都是同一种数据类型,没有必要进行类型转换。仅当两个操作数类型不一致时, Python 才会去检查一个操作数是否可以转换为另一类型的操作数。如果可以,转换它并返回转换结果。由于某些转换是不可能的,比如果将一个复数转换为非复数类型, 将一个浮点数转换为整数等等,因此转换过程必须遵守几个规则。将一个整数转换为浮点数,只要在整数后面加个 .0 就可以了。 要将一个非复数转换为复数,则只需要要加上一个 “0j” 的虚数部分。这些类型转换的基本原则是: 整数转换为浮点数, 非复数转换为复数。 在Python 语言参考中这样描述 coerce() 方法:
?? 如果有一个操作数是复数, 另一个操作数被转换为复数。
?? 否则,如果有一个操作数是浮点数, 另一个操作数被转换为浮点数。
?? 否则, 如果有一个操作数是长整数,则另一个操作数被转换为长整数;
?? 否则,两者必然都是普通整数,无须类型转换

传统除法
  如果是整数除法, 传统除法会舍去小数部分,返回一个整数(地板除)。如果操作数之一是浮点数,则执行真正的除法。包括Python 语言在内的很多语言都是这种行为。看下面的例子:
>>> 1 / 2 # perform integer result (floor) # 地板除
0
>>> 1.0 / 2.0 # returns actual quotient#真正除法
0.5

真正的除法
  除法运算总是返回真实的商, 不管操作数是整数还是浮点数。在未来版本的Python 中,这将是除法运算的标准行为。现阶段通过执行 from __future__ import division 指令, 也可以做到这一点。
>>> from __future__ import division
>>>
>>> 1 / 2 # returns real quotient
0.5
>>> 1.0 / 2.0 # returns real quotient
0.5

地板除
从Python 2.2 开始, 一个新的运算符 // 已经被增加进来, 以执行地板除: // 除法不
管操作数何种数值类型,总是舍去小数部分,返回数字序列中比真正的商小的最接近的数字。
>>> 1 // 2 # floors result, returns integer # 地板除, 返回整数
0
>>> 1.0 // 2.0 # floors result, returns float # 地板除, 返回浮点数
0.0
>>> -1 // 2 # move left on number line# 返回比 –0.5 小的整数, 也就是 -1
-1

幂运算
  幂运算操作符和一元操作符之间的优先级关系比较特别: 幂运算操作符比其左侧操作数
的一元操作符优先级低,比
起右侧操作数的一元操作符的优先级高,由于这个特性你会在算术运算符表中找到两个
** .下面举几个例子:
>>> 3 ** 2
9
>>> -3 ** 2 # ** 优先级高于左侧的 -
-9
>>> (-3) ** 2 # 加括号提高 -的优先级
9
>>> 4.0 ** -1.0 # ** 优先级低于右侧的 -
0.25

5.6.2 数字类型函数
  Python 现在拥有一系列针对数字类型的内建函数。一些函数用于数字类型转换, 另一些执行一些常用运算。
转换工厂函数
函数 int(), long(), float() 和 complex() 用来将其它数值类型转换为相应的数值类型。

  下面是一些使用内建函数的示例:
>>> int(4.25555)
4
>>> long(42)
42L
>>> float(4)
4.0
>>> complex(4)
(4+0j)
>>>

>>> complex(2.3e-10, 45.3e4)
(2.3e-10+453000j)
          表5.5 数值工厂函数总结
          类(工厂函数)       操作
            bool(obj) b      返回obj对象的布尔值,也就是obj.__nonzero__()方法的返回值
                   int(obj, base=10)    返回一个字符串或数值对象的整数表示, 类似string.atoi();从Python 1.6,
            long(obj, base=10)    返回一个字符或数据对象的长整数表示,类似string.atol(), 从ython1.6                                                                   起,引入了可选的进制参数
            float(obj)      返回一个字符串或数据对象的浮点数表示,类似string.atof()complex(str)                                                             orcomplex(real, imag=0.0) 返回一个字符串的复数表示

功能函数
  Python 有五个运算内建函数用于数值运算: abs(), coerce(), divmod(), pow(), pow()
和 round()。

  abs()返回给定参数的绝对值。如果参数是一个复数, 那么就返回math.sqrt(num.real2 +
num.imag2)。下面是几个abs()函数的示例:
>>> abs(-1)
1
>>> abs(10.)
10.0
>>> abs(1.2-2.1j)
2.41867732449
>>> abs(0.23 - 0.78)
0.55
  函数coerce(),尽管从技术上讲它是一个数据类型转换函数,不过它的行为更像一个运算
符,因此我将它放到了这一小节。在5.5.1 小节,我们讨论了Python 如何执行数值类型转换。
函数coerce()为程序员提供了不依赖Python 解释器, 而是自定义两个数值类型转换的方法。
对一种新创建的数值类型来说, 这个特性非常有用。函数coerce()仅回一个包含类型转换完
毕的两个数值元素的元组。下面是几个例子:

>>> coerce(1, 2)
(1, 2)
>>>
>>> coerce(1.3, 134L)
(1.3, 134.0)
>>>
>>> coerce(1, 134L)
(1L, 134L)
>>>
>>> coerce(1j, 134L)
(1j, (134+0j))
>>>
>>> coerce(1.23-41j, 134L)
((1.23-41j), (134+0j))
  divmod()内建函数把除法和取余运算结合起来, 返回一个包含商和余数的元组。对整数来
说, 它的返回值就是地板除和取余操作的结果。对浮点数来说, 返回的商部分是
math.floor(num1/num2),对复数来说, 商部分是ath.floor((num1/num2).real)。
>>> divmod(10,3)
(3, 1)
>>> divmod(3,10)

(0, 3)
>>> divmod(10,2.5)
(4.0, 0.0)
>>> divmod(2.5,10)
(0.0, 2.5)
>>> divmod(2+1j, 0.5-1j)
(0j, (2+1j))
函数 pow() 和双星号 (**) 运算符都可以进行指数运算。不过二者的区别并不仅仅在于
一个是运算符,一个是内建函数。
在Python 1.5 之前,并没有 ** 运算符。内建函数pow()还接受第三个可选的参数,一个
余数参数。如果有这个参数的, pow() 先进行指数运算,然后将运算结果和第三个参数进行取
余运算。这个特性主要用于密码运算,并且比 pow(x,y) % z 性能更好, 这是因为这个函数的
实现类似于C 函数 pow(x,y,z)。
>>> pow(2,5)
32
>>>
>>> pow(5,2)
25
>>> pow(3.141592,2)
9.86960029446
>>>
>>> pow(1+1j, 3)
(-2+2j)

内建函数round()用于对浮点数进行四舍五入运算。它有一个可选的小数位数参数。如果
不提供小数位参数, 它返回与第一个参数最接近的整数(但仍然是浮点类型)。第二个参数告
诉round 函数将结果精确到小数点后指定位数。
>>> round(3)
3.0
>>> round(3.45)
3.0
>>> round(3.4999999)
3.0
>>> round(3.4999999, 1)
3.5
>>> import math

  值得注意的是 round() 函数是按四舍五入的规则进行取整。也就是round(0.5)得到1,
round(-0.5)得到-1。猛一看 int(), round(), math.floor() 这几个函数好像做的是同一件
事, 很容易将它们弄混,是不是?下面列出它们之间的不同之处:
?? 函数 int()直接截去小数部分。(返回值为整数)
?? 函数 floor()得到最接近原数但小于原数的整数。(返回值为浮点数)
?? 函数 round()得到最接近原数的整数。(返回值为浮点数)
?? 的例子用四个正数和四个负数作为这三个函数的参数,将返回结果列在一起做个比较。
(为了便于比较,我们将int()函数的返回值也转换成了浮点数)。

int(0.2) +0.0
floor(0.2) +0.0
round(0.2) +0.0
--------------------
int(0.7) +0.0
floor(0.7) +0.0
round(0.7) +1.0
--------------------
int(1.2) +1.0
floor(1.2) +1.0
round(1.2) +1.0
--------------------
int(1.7) +1.0
floor(1.7) +1.0
round(1.7) +2.0
--------------------
int(-0.2) +0.0
floor(-0.2) -1.0
round(-0.2) +0.0

仅适用于整数的内建函数
  函数       操作
hex(num)   将数字转换成十六进制数并以字符串形式返回
oct(num)   将数字转换成八进制数并以字符串形式返回
chr(num)   将ASCII值的数字转换成ASCII字符,范围只能是0 <= num <= 255。
ord(chr)   接受一个 ASCII 或 Unicode 字符(长度为1的字符串),返回相应的ASCII或Unicode 值。
unichr(num)  接受Unicode码值,返回 其对应的Unicode字符。所接受的码值范围依赖于你的Python是构建于UCS‐2还是UCS‐4。

5.7.1 布尔“数”
  从Python2.3 开始,布尔类型添加到了Python 中来。尽管布尔值看上去是“True” 和“False,
但是事实上是整型的子类,对应与整数的1 和0。下面是有关布尔类型的主要概念:
?? 有两个永不改变的值 True 或False。
?? 布尔型是整型的子类,但是不能再被继承而生成它的子类。
?? 没有__nonzero__()方法的对象的默认值是 True。
?? 对于值为零的任何数字或空集(空列表、空元组和空字典等)在Python 中的布尔值是False。
?? 在数学运算中,Boolean 值的True 和False 分别对应于1 和 0。
?? 以前返回整数的大部分标准库函数和内建布尔型函数现在返回布尔型。
?? True 和False 现在都不是关键字,但是在Python 将来的版本中会是。

5.8 相关模块
在Python 标准库中有不少专门用于处理数值类型对象的模块,它们增强并扩展了内建函数
的功能和数值运算的功能。 表5.8 列出了几个比较核心的模块。要详细了解这些模块,请参阅
这些模块的文献或在线文档。
对高级的数字科学计算应用来说,你会对著名的第三方包 Numeric(NumPy) 和SciPy 感兴
趣。关于这两个包的详细请访问下面的网址。
http://numeric.scipy.org/
http://scipy.org/
表5.8 数字类型相关模块

模块     介绍
decimal      十进制浮点运算类 Decimal
array       高效数值数组(字符,整数,浮点数等等)
math/cmath     标准C库数学运算函数。常规数学运算在match模块,复数运算在cmath模块
operator       数字运算符的函数实现。比如 tor.sub(m,n)等价

核心模块: random
当你的程序需要随机数功能时,random 模块就能派上用场。该模块包含多个伪随机数发生
器,它们均以当前的时间戳为随机数种子。这样只要载入这个模块就能随时开始工作。下面列
出了该模块中最常用的函数:
两个整数参数,返回二者之间的随机整数

randrange()     它接受和 range() 函数一样的参数, 随机返回range([start,]stop[,step])结果的一项
uniform()      几乎和 randint()一样,不过它返回的是二者之间的一个浮点数(不包括范围上限)。
random()     类似 uniform() 只不过下限恒等于0.0,上限恒等于1.0
choice()     随机返回给定序列(关于序列,见第六章)的一个元素

  

时间: 2024-11-17 20:54:45

第五章 数字的相关文章

[python核心编程] 第五章练习题

第五章 数字 5-2. 操作符,写一个函数,计算并返回两个数的乘积“整理的时候才看到我把题目看成两个数的和了” 5-3. 标准类型操作符.写一段脚本,输入一个测验成绩,根据下面的标准,输出他的评分成绩(A-F) A:90~100 B:80~89 C:70~79 D:60~69 F:<60 5-4. 取余.判断给定年份是否是闰年.使用下面的公式. 一个闰年后就是指他可以被4整除,但不能被100整除,或者它可以被400整除. [python核心编程] 第五章练习题,布布扣,bubuko.com

Python核心编程第五章习题

Python核心编程-第五章-习题 5.1  整形,讲讲Python普通整形与长整形的区别? Python的标准整形类型是最通用的数字类型.在大多数32位机器上,标准整形类型的取值范围是-2**32-2**32 - 1. Python的长整型类型能表达的数值仅仅与你的机器支持的(虚拟)内存大小有关,换句话说,Python能轻松表达很大的整数. 长整型类型是标准整形类型的超集,当程序需要使用比标准整形更大的整型时,可以使用长整型类型,在整型值后面添加L,表示这个为长整型,3.0版本已经统一称为为整

python核心编程-第五章-个人笔记

1.用del删除对对象的引用 >>> a = 123 >>> a 123 >>> del a >>> a Traceback (most recent call last): File "<stdin>", line 1, in <module> NameError : name 'a' is not defined 2.整型 (1)布尔型    该类型取值范围只要两个值:布尔值True 和

python核心编程第五章练习-5.17-随机序列

5-17  生成一个有 N 个元素的由随机数 n 组成的列表, 其中 N 和 n 的取值范围分别为: (1 <N <= 100), (0 <= n <= 2**31 -1).然后再随机从这个列表中取 N (1 <= N <= 100)个随机数出来, 对它们排序,然后显示这个子集. #!/usr/bin/python import random N = random.randint(2, 100)  #随机获取一个指定范围内的整数 randlist = random.sa

python核心编程第五章练习-5.11-最大公约数和最小公倍数

a.求两个数的最大公约数 def common_divisor(a, b): for i in range(1, min(a, b) + 1): if a % i == 0 and b % i ==0: m = i print ("The common divisor is %d" %m) 一开始对上面这段代码始终没理解,为什么得到是就仅仅是6,因为按照目测,1, 2, 3, 6均符合if的条件,应该都会打印出来. 讨教之后才知道是因为没有区分代码组,print()的位置决定了它最终打

python核心编程--第六章 6.22 练习

6.22 练习 初学python,如果代码有问题,欢迎指正. #!/usr/bin/python # -*- coding: utf-8 -*- #6–1. 字符串.string 模块中是否有一种字符串方法或者函数 #可以帮我鉴定一下一个字符串是否是另一个大字符串的一部分? import string ss = "I'm chinese." substr = 'chinese' index = ss.find(substr) if index == -1: print("No

python核心编程--第其章 7.12 练习

7.12 练习 #!/usr/bin/python # -*- coding: utf-8 -*- # 7–5. userpw2.py. 下面的问题和例题7.1 中管理名字-密码的键值对数据的程序有关. # (a) 修改那个脚本,使它能记录用户上次的登录日期和时间(用time 模块), # 并与用户密码一起保存起来.程序的界面有要求用户输入用户名和密码的提示. # 无论户名是否成功登录,都应有提示,在户名成功登录后,应更新相应用户的上次 # 登录时间戳.如果本次登录与上次登录在时间上相差不超过4

Python核心编程_第二章课后习题

以下是自己在学习Python核心编程时,做的课后练习题.现在把它们贴出来,以记录自己的学习过程.小弟是机械出身,很多练习题目写的很是机械.虽然写出来的脚本都能满足题目要求,但效率可能不是最好的,所以,小弟还是厚着脸皮把它们给贴出来,一来可以让高手指点,二来可以与我一样在学习Python的兄弟共同学习. 以下的程序均以题目标号命名,如2-3这个题目,程序名就为2_3.py. 习题2_3.py #!/usr/bin/env python A = 10 B = 4 print "A plus B is

python核心编程-习题-第二章

PS:PDF在线地址:http://bcmi.sjtu.edu.cn/~zhaohai/ptm2012/data/Python-kernel.programming.v2.pdf 2-1  变量,print 和字符串格式化运算符.启动交互式解释器,给一些变量赋值(字符串,数值等等)并通过输入变量名显示它们的值.再用 print 语句做同样的事.这二者有何区别? 也尝试着使用字符串格式运算符%,多做几次,慢慢熟悉. # -*- coding:utf-8 -*- >>>a = 123 >

【7】python核心编程 第十一章-函数和函数式编程

1.*函数(与方法)装饰器 装饰器背后的主要动机源自python 面向对象编程.装饰器是在函数调用之上的修饰.这些修饰 仅是当声明一个函数或者方法的时候,才会应用的额外调用. 装饰器的语法以@开头,接着是装饰器函数的名字和可选的参数.紧跟着装饰器声明的是被修饰 的函数,和装饰函数的可选参数.装饰器看起来会是这样: @decorator(dec_opt_args) def func2Bdecorated(func_opt_args): : 那么什么是装饰器? 现在我们知道装饰器实际就是函数.我们也