精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

[]byte與string的兩種轉換方式和底層實現

開發 前端
Go語言提供給我們使用的還是標準轉換方式,主要是因為在你不確定安全隱患的情況下,使用強轉化方式可能不必要的問題。

不過你發現沒fasthttp關于string和[]byte的轉換方式和大家平常普遍使用的方式不一樣,fasthttp轉換實現如下:

//[]byte轉string
func b2s(b []byte) string {
    return *(*string)(unsafe.Pointer(&b))
}
 
//string轉[]byte
func s2b(s string) (b []byte) {
    bh := (*reflect.SliceHeader)(unsafe.Pointer(&b))
    sh := (*reflect.StringHeader)(unsafe.Pointer(&s))
    bh.Data = sh.Data
    bh.Cap = sh.Len
    bh.Len = sh.Len
    return b
}

為什么不用我們常見的string和[]byte的轉換方式呢?這樣做是怎么提高性能的呢?...

帶著這些疑問,今天將分享下并總結string和[]byte的轉換方式,不同的轉換方式之間的實現和區別!


圖片圖片

兩種轉換方式

如果此時此刻你剛好遇到面試官問你string和[]byte如何進行轉換,有幾種方式?你能答上來嗎

反正在寫這篇文章之前小許估計是答不出來的,哈哈!

畢竟知道的越多,不知道的也越多嘛

那今天我們就來聊聊,繼續往下讀之前,我們先了解下這兩種數據類型:

string和[]byte

圖片圖片

??上圖中可以看出 stringStruct和slice還是有一些相似之處,str和array指針指向底層數組的地址,len代表的就是數組長度。

關于string類型,在go標準庫中官方說明如下:

// string is the set of all strings of 8-bit bytes, conventionally but not
// necessarily representing UTF-8-encoded text. A string may be empty, but
// not nil. Values of string type are immutable.

type string string

string是8位字節的集合,string的定義在上圖中左側,通常但不一定代表UTF-8編碼的文本。string可以為空,但是不能為nil,并且string的值是不能改變的。

??為什么string類型沒有cap字段

string的不可變性,也就不能直接向底層數組追加元素,所以不需要Cap。

而[]byte就是一個byte類型的切片,切片本質也是一個結構體。

?? 這里我們先記住下這兩種數據類型的特點,對后面的了解兩者的轉換有幫助!

標準方式

Golang中string與[]byte的互換,這是我們常用的,也是立馬能想到的轉換方式,這種方式稱為標準方式。

// string 轉 []byte
s1 := "xiaoxu"
b := []byte(s1)

// []byte 轉 string
s2 := string(b)

那還有其他方式嗎?當然有的,那就是強轉換

強轉換方式

強轉換方式是通過unsafe和reflect包來實現的,代碼如下:

//[]byte轉string
func b2s(b []byte) string {
    return *(*string)(unsafe.Pointer(&b))
}
 
//string轉[]byte
func s2b(s string) (b []byte) {
    bh := (*reflect.SliceHeader)(unsafe.Pointer(&b))
    sh := (*reflect.StringHeader)(unsafe.Pointer(&s))
    bh.Data = sh.Data
    bh.Cap = sh.Len
    bh.Len = sh.Len
    return b
}

可以看出利用reflect.SliceHeader(代表一個運行時的切片) 和 unsafe.Pointer進行指針替換。

??為什么可以這么做呢?

前面我們在講string和[]byte類型的時候就提了,因為兩者的底層結構的字段相似!

array和str的len是一致的,而唯一不同的就是cap字段,所以他們的內存布局上是對齊的。

分析

我們看下這兩種轉換方式底層是如何實現的,這些實現代碼在標準庫中都是有的,下面底層實現的代碼來自Go 1.18.6版本。

標準方式底層實現

string轉[]byte底層實現

先看string轉[]byte的實現,(實現源碼在 src/runtime/string.go 中)

const tmpStringBufSize = 32

//長度32的數組
type tmpBuf [tmpStringBufSize]byte

//時間函數
func stringtoslicebyte(buf *tmpBuf, s string) []byte {
    var b []byte
    //判斷字符串長度是否小于等于32
    if buf != nil && len(s) <= len(buf) {
        *buf = tmpBuf{}
        b = buf[:len(s)]
    } else {
        //預定義數組長度不夠,重新分配內存
        b = rawbyteslice(len(s))
    }
    copy(b, s)
    return b
}

// rawbyteslice allocates a new byte slice. The byte slice is not zeroed.
//rawbyteslice函數 分配一個新的字節片。字節片未歸零
func rawbyteslice(size int) (b []byte) {
    cap := roundupsize(uintptr(size))
    p := mallocgc(cap, nil, false)
    if cap != uintptr(size) {
        memclrNoHeapPointers(add(p, uintptr(size)), cap-uintptr(size))
    }

    *(*slice)(unsafe.Pointer(&b)) = slice{p, size, int(cap)}
    return
}

圖片圖片

上面代碼可以看出string轉[]byte是,會根據字符串長度來決定是否需要重新分配一塊內存。

  • ? 預先定義了一個長度為32的數組
  • ? 若字符串的長度不超過這個長度32的數組,copy函數實現string到[]byte的拷貝
  • ? 若字符串的長度超過了這個長度32的數組,重新分配一塊內存了,再進行copy

[]byte轉string底層實現

再看[]byte轉string的實現,(實現源碼在 src/runtime/string.go 中)

const tmpStringBufSize = 32

//長度32的數組
type tmpBuf [tmpStringBufSize]byte

//實現函數
func slicebytetostring(buf *tmpBuf, ptr *byte, n int) (str string) {
    ...
    if n == 1 {
        p := unsafe.Pointer(&staticuint64s[*ptr])
        if goarch.BigEndian {
            p = add(p, 7)
        }
        stringStructOf(&str).str = p
        stringStructOf(&str).len = 1
        return
    }

    var p unsafe.Pointer
    //判斷字符串長度是否小于等于32
    if buf != nil && n <= len(buf) {
        p = unsafe.Pointer(buf)
    } else {
        p = mallocgc(uintptr(n), nil, false)
    }
    stringStructOf(&str).str = p
    stringStructOf(&str).len = n
    //拷貝byte數組至字符串
    memmove(p, unsafe.Pointer(ptr), uintptr(n))
    return
}

跟string轉[]byte一樣,當數組長度超過32時,同樣需要調用mallocgc分配一塊新內存

強轉換底層實現

從標準的轉換方式中,我們知道如果字符串長度超過32的話,會重新分配一塊新內存,進行內存拷貝。

//string轉[]byte
func s2b(s string) (b []byte) {
    bh := (*reflect.SliceHeader)(unsafe.Pointer(&b))
    sh := (*reflect.StringHeader)(unsafe.Pointer(&s))
    bh.Data = sh.Data
    bh.Cap = sh.Len
    bh.Len = sh.Len
    return b
}

強轉換過程中,通過 神奇的unsafe.Pointer指針

? 任何類型的指針 *T 都可以轉換為unsafe.Pointer類型的指針,可以存儲任何變量的地址

? unsafe.Pointer 類型的指針也可以轉換回普通指針,并且可以和類型*T不相同

?? refletc包的 reflect.SliceHeader 和 reflect.StringHeader分別代表什么意思?

reflect.SliceHeader:slice類型的運行時表示形式

reflect.StringHeader:string類型的運行時表示形式

//slice在運行時的描述符
type SliceHeader struct {      
     Data uintptr
     Len  int
    Cap  int
}

//string在運行時的描述符
type StringHeader struct {
    Data uintptr
    Len  int
}

*(reflect.SliceHeader)(unsafe.Pointer(&b)) 的目的就是通過unsafe.Pointer 把它們轉換為 *reflect.SliceHeader 指針。

而運行時表現形式 SliceHeader 和 StringHeader,而這兩個結構體都有一個 Data 字段,用于存放指向真實內容的指針。

??[]byte 和 string之間的轉換,就可以理解為是通過 unsafe.Pointer 把 *SliceHeader 轉為 *StringHeader,也就是 *[]byte 和 *string之間的轉換。

那么我們就可以理解相對于標準轉換方式,強轉換方式的優點在哪了!

直接替換指針的指向,避免了申請新內存(零拷貝),因為兩者指向的底層字段Data地址相同

總結

今天小許和大家一起了解了[]byte和string類型,以及[]byte和string的兩種轉換方式。

不過Go語言提供給我們使用的還是標準轉換方式,主要是因為在你不確定安全隱患的情況下,使用強轉化方式可能不必要的問題。

不過像fasthttp那樣,對程序對運行性能有高要求,那就可以考慮使用強轉換方式!

責任編輯:武曉燕 來源: 小許code
相關推薦

2010-07-14 10:30:26

Perl多線程

2021-12-08 10:47:35

RabbitMQ 實現延遲

2009-06-23 18:18:13

SpringHibernate

2009-06-15 15:02:48

Spring定時器

2011-03-03 10:26:04

Pureftpd

2022-06-08 15:12:34

前端前端截圖

2020-02-21 17:33:17

SparkKafka數據

2021-05-27 10:57:01

TCP定時器網絡協議

2023-05-31 19:10:31

2020-05-11 13:03:03

SR-TEIP路由器

2010-07-13 14:54:15

Perl面向對象編程

2009-06-25 13:43:00

Buffalo AJA

2010-10-21 16:24:18

sql server升

2023-03-29 13:06:36

2010-08-06 09:38:11

Flex讀取XML

2012-12-24 13:30:34

iOS

2010-09-28 15:12:27

Javascript

2015-10-09 09:51:29

Web API認證

2010-09-07 11:09:59

2021-06-30 07:19:34

SpringBoot定時任務
點贊
收藏

51CTO技術棧公眾號

婷婷激情五月网| 中文字幕av不卡在线| 国产美女激情视频| 福利在线一区| 亚洲最新在线观看| 亚洲自拍偷拍福利| 久热这里只有精品6| 欧美午夜精彩| 欧美三级电影在线观看| 三区精品视频| 国产福利免费视频| 午夜亚洲性色福利视频| 久久久国产影院| 毛茸茸free性熟hd| 福利精品在线| 欧美日韩国产精品一区二区三区四区| 国产精品入口免费| 一区二区乱子伦在线播放| 韩国亚洲精品| 久久激情五月丁香伊人| 91精品人妻一区二区| 2021年精品国产福利在线| 在线观看av一区二区| 99在线免费视频观看| 黄色网址免费在线观看| 久久精品一二三| 精品在线视频一区二区| 中文字幕av影院| 欧美日韩p片| 久久黄色av网站| 久久久久久久久综合| 日韩xxxx视频| 成人黄视频在线观看| 亚洲国产激情av| 国产激情久久久久| 精品在线播放视频| 红桃视频国产一区| 欧美精品日韩www.p站| 少妇太紧太爽又黄又硬又爽小说| 蜜桃精品视频| 富二代精品短视频| 福利视频一区二区三区四区| 成视频免费观看在线看| ...xxx性欧美| 蜜桃999成人看片在线观看| 最近中文字幕免费观看| 乱人伦精品视频在线观看| 97视频免费看| 日韩欧美亚洲视频| 一本色道久久综合| 18一19gay欧美视频网站| 日本五十熟hd丰满| 99在线热播精品免费99热| 欧美精品激情在线观看| 久久影院一区二区| 亚洲激情网址| 国产69精品久久久久久| 青青草免费观看视频| 久久精品人人| 欧美丰满少妇xxxx| 精品午夜福利视频| 中文一区在线| 日韩美女写真福利在线观看| 亚洲成人av网址| 9国产精品视频| 97在线免费视频| 黄色片网站在线免费观看| 欧美亚洲一级| 国产日本欧美一区| 国产suv一区二区| 成人免费毛片a| 久久久com| 免费观看成年人视频| xfplay精品久久| 五月天久久狠狠| 欧美videos极品另类| 久久夜色精品国产噜噜av小说| 欧美午夜不卡| 欧美精品福利在线| 久久99国产综合精品免费| 日本aⅴ精品一区二区三区| 国产狼人综合免费视频| www.国产com| 99亚洲一区二区| 国产精品久在线观看| 国产欧美熟妇另类久久久| 岛国av在线一区| 欧洲国产精品| 99热国产在线| 欧美性色xo影院| 欧美一级小视频| 欧美美女在线直播| 亚洲第一区第一页| 国产精品久久久久久久av| 一区二区三区四区电影| 久久天天躁狠狠躁夜夜躁| 国产精品1000| 久久99最新地址| 久久久久久草| 91蜜桃在线视频| 色综合久久久久| 国偷自产av一区二区三区麻豆| 久久久久九九精品影院| 国产婷婷成人久久av免费高清| 亚洲av网址在线| 亚洲国产一区二区在线观看| 久久久爽爽爽美女图片| 日韩三级免费看| 久草热8精品视频在线观看| 极品日韩久久| av激情在线| 精品视频资源站| 天天插天天射天天干| 日韩黄色网络| 九九精品在线视频| 国产精品第56页| 精品一二线国产| 欧美日韩高清在线一区| 美女91在线| 6080yy午夜一二三区久久| 成人免费毛片糖心| 亚洲国产裸拍裸体视频在线观看乱了中文| 久久久久久97| 国产女18毛片多18精品| 国产欧美日韩久久| 丰满少妇被猛烈进入高清播放| 日韩在线免费| 欧美 日韩 国产一区二区在线视频 | 国产一区二区四区| 亚洲人成777| 精品少妇一区二区三区免费观看| 给我免费观看片在线电影的| 你懂的成人av| 91欧美精品成人综合在线观看| 高清乱码毛片入口| 亚洲精品中文在线影院| 天堂视频免费看| 日韩一区欧美| 国产精品狠色婷| av在线播放网| 91福利区一区二区三区| 波多野结衣 在线| 婷婷成人基地| 成人久久久久爱| 日本在线免费播放| 欧美日本在线观看| 中文字幕美女视频| 蜜臀a∨国产成人精品| 色阁综合av| 免费一区二区三区四区| 日韩视频欧美视频| 日本在线播放视频| 韩国一区二区视频| 香蕉精品视频在线| 成年永久一区二区三区免费视频| 亚洲国产精品热久久| xxxx 国产| 99国产精品国产精品久久| 中文网丁香综合网| 一二三四视频在线中文| 亚洲人成伊人成综合网久久久| 91视频免费在线看| 成人综合婷婷国产精品久久免费| 午夜欧美性电影| 欧美美女被草| 欧美xxxx18国产| 好吊色一区二区三区| 天天色天天操综合| 微拍福利一区二区| 亚洲综合不卡| 日韩精品电影网站| 香蕉久久一区| 久久久久久久成人| 国产手机av在线| 亚洲一区二区三区国产| 亚洲最大的黄色网| 国产黄色大片在线观看| 亚洲精品一二| 久久99精品久久久久久水蜜桃| 污污在线观看| 欧美疯狂性受xxxxx喷水图片| av网在线播放| 美国av一区二区| 欧美黄网在线观看| 无码少妇一区二区三区| 国产噜噜噜噜噜久久久久久久久 | 欧美久久久久久久久久久久| 99久久综合色| 久热精品在线播放| 亚洲国产高清视频| 午夜一区二区三视频在线观看| 在线电影福利片| 精品一区二区三区三区| 91精品人妻一区二区三区果冻| 国产亚洲精品久| 下面一进一出好爽视频| 久久福利一区| 久久人妻无码一区二区| 午夜精品在线| 国产成人精品一区二区三区| 最爽无遮挡行房视频在线| 亚洲女成人图区| 亚洲不卡免费视频| 欧美视频你懂的| 日本一区二区三区免费视频| 国产精品高清亚洲| 中文字幕在线免费看线人| 国产一区二区三区成人欧美日韩在线观看| 国产一区不卡在线观看| 亚洲久草在线| 日韩美女免费观看| 韩日毛片在线观看| 欧美成人黄色小视频| 国产三区四区在线观看| 日韩av在线免费看| 国产激情视频在线播放| 亚洲图片自拍偷拍| 艳妇荡乳欲伦69影片| 久久婷婷成人综合色| 逼特逼视频在线观看| 精品一区二区三区在线观看国产| 穿情趣内衣被c到高潮视频| 蜜桃精品一区二区三区| 国产精品视频成人| 欧美日韩视频网站| 97人人做人人爱| 国产www视频在线观看| 久久视频国产精品免费视频在线| 亚洲va天堂va欧美ⅴa在线| 国产精品91一区二区| 日本精品视频网站| 成人影音在线| 欧美日韩电影在线观看| 精品孕妇一区二区三区| 日韩一级裸体免费视频| av大片在线看| 中文字幕视频在线免费欧美日韩综合在线看 | 91福利视频在线观看| 日本理论片午伦夜理片在线观看| 亚洲精品国产美女| 蜜臀av午夜精品| 欧美成人精品福利| 天堂av免费在线观看| 一本久久a久久精品亚洲| 91久久国产视频| 1024成人网色www| 中日韩一级黄色片| 亚洲欧美在线另类| japanese中文字幕| 国产午夜精品在线观看| xxxxwww一片| 成人小视频在线观看| 一级黄色免费视频| 精品一区二区三区免费播放| 视频二区在线播放| 国产在线麻豆精品观看| 五月天婷婷影视| 国产乱对白刺激视频不卡| 国产精品探花在线播放| 久久综合影音| 日本xxxx黄色| 国产精品腿扒开做爽爽爽挤奶网站| 亚洲一区二区三区色| 色中色综合网| 美女在线免费视频| 午夜精品网站| 又粗又黑又大的吊av| 国产精品vip| 免费 成 人 黄 色| 日韩不卡一二三区| 日本在线观看a| 日本不卡一区二区三区高清视频| 成人免费aaa| 久久精品人人做人人爽电影蜜月| 妞干网在线视频观看| 亚洲欧美日韩专区| 天天干天天玩天天操| 日韩高清在线一区| 久久婷婷中文字幕| 波多野结衣中文字幕一区二区三区| 亚洲色图偷拍视频| 成人毛片视频在线观看| 中文人妻一区二区三区| 国产精品高潮久久久久无| 久久精品视频6| 色婷婷综合久色| 99精品免费观看| 91精品国产高清一区二区三区蜜臀| a片在线免费观看| 日韩一级黄色大片| 国产叼嘿视频在线观看| 亚洲男子天堂网| 日韩av电影免费观看| 亚洲综合图色| 99热一区二区三区| 亚洲激情网站| 在线免费看污网站| 91免费精品国自产拍在线不卡| 不卡的一区二区| 久久久久久电影| 久久综合久久鬼| 欧美日本精品一区二区三区| 日韩性xxxx| 久久亚洲欧美日韩精品专区| 竹内纱里奈兽皇系列在线观看| 97超级碰碰碰久久久| 少妇在线看www| 亚洲伊人第一页| 日韩中文字幕一区二区高清99| 96pao国产成视频永久免费| 亚洲免费福利一区| www.国产二区| 免费欧美在线视频| 可以直接看的无码av| 一区二区三区高清在线| 久久久久久久久久久久久久免费看| 亚洲国产日韩a在线播放性色| 日韩成人av毛片| 黑人巨大精品欧美一区二区| 99热这里只有精品99| 在线看福利67194| 欧美黑人巨大xxxxx| 国产精品美女诱惑| 欧美/亚洲一区| 手机在线国产视频| 国产精品三级视频| 国产成人精品亚洲| 亚洲人永久免费| 国产社区精品视频| 国产精品一区二区a| 亚洲图片久久| 精品这里只有精品| 99视频一区二区| 国产精品1234区| 精品国产电影一区二区| 伦理av在线| 99视频在线播放| 在线一区免费| 韩国三级与黑人| 亚洲美女精品一区| 国内老熟妇对白hdxxxx| 日韩av中文字幕在线| 国产www视频在线观看| 国产精品久久久久久影视| 免费看成人吃奶视频在线| 亚洲色成人一区二区三区小说| 久久99九九99精品| 免费黄色激情视频| 91麻豆精品国产91久久久使用方法| 午夜激情在线视频| 欧美亚洲另类制服自拍| 伊人久久大香线蕉av不卡| 一本色道久久88亚洲精品综合| 亚洲制服少妇| 在线不卡av电影| 欧美日韩在线一区二区| 香蕉视频在线免费看| 亚洲最大成人网色| 亚洲香蕉网站| 九色91popny| 日韩理论片网站| 精品人妻一区二区三区浪潮在线| 亚洲性生活视频在线观看| 成人精品动漫| 欧美日韩一级在线| 成人免费电影视频| av图片在线观看| 中文字幕精品国产| 中文字幕成在线观看| 日本不卡高清视频一区| 美女视频黄免费的久久| 欧美日韩午夜视频| 91成人免费在线视频| 欧美激情二区| 国产精品麻豆免费版| 免费视频一区| 一本一生久久a久久精品综合蜜 | 欧美独立站高清久久| 91好吊色国产欧美日韩在线| 久久一区二区视频| 91超薄丝袜肉丝一区二区| 久久久久国产精品一区| 国产一区二区在线| 男人操女人逼免费视频| 国产偷国产偷亚洲高清人白洁| 丰满少妇乱子伦精品看片| 亚洲人成在线观看| 视频一区在线| 黄色录像特级片| 91蜜桃传媒精品久久久一区二区| 国产精品白浆一区二小说| 亚洲人精选亚洲人成在线| 玖玖玖视频精品| av片中文字幕| 亚洲综合网站在线观看| 成人动漫在线播放| 国产精品一区二区三区免费观看 | 中文字幕精品综合| 亚洲精选一区二区三区| 国产精品99久久久久久久久久久久|