網(wǎng)站首頁(yè) 編程語(yǔ)言 正文
sync包
常用的有3個(gè)功能
鎖
鎖分為普通互斥鎖和讀寫(xiě)鎖
互斥鎖 Mutex | 讀寫(xiě)鎖 RWMutex |
---|---|
一個(gè)線程未釋放鎖時(shí),其他線程加鎖阻塞 | 讀鎖:一個(gè)線程未釋放讀鎖時(shí),其他線程可獲取讀鎖,獲取寫(xiě)鎖阻塞 寫(xiě)鎖:一個(gè)線程未釋放寫(xiě)鎖時(shí),其他線程可獲取讀鎖或?qū)戞i都會(huì)阻塞 |
線程監(jiān)聽(tīng)WaitGroup
使用場(chǎng)景:用于監(jiān)聽(tīng)一組子線程是否執(zhí)行完畢
使用流程 | 代碼 |
---|---|
建立監(jiān)聽(tīng)對(duì)象 | wg := new(sync.WaitGroup) |
創(chuàng)建多個(gè)子線程并計(jì)入計(jì)數(shù)器 | go func1(wg) wg.Add(1) go func2(wg) wg.Add(1) |
線程子線程執(zhí)行完畢后,減少計(jì)數(shù)器值 | func1(wg){wg.Done()} |
監(jiān)聽(tīng)計(jì)數(shù)器值,直到計(jì)數(shù)器值為0時(shí),執(zhí)行后面的代碼 | wg.Wait() |
池Pool
用于存放每次請(qǐng)求都需要實(shí)例化,且生命周期較長(zhǎng)的對(duì)象,以減輕垃圾回收壓力。
使用流程 | 代碼 |
---|---|
建立一個(gè)池 | RequestPool = sync.Pool{New: func() interface{} {return &RequestHeader{}}} |
從池中取一個(gè)對(duì)象 | RequestPool .Get() |
把對(duì)象放回池中 | RequestPool .Put(RequestHeader) 把對(duì)象放入池之前,需要把對(duì)象中所有值都初始化 |
encoding/binary包
主要用來(lái)把數(shù)字轉(zhuǎn)換為字節(jié)類(lèi)型
單數(shù)值轉(zhuǎn)換
//序列化 var dataA uint64=6010 var buffer bytes.Buffer err1 := binary.Write(&buffer, binary.BigEndian, &dataA) if err1!=nil{ log.Panic(err1) } byteA:=buffer.Bytes() fmt.Println("序列化后:",byteA) //反序列化 var dataB uint64 var byteB []byte=byteA err2:=binary.Read(bytes.NewReader(byteB),binary.BigEndian,&dataB) if err2!=nil{ log.Panic(err2) } fmt.Println("反序列化后:",dataB)
其中的BigEndian和LittleEndian 指定了轉(zhuǎn)換的方式是 大端字節(jié)序,還是小端字節(jié)序。
所謂大端和小端節(jié)序,是指不同cpu再把數(shù)據(jù)流轉(zhuǎn)換為字節(jié)時(shí),排位位置的不同,如下
若不同計(jì)算機(jī)程序之間使用了不同節(jié)序處理同一組數(shù)據(jù),就會(huì)造成無(wú)法解析的情況
多數(shù)值轉(zhuǎn)換
指把多個(gè)數(shù)字轉(zhuǎn)換到一個(gè)byte切片中
首先定義一個(gè)定長(zhǎng)切片 s := make([]byte,10)
首先要確定轉(zhuǎn)換的節(jié)序,也可以跳過(guò)該步驟
binary.LittleEndian.PutUint16(s, uint16(0))
確定完之后,就可以向s中插入數(shù)字了
start := 0 start += binary.PutUvarint(b[2:], 1198)
插入數(shù)字到切片后,會(huì)返回該數(shù)字在切片中占用的長(zhǎng)度
若切片空間不夠,則返報(bào)錯(cuò)
所以我們最好確定往切片中插入數(shù)字的個(gè)數(shù),并估算每個(gè)數(shù)字占用最大占用長(zhǎng)度
解析切片中的某個(gè)數(shù)字,要知道該數(shù)字在切片中占用的起始位置,若位置不對(duì)則無(wú)法解析出正確的數(shù)字,返回0
i,err := binary.ReadUvarint(bytes.NewReader(b[2:])) if err==nil{ fmt.Println(i) }else{ fmt.Println(err.Error()) }
切片中可以插入字符串,轉(zhuǎn)換為數(shù)字時(shí),只要能夠從正確的位置開(kāi)始解析,就會(huì)解析出正確的數(shù)字
encoding/gob包
是一個(gè)golang專(zhuān)屬的數(shù)據(jù)序列化工具,用于序列化和反序列化數(shù)據(jù),作用類(lèi)似于json
不同的是,在反序列化時(shí),需要有一個(gè)指定格式的變量接收值。該變量類(lèi)型需要與序列化時(shí)數(shù)據(jù)類(lèi)型兼容,否則反序列化失敗
type S struct{ Field1 string Field2 int } func main() { s1 := &S{ Field1: "Hello Gob", Field2: 999, } log.Println("Original value:", s1) buf := new(bytes.Buffer) err := gob.NewEncoder(buf).Encode(s1) if err != nil { log.Println("Encode:", err) return } s2 := &S{} err = gob.NewDecoder(buf).Decode(s2) if err != nil { log.Println("Decode:", err) return } log.Println("Decoded value:", s2) }
簡(jiǎn)單的數(shù)據(jù)可以使用上面代碼直接加密和解密
但是當(dāng)需要解密的數(shù)據(jù)是接口類(lèi)型時(shí),由于接口的特殊性,實(shí)現(xiàn)了接口中方法的變量可以作為值代替該方法,這導(dǎo)致gob不知道接口中數(shù)據(jù)的具體類(lèi)型,會(huì)解密失敗,如下
type Getter interface { Get() string } type Foo struct { Bar string } func (f Foo)Get() string { return f.Bar } buf := bytes.NewBuffer(nil) // 創(chuàng)建一個(gè)接口變量 //接口中原值是一個(gè)get方法,因?yàn)镕oo實(shí)現(xiàn)了get方法,所以可以最為值代替Get g := Getter(Foo{"wazzup"}) // gob解密g時(shí),認(rèn)為g中的值是Get() 類(lèi)型,但其實(shí)是Foo類(lèi)型,就會(huì)報(bào)錯(cuò) enc := gob.NewEncoder(buf) enc.Encode(&g)
解決這個(gè)問(wèn)題的方法就是在代碼初始化時(shí),使用 gob.Register()方法注冊(cè)Foo變量
當(dāng)gob解碼是發(fā)現(xiàn)類(lèi)型不對(duì)應(yīng),會(huì)從已注冊(cè)的類(lèi)型中查找
hash/crc32包
常用方法:
func ChecksumIEEE(data []byte) uint32
返回?cái)?shù)據(jù)data使用IEEE多項(xiàng)式計(jì)算出的CRC-32校驗(yàn)和
可通過(guò)對(duì)比數(shù)據(jù)發(fā)送和接收時(shí)的校驗(yàn)和,驗(yàn)證數(shù)據(jù)是否被篡改
原文鏈接:https://blog.csdn.net/u012830303/article/details/126485652
相關(guān)推薦
- 2022-10-19 Python基礎(chǔ)之類(lèi)的定義和使用詳解_python
- 2022-05-25 Entity?Framework?Core對(duì)Web項(xiàng)目生成數(shù)據(jù)庫(kù)表_實(shí)用技巧
- 2022-07-13 Android單選多選按鈕的使用方法_Android
- 2022-05-12 寶塔面板配置SSL證書(shū)
- 2023-05-23 Django?事務(wù)回滾的具體實(shí)現(xiàn)_python
- 2022-10-16 解析React?ref?命令代替父子組件的數(shù)據(jù)傳遞問(wèn)題_React
- 2022-07-20 使用numpy.ndarray添加元素_python
- 2023-04-08 淺析C語(yǔ)言中對(duì)于char*和char[]的理解_C 語(yǔ)言
- 最近更新
-
- window11 系統(tǒng)安裝 yarn
- 超詳細(xì)win安裝深度學(xué)習(xí)環(huán)境2025年最新版(
- Linux 中運(yùn)行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲(chǔ)小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎(chǔ)操作-- 運(yùn)算符,流程控制 Flo
- 1. Int 和Integer 的區(qū)別,Jav
- spring @retryable不生效的一種
- Spring Security之認(rèn)證信息的處理
- Spring Security之認(rèn)證過(guò)濾器
- Spring Security概述快速入門(mén)
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權(quán)
- redisson分布式鎖中waittime的設(shè)
- maven:解決release錯(cuò)誤:Artif
- restTemplate使用總結(jié)
- Spring Security之安全異常處理
- MybatisPlus優(yōu)雅實(shí)現(xiàn)加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務(wù)發(fā)現(xiàn)-Nac
- Spring Security之基于HttpR
- Redis 底層數(shù)據(jù)結(jié)構(gòu)-簡(jiǎn)單動(dòng)態(tài)字符串(SD
- arthas操作spring被代理目標(biāo)對(duì)象命令
- Spring中的單例模式應(yīng)用詳解
- 聊聊消息隊(duì)列,發(fā)送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠(yuǎn)程分支