print('hello world')
一个简短的语句开启你的世界。好像看过的培训课都这么说😊😊
在Python里,一切皆对象,完全的面向对象。
Python中,所有的元素都是对象。(对象是一个抽象,可想象成现实中的一个实际物体。)
1.什么是对象?
对象的本质是:
对象是分配的一块内存,有足够的空间去表示它们所代表的值。—— 《Learning Python》
或者说:一块内存空间,拥有特定的值,支持特定类型的相关操作。
2.对象的特点:
Python中,对象具有三要素:标识(identity)、类型(type)、值(value)。
![](https://i-blog.csdnimg.cn/blog_migrate/43d6fbb52c495d4d54c8e6bf0aee2158.png)
标识(identity):
用于唯一标识对象,通常对应对象在计算机内存中的地址。使用内置函数id(obj)返回对象唯一标识。
类型(type):
对象中含有标准的头部信息:类型标识符。标识对象类型,表示对象存储的数据的类型。
类型可以限制对象的取值范围和可执行的操作。使用内置函数type(obj)返回对象所属类型。
每一个对象都有两个标准的头部信息:
1.类型标识符,去标识对象的(数据)类型;
2.引用计数器,记录当前对象的引用的数目。
(回收机制:变量的引用计数器为0,自动清理。 ※ 较小整数型对象有缓存机制。)
值(value):
表示对象存储的数据的信息。使用内置函数print(obj)可以直接打印值。
3. 这里就不得不说 python的操作符的使用:
操作符is 和==的区别与关系:
is
判断两个变量是否指向同一个对象,比较两个引用是否代表了内存中同一个地址,是否指向同一块内存空间。通过id(obj)返回值判断。
==
比较对象的本身内容{类型(type)和值(value)}是否一致。默认会调用对象的__eq__方法。
关系 与 案例:
当id相同时,is 为True,两者的type和value肯定相同,
但当type与value相同时,== 为True,但两者的id不一定相同。
列表
>>> a = [1,3]
>>> b = [1,3]
>>> a == b
True
>>> a is b
False
>>> id(a)
4544053632
>>> id(b)
4544054976
整数
>>> c = 257
>>> d = 257
>>> c == d
True
>>> c is d
True
>>> id(c)
140673355915216
>>> id(d)
140673355915216
4. 对象的分类:可变对象 和 不可对象
不可变对象 Immutable Ojbects:int、str、float、tuple
不可变对象不允许对自身内容进行原地修改。
对一个不可变对象进行赋值,实际上是创建一个新对象,再让变量指向这个新对象。
实例化新对象,开辟新内存空间,产生新地址。对象的id改变。
包括:int、str、float、tuple
>>> a = 1
>>> print("a = ", a ,"\tid(a):",id(a))
a = 1 id(a): 4376021296
>>> a = 2
>>> print("a = ", a ,"\tid(a):",id(a))
a = 2 id(a): 4500150608
# 整数int 不支持原地修改自身,修改的本质是变量重新被创建并引用了新的对象。id改变。
可变对象 Mutable Objects:list、set、dict
可变对象则可以对自身内容进行原地 (inplace) 修改。
对一个可变对象赋值,实际上是使其内容原地 (inplace)修改,没有返回值。
不开辟新的内存空间,地址不变。对象的id不变。
包括:list、set、dict。
>>> l = [1,2,3]
>>> print('l =',l, '\tid(l):',id(l))
l = [1, 2, 3] id(l): 4545937920
>>> l[1] = 4 #修改索引值为1的元素的值
>>> print('l =',l, '\tid(l):',id(l))
l = [1, 4, 3] id(l): 4545937920
>>> l.append(5) #在l末尾增加一个元素
>>> print('l =',l, '\tid(l):',id(l))
l = [1, 4, 3, 5] id(l): 4545937920
# 列表 l 原地修改其自身,其 id 并未改变。
两者在功能上的区别:
不可变对象可作为字典 dict 的键 key,而可变对象不行。 list 不能作为字典的键,但 tuple 可以。
不可变对象和可变对象的特殊方法,返回值不同。
str是不可变对象,方法如: replace、strip、upper 等不能修改原对象,会返回一个新对象。
list是可变对象,方法如:reverse、sort、append等在原有对象上直接修改,无返回值,返回值为None。
str不可变对象,方法如: replace、strip、upper 等不能修改原对象,会返回一个新对象。
s1 = 'abc'
s2 = s1.replace('b','d')
print('s1 =',s1,'\tid(s1):',id(s1))
print('s2 =',s2,'\tid(s2):',id(s2))
输出:
s1 = abc id(s1): 4391114416
s2 = adc id(s2): 4434508848
s1 从始至终,id 没有变化。
s2 多一次赋值,id 就会变一次,每次创建一个新对象。
s1 = ' a b c '
s2 = s1.strip()
print('s1 =',s1,"\tid(s1):",id(s1))
print('s2 =',s2,"\tid(s2):",id(s2))
输出:
s1 = a b c id(s1): 4435641712
s2 = a b c id(s2): 4434508656
s1 从始至终,id 没有变化。
s2 多一次赋值,id 就会变一次,每次创建一个新对象。
s1 = 'dog'
s2 = s1.upper()
print('s1 =',s1,"\tid(s1):",id(s1))
print('s2 =',s2,"\tid(s2):",id(s2))
输出:
s1 = dog id(s1): 4435641840
s2 = DOG id(s2): 4434508656
list 是可变对象,它的方法如 reverse、sort、append,都是在原有对象上直接修改,无返回值,返回值为 None。
l = [1,2,3]
b = l.append(4)
print(b)
输出:
None
列表原地修改,所以没有返回值。只能直接查看l,而不能使用变量对修改方法进行引用。
>>> l = [1,2,3]
>>> l.append(4)
>>> l
输出:
[1, 2, 3, 4]
>>> l = [7,4,16,2,6,98,540]
>>> l.sort(reverse=True)
>>> l
输出:
[540, 98, 16, 7, 6, 4, 2]
>>> l.sort(reverse=False)
>>> l
输出:
[2, 4, 6, 7, 16, 98, 540]
>>> l
输出:
[2, 4, 6, 7, 16, 98, 540]
>>> l.reverse()
>>> l
输出:
[540, 98, 16, 7, 6, 4, 2]
>>> a = l.sort()
>>> print(a)
输出:
None
>>> l.sort()
>>> l
输出:
[2, 4, 6, 7, 16, 98, 540]
3.3.3 =+ 和 += 的区别:
涉及关于赋值语句(assignment-statements) "="
和增强赋值语句(augmented assignment-statements) "+=" 。
赋值语句(assignment-statements) "=" :
是将右边的表达式的结果对象,引用绑定到 = 左边的变量名上。
创建一个新对象并将其赋值给目标,返回一个新对象,引用地址改变,原对象不变。
"= +"调用对象的 __add__ 方法。
增强赋值语句(augmented assignment-statements) "+=":
是对左边的对象原地(in-place)修改操作,直接修改原对象[1]。
直接在原对象进行修改,返回值为None,引用地址不变。
"+="调用对象的__iadd__ 方法。
不可变对象:
只有__add__方法,= + 和 += 的效果一样,都创建新对象。[2]
不可变对象str有__iadd__方法,不像列表一样内存地址id不变,str的内存地址id会变。[3]
例如:
>>> a = 500
>>> id(a)
4384329328
>>> a = a + 1
>>> id(a)
4384329104
>>> a = 500
>>> id(a)
4384329328
>>> a += 1
>>> id(a)
4384325680
可变对象:
= 和 += ,分别调用 __add__ 方法和 __iadd__ 方法,操作结果不同。
对 list 而言,+= 和 extend() 等价[4]。
可变对象,以list为例[5]:
>>> l = [1, 2, 3]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2, 3] id(l): 4527818688
>>> l += [4]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2, 3, 4] id(l): 4527818688
>>> l = [1,2,3]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2, 3] id(l): 4382181952
>>> l = l + [4]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2, 3, 4] id(l): 4382181440
list 的 = + 与 __add__ 方法,创建新对象,id变化。
>>> l = [1,2]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2] id(l): 4423449600
>>> l = l + [3]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2, 3] id(l): 4382185024
>>> l = [1,2]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2] id(l): 4423449600
>>> l = l.__add__([3])
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2, 3] id(l): 4382181504
list的 += 与 __iadd__ 方法直接将list 原地修改,id不变。
>>> l = [1,2]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2] id(l): 4541393024
>>> l += [3]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2, 3] id(l): 4541393024
>>> l = [1,2]
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2] id(l): 4539924288
>>> l = l.__iadd__([3])
>>> print('l =',l,'\tid(l):',id(l))
l = [1, 2, 3] id(l): 4539924288
注意:
针对可变对象,研究的是同一对象,可变指的是原地修改的方法:append,remove, += 这类操作,
而不包括新赋值操作,新赋值操作则会新建一个对象,id则改变。
5.对象的存储和创建:
Python中,对象存储在堆(heap)内存中。对象通过调用__new__创建。