首頁 > 後端開發 > Golang > Go 中的切片類型轉換

Go 中的切片類型轉換

WBOY
發布: 2024-02-10 15:00:20
轉載
634 人瀏覽過

Go 中的切片类型转换

php小編蘋果為大家介紹Go語言中的切片型別轉換。在Go語言中,切片是一種動態數組,常用於儲存和操作一組相同類型的元素。切片類型轉換是指將一個類型的切片轉換為另一個類型的切片,這在實際開發中非常常見。本文將詳細介紹切片類型轉換的注意事項和實際應用,幫助讀者更能理解並運用這項特性。

問題內容

我對 go 很陌生,有 c 背景,並且偶然發現了一些奇怪的問題。 程式碼如下:

package main

import (
"fmt"
"unsafe"
)

func main() {
     arr := []string { "one", "two", "three" }
     address := unsafe.pointer(&arr)
     addptr := (*[]string)(unsafe.pointer(*(*uintptr)(address)))
     fmt.println((*addptr)[0])
}
登入後複製

此程式碼失敗並顯示:

runtime error: growslice: len out of range
登入後複製

例如,如果我將演員表更改為:

addptr := (*[0]string)(unsafe.pointer(*(*uintptr)(address)))
登入後複製

上面的程式碼工作得很好。

我知道這是對陣列指標的強制轉換,並且陣列必須具有恆定的大小, 但如何將其轉換為指向切片的指標呢?

更令人困惑的是,可以取得切片位址並將其指派給指針,如下所示:

func main() {
     arr := []string { "one", "two", "three" }
     var arrPtr *[]string = &arr
     fmt.Println((*arrPtr)[0])
}
登入後複製

這次一切都會正常,儘管指標的類型與我在第一個範例中將不安全指標轉換為相同的類型。 有人可以幫忙理解這裡到底發生了什麼事嗎?

解決方法

一些背景:切片標頭包含指向後備數組、長度和容量的指標。

問題第一部分中的程式碼將切片頭轉換為指向切片頭的指標。 go vet 指令警告問題中的程式碼可能濫用 unsafe.pointer。

透過刪除額外的取消引用操作來修復,以便程式碼從指向切片頭的指標轉換為指向切片頭的指標。

arr := []string{"one", "two", "three"}
address := unsafe.pointer(&arr)
addptr := (*[]string)(unsafe.pointer((*uintptr)(address)))
fmt.println((*addptr)[0]) // prints one
登入後複製

不需要轉換為 *uintptr。簡化為:

arr := []string{"one", "two", "three"}
address := unsafe.pointer(&arr)
addptr := (*[]string)(unsafe.pointer(address))
fmt.println((*addptr)[0]) // prints one
登入後複製

不需要不安全的惡作劇。簡化為:

arr := []string{"one", "two", "three"}
addptr := &arr
fmt.println((*addptr)[0]) // prints one
登入後複製

使用下列程式碼將切片的後備陣列指標轉換為陣列指標。程式碼很脆弱,因為它假設切片頭的第一個字是指向後備數組的指標。

arr := []string{"one", "two", "three"}
address := unsafe.pointer(&arr)
addptr := (*[1]string)(unsafe.pointer(*(*uintptr)(address)))
fmt.println((*addptr)[0]) // prints one
登入後複製

不需要前面程式碼片段中的 uintptr 轉換。簡化為:

arr := []string{"one", "two", "three"}
address := unsafe.Pointer(&arr)
addPtr := (*[]string)(address)
fmt.Println((*addPtr)[0]) // prints one
登入後複製

我希望這會有所幫助。

以上是Go 中的切片類型轉換的詳細內容。更多資訊請關注PHP中文網其他相關文章!

相關標籤:
來源:stackoverflow.com
本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn
最新問題
熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板