日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > python >内容正文

python

python动态数据类型_[python学习手册-笔记]004.动态类型

發(fā)布時間:2023/12/14 python 27 豆豆
生活随笔 收集整理的這篇文章主要介紹了 python动态数据类型_[python学习手册-笔记]004.动态类型 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

004.動態(tài)類型

?

本系列文章是我我的學習《python學習手冊(第五版)》的學習筆記,其中大部份內容為該書的總結和我的理解,小部份內容為相關知識點的擴展。html

非商業(yè)用途轉載請注明做者和出處;商業(yè)用途請聯系本人(gaoyang1019@hotmail.com)獲取許可。java

?

基礎概念的解釋

首先咱們來解釋一些基礎概念,看不懂的能夠跳過,這對于初學者不是很重要。python

強類型語言和弱類型語言

首先,強弱類型語言的區(qū)分不是看變量聲明的時候是否顯式的定義數據類型。程序員

強類型語言,定義是任何變量在使用的時候必需要指定這個變量的類型,并且在程序的運行過程當中這個變量只能存儲這個類型的數據。所以,對于強類型語言,一個變量不通過強制轉換,它永遠是這個數據類型,不容許隱式的類型轉換。好比java,python都屬于強類型語言。web

強類型語言在編譯的時候,就能夠檢查出類型錯誤,避免一些不可預知的錯誤,使得程序更加安全。緩存

與之對應的是弱類型語言,在變量使用的時候,不嚴格的檢查數據類型,好比vbScript,數字12和字符串3進行鏈接,能夠直接獲得123。再好比C語言中int i = 0.0是能夠經過編譯的。安全

另外知乎上關于相關問題 rainoftime 大神也有相關解答,沒有查到權威解釋,對大神的解答存疑,可是能夠參考,幫助咱們理解。數據結構

動態(tài)類型語言和靜態(tài)類型語言

動態(tài)類型和靜態(tài)類型的區(qū)別主要在數據類型檢查的階段。app

動態(tài)類型語言:運行期間才去作數據類型的檢查。在動態(tài)類型語言中,不須要給變量顯式的指明其數據類型,該語言會在第一次賦值的時候,將內部的數據類型記錄下來。編輯器

靜態(tài)類型語言,在編譯階段就進行數據類型檢查。也就是說靜態(tài)類型語言,在定義變量的時候,必須聲明數據類型。

這里有個比較經典的圖:

各種語言的定義

堆和棧

首先,堆兒(很差意思,這里不該該帶兒化音...),堆(heap)和棧(stack)的概念在不一樣范疇是有不一樣含義的。

在數據結構中,堆指的是知足父子節(jié)點知足大小關系的一種徹底二叉樹。棧指的是知足后進先出(LIFO),支持pop和push兩種操做的一個“桶”(原本想說序列,可是不知道準不許確,因此說了個桶...)

在操做系統中,堆兒和棧指的是內存空間。

棧,和數據結構中的棧差很少,是一個LIFO隊列,由編譯器自動分配和釋放,主要用來存放函數的參數值,局部變量的值等內容。

堆,通常由程序員分配和釋放,固然,像java和python這類語言也有自動垃圾回收的機制。這個咱們在后面會講到。

變量、對象和引用

python中的變量聲明是不須要顯式的指定類型的,但這并不代表python是一個弱類型語言。

好比,咱們的一條簡單的賦值語句a=3,那么接下來python編譯器會作哪些事情呢?

建立變量和字面量:

建立一個字面量3(若是這個字面量尚未被建立過的狀況下)

建立一個名稱叫a的變量。通常咱們理解在這個變量a第一次被賦值的時候就建立了它。(實際python解釋器在運行代碼以前就會檢測變量名)

檢查變量類型:

python中類型是針對對象而言的,并非針對變量名而言的。 對象會包含兩個重要的頭部信息,一個是類型標志符,一個是引用計數器。

變量名并不會限制變量的類型。也就是說這個

a 它只是一個名字,具體“關聯”什么類型的變量,這個是沒有限制的。

變量的使用

當變量出如今表達式中的時候,它就會被當前引用的對象所代替。

仍是說這個例子,若是在以后的代碼中使用了a,好比

a+1那么這里的a就會被指向3這個字面量

簡單總結,當咱們執(zhí)行a=3的時候,實際作了三件事:

建立一個對象實例,3

建立一個變量,a

將變量名a引用到對象實例3上

image-20201214204037907

這里提到了一個概念,引用。 引用其實就是一種關系,是經過內存中的指針所實現的。

好嘞,這里又出現了一個新的概念,指針。 指針這個東西,簡單來講能夠理解為內存地址的一個指向。就是對初學者很差解釋(主要是我懶得解釋,就是屬于那種懂的不須要講,不懂的一時半會講了也是不懂,可是隨著學習的深刻,慢慢就理解了的東西。。。)

變量的類型

首先,python是一個強類型語言,這是毫無疑問的。 可是python不須要顯式的聲明變量類型。 這是由于python的類型是記錄在對象實例中的。

在前面咱們講到過,python中的對象會包含兩個重要的頭部信息:

類型標志符(type designator):用來標識這個對象的類型

引用計數器(reference counter): 代表有多少個變量引用到了這個對象上,用于跟蹤改對象應該什么時候被回收

由于對象的這個機制,python中的變量聲明的時候,就不須要再指定類型了。 也就是說變量名與變量類型是無關的。

a=1

a='spam'

a=1.123

并且如上所示,同一個變量名能夠賦值給不一樣類型的對象實例。

共享引用

這里提出一個問題,以下代碼:

In?[6]:?a=3

In?[7]:?b=a

In?[8]:?a='spam'

那么在通過這一系列操做以后,a和b的值分別是啥?

In?[9]:?a

Out[9]:?'spam'

In?[10]:?b

Out[10]:?3

首先咱們來看,在執(zhí)行a=3和b=a以后,發(fā)生了什么

image-20201214210333750

a=3根據以前的介紹,比較好理解了。b=a實際上變量名b只是復制了a的引用,而后b也引用到了對象實例3上。那在以后這一句a='spam'又發(fā)生了什么?

image-20201214210854202

這個圖就說的很清楚了,在咱們執(zhí)行了a='spam'以后,a被指向了另一個對象。

搞清楚了這個以后,咱們再來看下一個例子:

a=3

b=a

a=a+3

這個前兩句就不須要解釋了,第三句a=a+3 其實一眼就能夠看出來,此時a是6。這個就涉及到前面說的,當a出如今表達式中的時候,它就會“變成”它所引用的對象實例。a=a+3也就是會變成3+3 計算后得出新的對象實例6,而后變量a引用到6這個對象上。

「在原位置修改」

關于共享引用,這里看一個特殊的例子:

In?[16]:?L1=[1,2,3]

In?[17]:?L2=L1

In?[18]:?L1[0]=1111

In?[19]:?L1

Out[19]:?[1111,?2,?3]

In?[20]:?L2

Out[20]:?[1111,?2,?3]

按照以前的劇本,L2和L1都是指向列表[1,2,3]這個對象的,那為何在咱們修改L1[0] 這個元素以后,為何L2也跟著發(fā)生變化了呢?

我本身畫了圖,從這個圖能夠看出來,實際上對于L1和L2的共享引用來看,并無違反咱們上面說的共享引用的原則。只是對于序列中元素的修改,L1[0]會在原位置覆蓋列表對象中的某部分值。

image-20201214212940939

那么問題來了若是在修改L1[0]以后,并不想L2的值受到影響,那該怎么辦?

簡單

把列表原本來本的復制一份就行了。 復制的辦法有三種:

第一種針對列表而言,能夠直接建立一個完整的切片,本質上是一種淺拷貝。

In?[32]:?L1=[[1,2,3],4,5,6]

In?[33]:?L2=L1[:]

In?[34]:?L2

Out[34]:?[[1,?2,?3],?4,?5,?6]

In?[37]:?L1[2]='aaa'

In?[38]:?L2

Out[38]:?[[1111,?2,?3],?4,?5,?6]

In?[39]:?L1

Out[39]:?[[1111,?2,?3],?4,?'aaa',?6]

第二種,淺拷貝,以下面這個例子中的D1.copy()

In?[26]:?D1={a:[1,2,3],b:3}

In?[27]:?import?copy

In?[28]:?D2=D1.copy()

In?[29]:?D2

Out[29]:?{6:?[1,?2,?3],?3:?3}

In?[30]:?D1[a][0]=1111

In?[31]:?D2

Out[31]:?{6:?[1111,?2,?3],?3:?3}

第三種,深拷貝,以下D2=copy.deepcopy(D1)

In?[41]:?import?copy

In?[45]:?D1={'A':[1,2,3],'B':'spam'}

In?[46]:?D1

Out[46]:?{'A':?[1,?2,?3],?'B':?'spam'}

In?[47]:?D2=copy.deepcopy(D1)

In?[48]:?D2

Out[48]:?{'A':?[1,?2,?3],?'B':?'spam'}

In?[49]:?D1['A'][0]=1111

In?[50]:?D1

Out[50]:?{'A':?[1111,?2,?3],?'B':?'spam'}

In?[51]:?D2

Out[51]:?{'A':?[1,?2,?3],?'B':?'spam'}

我相信,看到這里,對于深拷貝和淺拷貝有些讀者已經明白了,可是有些讀者仍是迷糊的。 這里簡單說一下,

淺拷貝:只拷貝父對象,不會拷貝對象內部的子對象。

深拷貝:徹底拷貝父對象和子對象。

淺拷貝

深拷貝

「關于相等」

先看一個例子

In?[59]:?L1=[1,2,3]

In?[60]:?L2=L1

In?[61]:?L1==L2

Out[61]:?True

In?[62]:?L1?is?L2

Out[62]:?True

In?[66]:?L1=[1,2,3]

In?[67]:?L2=[1,2,3]

In?[68]:?L1==L2

Out[68]:?True

In?[69]:?L1?is?L2

Out[69]:?False

從上面這個例子就能夠看出來,==比較的是值,is 實際比較的是實現引用的指針。

對象的垃圾收集和弱引用

垃圾回收機制也是一件很復雜的事情,可是python編譯器能夠本身去處理這玩意兒。 因此在初級階段,咱們不須要過多關注這玩意兒。 知道有這么個東西就夠了。

這里簡單的介紹下,python中的垃圾回收就是咱們所謂的GC,靠的是對象的引用計數器。引用計數器為0的時候,這個對象實例就會被釋放。對象的引用計數器能夠經過sys.getrefcount(istance)來查看。

In?[70]:?import?sys

In?[72]:?sys.getrefcount(1)

Out[72]:?2719

引用計數器的引入能夠很好的跟蹤對象的使用狀況,可是在某些狀況下,也可能會帶來問題。 好比循環(huán)引用的問題。

以下代碼:

In?[73]:?L?=[1,2,3]

In?[74]:?L.append(L)

固然,正常人確定不會寫出這種智障代碼,可是在一些復雜的數據結構中,子對象互相引用,就可能會形成死鎖。好比:

In?[1]:?class?Node:

...:???def?__init__(self):

...:?????self.parent=None

...:?????self.child=None

...:???def?add_child(self,child):

...:?????self.child=child

...:?????child.parent=self

...:???def?__del__(self):

...:?????print('deleted')

...:

這里咱們定義了一個簡單的類。這時,若是咱們建立一個節(jié)點,而后刪除它,能夠看到,對象被回收,而且準確的打印出了deleted。

In?[2]:?a=Node()

In?[3]:?del?a

deleted

那么,像下面這個例子,在刪除a節(jié)點以后,貌似沒有觸發(fā)垃圾回收,只有手動的gc以后,這兩個對象實例才被刪除。

在刪除a以后,沒有觸發(fā)垃圾回收,是由于它倆互相引用,實例的引用計數器并無置0 。

那在手動gc以后,因為python的gc會檢測這種循環(huán)引用,并刪除它。

In?[4]:?a=Node()

In?[5]:?a.add_child(Node())

In?[6]:?del?a

In?[7]:?import?gc

In?[8]:?gc.collect()

deleted

deleted

Out[8]:?356

A和B的關系

那么若是使用弱引用的話,效果就不同了

In?[9]:?import?weakref

...:

...:?class?Node:

...:???def?__init__(self):

...:?????self.parent=None

...:?????self.child=None

...:???def?add_child(self,child):

...:?????self.child=child

...:?????child.parent=weakref.ref(self)

...:???def?__del__(self):

...:?????print('deleted')

...:

In?[10]:?a=Node()

In?[11]:?a.add_child(Node())

In?[12]:?del?a

deleted

deleted

因此這里就能夠看出來,所謂弱引用,其實并無增長對象的引用計數器,即便弱引用存在,垃圾回收器也會當作沒看見。

弱引用通常能夠拿來作緩存使用,對象存在時可用,對象不存在的時候返回None。這正符合緩存有則使用,無則從新獲取的性質。

總結

以上是生活随笔為你收集整理的python动态数据类型_[python学习手册-笔记]004.动态类型的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 欧美性猛交xxx乱大交3 | 丁香婷婷在线观看 | 91插插影库 | 高清一区二区 | 91字幕网 | 亚洲五码av | 中文字幕日本视频 | 国产三级在线观看视频 | 国产成人精品久久久 | 中文字字幕在线观看 | 五月婷婷综合在线 | 北条麻妃在线一区 | 欧美一级影院 | 男人日女人免费视频 | 日韩在线免费视频观看 | 欧美一区二区三区成人久久片 | 又大又粗又爽18禁免费看 | 国产精品一区二区在线看 | 黄网www | cao在线| 永久免费视频网站直接看 | 日本天天色 | 国产超级av| 亚洲视频一区二区 | 国产一区在线观看视频 | 亚洲熟妇国产熟妇肥婆 | 国产一级在线视频 | 377p粉嫩大胆色噜噜噜 | 91成人精品国产刺激国语对白 | 美女xx网站 | 亚洲国产精品久久久久爰性色 | 亚洲乱码国产乱码精品天美传媒 | 欧美黄色短片 | 国产成人精品一区二区三区网站观看 | 精品99在线 | 九色在线视频 | 办公室大战高跟丝袜秘书经理ol | 亚洲天堂资源在线 | 91国自产精品中文字幕亚洲 | 91久久久久一区二区 | 五月天丁香 | 成人久久精品人妻一区二区三区 | 91精品国产成人观看 | 污污视频在线免费看 | 中文字幕1区2区3区 www.com黄色片 | 一区免费在线 | 亚洲精品乱码久久久久久按摩观 | 日韩在线精品强乱中文字幕 | 国产最新在线观看 | 人与动物黄色片 | 国产精品久久999 | 欧美性理论片在线观看片免费 | 麻豆传媒网址 | 香蕉视频网站 | 美女日批网站 | 在线视频观看一区二区 | 99福利网 | 国产免费麻豆 | 成人免费观看视频大全 | 在线免费观看你懂的 | 精品一二三四区 | 绿色地狱在线观看 | 日本wwwxx | 91九色国产在线 | 久久视频黄色 | 色综合影视 | 天天爽夜夜爽夜夜爽 | 欧美私人影院 | 欧美日韩人妻一区二区 | 日韩欧美中文在线 | 美女天天操 | 日韩国产电影 | 日本一区二区不卡在线 | 亚洲免费观看高清在线观看 | 91久久免费 | 69精品在线 | 久久妇女 | 色亭亭 | 午夜视频在线观看视频 | 男人激情网 | 久久视频免费观看 | 国产又粗又黄又爽的视频 | av动漫天堂| 伊人222成人综合网 亚洲日本中文 | 黄色大片免费在线观看 | 欧美性极品少妇xxxx | 午夜看黄神器 | av观看网址 | 男生捅女生肌肌 | 亚洲av无码一区二区三区网址 | 精品国产亚洲AV | 欧美一区二区三区四 | 国产第一页av | 五十路熟母 | 成人美女免费网站视频 | 日韩欧美中文字幕一区 | 国产激情四射 | 中国毛片视频 | 五月婷婷激情综合 |