真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

go語言編程類型切片 golang切片轉(zhuǎn)字符串

Go切片數(shù)組深度解析

Go 中的分片數(shù)組,實(shí)際上有點(diǎn)類似于Java中的ArrayList,是一個可以擴(kuò)展的數(shù)組,但是Go中的切片由比較靈活,它和數(shù)組很像,也是基于數(shù)組,所以在了解Go切片前我們先了解下數(shù)組。

成都創(chuàng)新互聯(lián)公司主要從事網(wǎng)站設(shè)計、成都網(wǎng)站建設(shè)、網(wǎng)頁設(shè)計、企業(yè)做網(wǎng)站、公司建網(wǎng)站等業(yè)務(wù)。立足成都服務(wù)硚口,十多年網(wǎng)站建設(shè)經(jīng)驗(yàn),價格優(yōu)惠、服務(wù)專業(yè),歡迎來電咨詢建站服務(wù):18982081108

數(shù)組簡單描述就由相同類型元素組成的數(shù)據(jù)結(jié)構(gòu), 在創(chuàng)建初期就確定了長度,是不可變的。

但是Go的數(shù)組類型又和C與Java的數(shù)組類型不一樣, NewArray 用于創(chuàng)建一個數(shù)組,從源碼中可以看出最后返回的是 Array{}的指針,并不是第一個元素的指針,在Go中數(shù)組屬于值類型,在進(jìn)行傳遞時,采取的是值傳遞,通過拷貝整個數(shù)組。Go語言的數(shù)組是一種有序的struct。

Go 語言的數(shù)組有兩種不同的創(chuàng)建方式,一種是顯示的初始化,一種是隱式的初始化。

注意一定是使用 [...]T 進(jìn)行創(chuàng)建,使用三個點(diǎn)的隱式創(chuàng)建,編譯器會對數(shù)組的大小進(jìn)行推導(dǎo),只是Go提供的一種語法糖。

其次,Go中數(shù)組的類型,是由數(shù)值類型和長度兩個一起確定的。[2]int 和 [3]int 不是同一個類型,不能進(jìn)行傳參和比較,把數(shù)組理解為類型和長度兩個屬性的結(jié)構(gòu)體,其實(shí)就一目了然了。

Go中的數(shù)組屬于值類型,通常應(yīng)該存儲于棧中,局部變量依然會根據(jù)逃逸分析確定存儲棧還是堆中。

編譯器對數(shù)組函數(shù)中做兩種不同的優(yōu)化:

在靜態(tài)區(qū)完成賦值后復(fù)制到棧中。

總結(jié)起來,在不考慮逃逸分析的情況下,如果數(shù)組中元素的個數(shù)小于或者等于 4 個,那么所有的變量會直接在棧上初始化,如果數(shù)組元素大于 4 個,變量就會在靜態(tài)存儲區(qū)初始化然后拷貝到棧上。

由于數(shù)組是值類型,那么賦值和函數(shù)傳參操作都會復(fù)制整個數(shù)組數(shù)據(jù)。

不管是賦值或函數(shù)傳參,地址都不一致,發(fā)生了拷貝。如果數(shù)組的數(shù)據(jù)較大,則會消耗掉大量內(nèi)存。那么為了減少拷貝我們可以主動的傳遞指針呀。

地址是一樣的,不過傳指針會有一個弊端,從打印結(jié)果可以看到,指針地址都是同一個,萬一原數(shù)組的指針指向更改了,那么函數(shù)里面的指針指向都會跟著更改。

同樣的我們將數(shù)組轉(zhuǎn)換為切片,通過傳遞切片,地址是不一樣的,數(shù)組值相同。

切片是引用傳遞,所以它們不需要使用額外的內(nèi)存并且比使用數(shù)組更有效率。

所以,切片屬于引用類型。

通過這種方式可以將數(shù)組轉(zhuǎn)換為切片。

中間不加三個點(diǎn)就是切片,使用這種方式創(chuàng)建切片,實(shí)際上是先創(chuàng)建數(shù)組,然后再通過第一種方式創(chuàng)建。

使用make創(chuàng)建切片,就不光編譯期了,make創(chuàng)建切片會涉及到運(yùn)行期。1. 切片的大小和容量是否足夠??;

切片是否發(fā)生了逃逸,最終在堆上初始化。如果切片小的話會先在?;蜢o態(tài)區(qū)進(jìn)行創(chuàng)建。

切片有一個數(shù)組的指針,len是指切片的長度, cap指的是切片的容量。

cap是在初始化切片是生成的容量。

發(fā)現(xiàn)切片的結(jié)構(gòu)體是數(shù)組的地址指針array unsafe.Pointer,而Go中數(shù)組的地址代表數(shù)組結(jié)構(gòu)體的地址。

slice 中得到一塊內(nèi)存地址,array[0]或者unsafe.Pointer(array[0])。

也可以通過地址構(gòu)造切片

nil切片:指的unsafe.Pointer 為nil

空切片:

創(chuàng)建的指針不為空,len和cap為空

當(dāng)一個切片的容量滿了,就需要擴(kuò)容了。怎么擴(kuò),策略是什么?

如果原來數(shù)組切片的容量已經(jīng)達(dá)到了最大值,再想擴(kuò)容, Go 默認(rèn)會先開一片內(nèi)存區(qū)域,把原來的值拷貝過來,然后再執(zhí)行 append() 操作。這種情況對現(xiàn)數(shù)組的地址和原數(shù)組地址不相同。

從上面結(jié)果我們可以看到,如果用 range 的方式去遍歷一個切片,拿到的 Value 其實(shí)是切片里面的值拷貝,即淺拷貝。所以每次打印 Value 的地址都不變。

由于 Value 是值拷貝的,并非引用傳遞,所以直接改 Value 是達(dá)不到更改原切片值的目的的,需要通過 slice[index] 獲取真實(shí)的地址。

Golang 中數(shù)組(Array)和切片(Slice)的區(qū)別

Go 中數(shù)組的長度是不可改變的,而 Slice 解決的就是對不定長數(shù)組的需求。他們的區(qū)別主要有兩點(diǎn)。

數(shù)組:

切片:

注意 1

雖然數(shù)組在初始化時也可以不指定長度,但 Go 語言會根據(jù)數(shù)組中元素個數(shù)自動設(shè)置數(shù)組長度,并且不可改變。切片通過 append 方法增加元素:

如果將 append 用在數(shù)組上,你將會收到報錯:first argument to append must be slice。

注意 2

切片不只有長度(len)的概念,同時還有容量(cap)的概念。因此切片其實(shí)還有一個指定長度和容量的初始化方式:

這就初始化了一個長度為3,容量為5的切片。

此外,切片還可以從一個數(shù)組中初始化(可應(yīng)用于如何將數(shù)組轉(zhuǎn)換成切片):

上述例子通過數(shù)組 a 初始化了一個切片 s。

當(dāng)切片和數(shù)組作為參數(shù)在函數(shù)(func)中傳遞時,數(shù)組傳遞的是值,而切片傳遞的是指針。因此當(dāng)傳入的切片在函數(shù)中被改變時,函數(shù)外的切片也會同時改變。相同的情況,函數(shù)外的數(shù)組則不會發(fā)生任何變化。

go和python切片的不同

go有切片slice類型,python有列表和元組,這兩種語言都有切片操作。

但是它們的切片操作是完全不同的。

首先說第一個,go的切片,其成員是相同類型的,python的列表和元組則不限制類型。

兩種語言都有[a:b]這種切片操作,意義也類似,但是go的a、b兩個參數(shù)不能是負(fù)數(shù),python可以是負(fù)數(shù),此時就相當(dāng)于從末尾往前數(shù)。

兩種語言都有[a:b:c]這種切片操作,意義卻是完全不同的。go的c,表示的是容量;而python的c表示的是步長。

但是最大的不同,還是:

python的切片產(chǎn)生的是新的對象,對新對象的成員的操作不影響舊對象;go的切片產(chǎn)生的是舊對象一部分的引用,對其成員的操作會影響舊對象。

究其原因,還是底層實(shí)現(xiàn)的不同。

go的切片,底層是一個三元組,一個指針,一個長度,一個容量。指針指向一塊連續(xù)的內(nèi)存,長度是已有成員數(shù),容量是最大成員數(shù)。切片時,一般并不會申請新的內(nèi)存,而是對原指針進(jìn)行移動,然后和新的長度、容量組成一個切片類型值返回。也就是說,go的切片操作通常會和生成該切片的切片共用內(nèi)存。

不僅是切片,字符串、數(shù)組的切片也是一樣的,通常會共用內(nèi)存。

當(dāng)然也有異常情況,那就是切片時,提供的容量過大,此時會申請新內(nèi)存并拷貝;或者對切片append超出容量,也會如此。這時,新的切片,才不會和老切片共享內(nèi)存。(如果你切片/創(chuàng)建時提供的容量小于長度,會panic)

python的列表,其實(shí)是個指針數(shù)組。當(dāng)然在下層也會提供一些空位之類的,但基本就是個數(shù)組。對它們切片,會創(chuàng)建新的數(shù)組,注意,是創(chuàng)建新的數(shù)組!python的列表可沒有容量的概念。

這其實(shí)也體現(xiàn)了腳本語言和編譯語言的不同。雖然兩個語言都有類似的切片操作;但是python主要目標(biāo)是方便;go主要目標(biāo)卻是快速(并彌補(bǔ)丟棄指針運(yùn)算的缺陷)。 a


網(wǎng)站題目:go語言編程類型切片 golang切片轉(zhuǎn)字符串
分享URL:http://weahome.cn/article/hjjhjs.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部