Python 学习笔记 (II-B)

Tip 2-28: Python判断一个数字表达式的类型,如果只有数字,则判断为整数,如果包含小数点或者浮点e,则判断为浮点数,浮点数采取 C - double 的方式处理。python 即认为数字表达式为虚数。0x???, 0o???, 0b??? 来表示一个十六进制、八进制、二进制的整数。使用 hex(num), oct(num), bin(num) 则可以返回整数在这些进制下表达的字符串。复数的话,必须显式声明虚部 (即便是 1+0j),也可以用 complex(r, i) 的方式构造一个虚数。

Tip 2-29: 在 Python 3.0+ 基本的数值类型有 int, float 和 complex (这个通过 type 函数可以看到)。其中 int 可以是基本长度的或者是完全不限长度的大整数,其表现也可以用其他常用进制表示。

Tip 2-30: 基本数值类型支持的操作以及运算符,可以通过 dir 或者 help 一个给定类型的数值来查看,很多的。

Tip 2-31: Python 根据运算符优先级决定运算顺序,这与类型无关。Python 在执行运算符时,会“向上转换”操作数,将低精度转换成与另一个操作数相同的较高精度,再执行运算。数值的精度顺序是:int < float < complex。当然,也可以使用 int(3.0), float(1) 这样的方式进行强制转换。

Tip 2-32: 关于变量:1. 变量在第一次被赋值的时候创建; 2. 变量在表达式中使用的时候会被替换成它的值; 3. 变量没赋值前不能在表达式中使用; 3. 变量总是引用一个对象,并且不能事先声明。

Tip 2-33: Python 的比较表达式可以被串联,也就是说 1<a>3 这样的表达式是合法的,它将会被解析成两个表达式的与,即 (1<a and a>3)。

Tip 2-34: 整除运算符 // 逻辑上等价于除了之后向下取整,其返回的对象类型为两个操作数的较高者,也就是说 5//3 将返回一个 int 类型,而 5//3.0 或者 5.0//3 将返回一个 float(1)。另外,在 Python 3 以前,整数 / 整数将返回整除的结果,而 Python 3.0+ 将返回一个浮点数的除法结果。

Tip 2-35: 在 3.0 之前的版本,整数有两种类型,普通型和长整形,长整形以 L 结尾,例如:10000L,而在 3.0+ 则将这两种类型实质上合并了。

Tip 2-36: Decimal 类型使用 Decimal('X.YYYY') 的字符串 + 构造型来表达一个十进制数,其小数点精度位数即在串中反映。若不同精度的 Decimal 之间进行加减运算,结果会产生一个运算数中最高精度的 Decimal。Decimal 不能与 float 进行运算。

Tip 2-37: 也可以在全局设定 Decimal 的精度,Decimal 有一个上下文 context 的概念,在同一个上下文中可以设置 decimal 的精度(个人认为这样的设置很不优美,假如需要在同一个上下文环境中同时使用两种不同精度的十进制数呢?),并设置其整个上下文的精度。

 

# 设置全局 decimal 精度
>>> 1999 + 1.33
2000.3299999999999
>>>
>>> decimal.getcontext().prec = 2
>>> pay = decimal.Decimal(str(1999 + 1.33))
>>> pay
Decimal('2000.33')

# 在一个上下文中设置 decimal 精度
>>> decimal.Decimal('1.00') / decimal.Decimal('3.00')
Decimal('0.3333333333333333333333333333')
>>>
>>> with decimal.localcontext() as ctx:
... ctx.prec = 2
... decimal.Decimal('1.00') / decimal.Decimal('3.00')
...
Decimal('0.33')
>>>
>>> decimal.Decimal('1.00') / decimal.Decimal('3.00')
Decimal('0.3333333333333333333333333333')

 

Tip 2-38: Fraction 通过显式保存整形的分子和分母来表示分数,以避免精度损失,可以通过分子和分母的形式,或者浮点字符串的形式来构造一个 Fraction。

Tip 2-39: * 运算符是一个有力的工具(3.0+),可以将一个元组展开变成一系列参数,而不是将元组作为一个单一的参数使用。

Tip 2-40: 浮点数有一个方法 .as_integer_ratio(),可以将浮点数转换为有理数形式,用一个二元组返回分子和分母。

Tip 2-41: Fraction 的转换级别高于 int 低于 float。

Tip 2-42: 可以通过 limit_denominator(lim) 方法来限定近似一个分数的分母。例如:Fraction(21,100).limit_denominator(10) 将返回 Fraction(1, 5)。

Tip 2-43: set 是一个集合类型,mutable,可以进行迭代和在位操作。注意 {} 是一个 dictionary 而不是 set,而 {0} 是一个 set,这是一个特殊情况,构造一个空集合可以用 set() 来获得。

Tip 2-44: 注意,无论是 dictionary 的 key 还是 set 的元素,由于是使用 hash 进行映射,因此都必须是 hashable 的,也就是说必须是 immutable 的。

Tip 2-45: 由于 Python 的动态类型特性,变量的类型在运行时才被确定,而在代码中不需要声明类型。

Tip 2-46: 变量在第一次被赋值的时候被创建,再次赋值时就被修改,类型不在变量名中,而在对象之中,变量和对象是分离的。程序执行时,变量名会被直接替换成它链接到的对象本身,而不管这个对象是什么。注意分清“对象”和“变量名”这两个不同的概念,在 python 中相当重要。

Tip 2-47: 一个赋值语句的执行分为三步:第一步,根据右值创建对象;第二步,看左值,如果没有这个变量名则创建一个变量名;第三步,将对象链接到变量名之上。

Tip 2-48: 这种链接在 Python 中叫做“引用 (reference)”,Python 的变量名存放在一个系统表中,然后它的引用指向对象所在的内存地址。

Tip 2-49: 对象有两个基本的属性:类型和引用计数。前者用于识别对象的类型(变量名引用它的时候就可以进绑定),后者用于垃圾回收。

Tip 2-50: Python 通过存放在对象中的引用计数来进行垃圾回收,赋值操作使得对象中的引用计数发生改变,当引用数为 0 的时候,垃圾回收器就会回收该变量占用的资源。

Tip 2-51: 变量的引用只会从变量名直接引用到对象,如果将一个变量 a 赋值给另一个变量 b (b=a),则会将 b 引用至 a 背后对应的对象,即 a 和 b 同时引用一个对象,即使后来 a 的引用发生改变,b 也还是引用到那个对象。这种多个变量引用同一个对象的情况叫做“共享引用 (shared reference)”。

Tip 2-52: 对于诸如 list 这样的 mutable 的对象,如果出现共享引用的情况,通过一个变量可以修改到对象的内容,这时会导致另一个变量的值也发生改变(引用没有变,但是对象变了)。因此对于这些 mutable 的对象类型应尽量避免共享引用。如果想避免共享引用导致的原对象修改,可使用 copy 来生成一个副本。也可使用诸如 L2 = L1[:] 的方式来创建一个副本。

Tip 2-53: import copy 之后,可以使用 copy.copy(x) 或者 copy.deepcopy(x) 来复制对象,如果使用 copy,则只有第一层的 mutable 对象会被复制,而其元素指向的对象则不会被复制,使用 deepcopy 则会递归复制所有引用到的对象。

Tip 2-54: 大部分对象还是会在失去引用后被删掉,但对于一些小的整数和字符串,python 则不会这么做,而用一张系统表缓存这些常用的对象,以备后用。

Tip 2-55: 使用 == 来判别两个变量值是否相等,使用 is 来判别两个变量是否引用同一个对象。

Tip 2-56: 使用 sys.getrefcount(x) 函数可以返回一个变量当前的引用计数。

Tip 2-57: python 串有两种,一种用来存放 unicode 字符(每个位置一个 unicode 字符),另一种是二进制字符串(每个位置一个二进制位):在 3.0+ 版本,前者的类型是 str(表现为 '字符串'),后者的类型为 bytes(表现为 b'\xd7\xd6\xb7\xfb\xb4\xae');在 2.X 版本,前者的类型是 unicode,后者的类型是 str。

Tip 2-58: bytearray 类型是一种 mutable 的串类型,自2.6版本之后支持。

Tip 2-59: 可以用单引号或双引号界定单行字符串,用连续三个单引号或者双引号界定多行字符串,用斜杠开头的转义字符等等,如不使用转义字符可以 r 开头声明为 raw string。注意,使用 raw string 的时候 \' 和 \" 还是会被转义。

Tip 2-60: 连续的字符串变量将自动被串接成一个。

Tip 2-61: 多行字符串可用于临时性注释。

Tip 2-62: python 不允许直接用字符串串接一个数字,它不会自动做转换(貌似 php 是可以的,这点不同)。

Tip 2-63: 采用所有序列 slicing 同样的方法,可以对字符串进行切片操作,另外可以使用 slice(a, b, c) 缺省使用 None 来构造一个 slice 对象

 

>>> S = "abcdefgh"
>>> S[::-1]
'hgfedcba'
>>> slc = slice(None, None, -1)
>>> S[slc]
'hgfedcba'

 

Tip 2-64: 字符串与数字等之间的转换,可以使用类型转换 (int(s), float(s), str(x) 等)、repr、eval 等,字符与 asc 码之间可以使用 ord 和 chr 来转换 (中文也可以的)。

Tip 2-65: 格式化字符串有两种方式:格式化表达式和格式化函数。格式化表达式采用类似 C printf 的方式来指定格式化字符串,采取 sformat % (para0 [,para1...]) 的方式调用,但有可能在以后的版本被淘汰;格式化函数使用 sformat.format(parameters) 的方式调用。

Tip 2-66: 格式化表达式中,无论任何变量都可以使用 %s 进行输出。与 C printf 不同,还可以使用 %(name)? 的方式来指定输出变量,然后在 % 的右运算符指定 { name : value } 的方式来格式化输出 value 这个值。

Tip 2-67: 函数调用的参数分为 keyword arg 和 non-keyword arg,keyword arg 必须放在所有 non-keyword arg 后面。format 方法使用 {} 界定输出参数,可以(同时)使用 keyword 和 non-keyword 两种模式指定输出参数。

Tip 2-68: format 函数格式化字段的一般形式为 {fieldname!conversionflag:formatspec},其中 conversionflag 的选项为 r for repr, s for str, a for ascii;formatspec 的一般形式为 [[fill]align][sign][#][0][width][.precision][typecode]

Tip 2-69: format 函数的圆括号还可以嵌套参数,譬如 {0:{1}d} 这样的话第二个参数就可以通过参数列表指定,来动态确定输出整数的宽度。

Tip 2-70: 调用 format(val, sformat) 可以单独格式化一个参数。例如:format(123, '05d') 就返回 '00123'。

Tip 2-71: 使用 list 的时候,可以灵活通过对 list 的切片赋值或者使用 del 一个 list 的切片来对 list 进行增删改操作。

Tip 2-72: 如为避免对未定义的 dictionary 取值时引发异常,可以使用 D.get(var[, default]) 的方式来对 dictionary 进行取值。

Tip 2-73: 使用 dict 的 keys(), values(), items() 方法,在 2.X 版本会返回一个 list,而在 3.X 则会返回一个视图(也可以理解成迭代器),这个视图则只是引用了原来的 dict,只能挨个挨个访问,而不重新构造一个 list。如果使用这个视图构造一个 list,则这个 list 也受原来的 dict 关联,也就是说,如果

D = {1:1, 2:2, 3:3} a = list(D.keys()) del D[1]

这时候 a 的 1 这个元素也会丢掉。

Tip 2-74: 使用 dict 的视图时,还支持集合的操作,只要它是唯一的,于是,keys() 和 items() 都支持集合操作(交并补差),而 values() 则由于不唯一而不支持集合操作。

 

 

 

 

</待续 PAGE 250> 

 

 

posted @ 2013-05-21 18:27  呆滞的慢板  阅读(370)  评论(0编辑  收藏  举报
呆滞的慢板