日日操夜夜添-日日操影院-日日草夜夜操-日日干干-精品一区二区三区波多野结衣-精品一区二区三区高清免费不卡

公告:魔扣目錄網為廣大站長提供免費收錄網站服務,提交前請做好本站友鏈:【 網站目錄:http://www.ylptlb.cn 】, 免友鏈快審服務(50元/站),

點擊這里在線咨詢客服
新站提交
  • 網站:51998
  • 待審:31
  • 小程序:12
  • 文章:1030137
  • 會員:747

概述

GO 語言的切片這兩天用了用, 可以支持切割數組的中間部分. 但今天使用中, 出了 bug, 查了半天, 發現是切片的問題, 簡單寫個 demo 復現當時的情況:

package main

import "fmt"

func main() {
	a := []int{1, 2, 3, 4, 5}
	b := a[2:4]
	b[0] = 9
	fmt.Println(a)
}

你以為輸出的是什么? 來, 看結果:

[1 2 9 4 5]

懵沒懵?? 這是怎么回事呢?

(我用個語言怎么老踩坑, 笨的一X)

解惑

看這段 GO 代碼的輸出, 我們在修改b數組第一個元素值的時候, a數組的第三個元素修改了, 這兩個有什么聯系嗎? 仔細看, b數組在切的時候, 切的不就是a數組第三第四的元素嗎? 如此看來, b[0] 不正對應 a[2] 嗎?

大膽假設: **GO 中對數組進行切割, 并不會切一個新的數組出來, 而是仍然使用原數組, 只是修改下數組的首地址和長度. **

驗證:

package main

import "fmt"

func main() {
	a := []int{1, 2, 3, 4, 5}
	b := a[2:4]
	b[0] = 9
	fmt.Printf("%pn", &a[2])
	fmt.Printf("%pn", &b[0])
}

打印出來的地址完全一致, 印證了之前的猜想, 果然是一個數組. 同時修改a數組, 也會影響到b數組.

那可不可以對b數組越界訪問, 訪問a數組的值呢? 不行, GO 會對數組進行越界檢查.

查看文檔后發現, GO 切片的內部實現是這樣的包含了三個字段. 其中各字段含義如下:

  1. 數組首地址指針: 指向底層數組的首地址(這個是真正的數組)
  2. 數組長度: 數組當前已經使用的長度
  3. 數組容量: 數組已分配內存的總長度, 比數組長度多出的部分, 是占用內存還沒有使用的.

如此看來, 對其進行切割, 并不會整個復制, 對于大切片的操作就顯得很友好了, 畢竟共享底層數組, 只需要創建很少的數據就可以了. 只是要注意數組的同步修改問題.

這么看來, 貌似也可以解釋為什么叫切片了. **切片就是將底層的數組切出一部分來, 而不會創建新的數組. **

切片是有容量的, 那上面的切片b的容量是多少呢? 我看了一下: 長度是2, 容量是3.

GO 的切片在容量足夠的時候, 是不會動態擴容的. (擴容會創建更大容量新的數組并復制原數組數據). 那也就是說, 如果我向b追加數據, 就可以影響到原數組的后面的數據了??

試一發:

package main

import "fmt"

func main() {
	a := []int{1, 2, 3, 4, 5}
	b := a[2:4]
	b = Append(b, 10)
	fmt.Println(b)
	fmt.Println(a)
}

果然, 容量允許的話, 追加操作使用的仍然是原始數組.

所以: 切片的容量其實是底層數組的容量

同時, 有了之前對 GO 的了解, 知道 GO 所有的函數都是以傳遞副本值的方式進行, 傳遞切片也一樣, 而切片的結構體包含(數組指針, 長度, 容量)三個元素, 底層數組并不屬于值本身, 所以切片在函數間傳遞的復制成本很小, 而且函數對切片的修改也會反應到底層數組上. 同理可得, 如果在函數中對切片執行了擴容操作, 那改動就不會影響原數據, 因為擴容后操作的是新的數組了.

OK. 切片到這里就結束了, 簡單說就是數組上面再套一層. 切片的切片共享底層數組.

最后說一句, GO 創建數組和切片的方式(數組和切片是不同的數據結構):

// 方括號為空, 創建的是切片類型
a := []int{1, 2}
// 方括號指定長度, 創建的是真正的數組類型
b := [2]int{}

總結

至此, 對 GO 的切片有了全新的認識. 在使用切片的時候, 需要特別注意, 切片的截取與原對象共享底層數組, 在數據修改時要特別注意.

如果需要一個安全的可修改的切片, 可以使用copy函數復制一個全新的數組出來, 與原數組分離就可以了.

分享到:
標簽:切片
用戶無頭像

網友整理

注冊時間:

網站:5 個   小程序:0 個  文章:12 篇

  • 51998

    網站

  • 12

    小程序

  • 1030137

    文章

  • 747

    會員

趕快注冊賬號,推廣您的網站吧!
最新入駐小程序

數獨大挑戰2018-06-03

數獨一種數學游戲,玩家需要根據9

答題星2018-06-03

您可以通過答題星輕松地創建試卷

全階人生考試2018-06-03

各種考試題,題庫,初中,高中,大學四六

運動步數有氧達人2018-06-03

記錄運動步數,積累氧氣值。還可偷

每日養生app2018-06-03

每日養生,天天健康

體育訓練成績評定2018-06-03

通用課目體育訓練成績評定