最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Golang數(shù)據(jù)類型比較詳解

 更新時間:2023年04月13日 09:46:34   作者:xidianhuihui  
這篇文章主要圍繞Golang數(shù)據(jù)類型比較詳細(xì)展開,文中有詳細(xì)的比較過程,需要的朋友可以參考一下

直接使用==比較的情況

分類說明是否能比較說明
基本類型整型( int/uint/int8/uint8/int16/uint16/int32/uint32/int64/uint64/byte/rune等)浮點(diǎn)數(shù)( float32/float64)復(fù)數(shù)類型( complex64/complex128)字符串( string)
引用類型切片(slice)、map
聚合類型(復(fù)合類型)數(shù)組相同長度的數(shù)組可以比較,不同長度的數(shù)組不能進(jìn)行比較
結(jié)構(gòu)體只包含可比較的類型情況下可比較
接口類型如error

 基本數(shù)據(jù)類

  • 類型一致且是基本類型,值相等的時候,才能==
  • 非基本類型會panic panic: runtime error: comparing uncomparable type []int

浮點(diǎn)比較

不過基本類型中也要注意浮點(diǎn)型的比較就不像我們現(xiàn)實(shí)中的一樣,比如0.1+0.2在計算中運(yùn)行結(jié)果就不是0.3了,而是0.30000000000000004了

package main import "fmt" func main() {     
    var a float64=0.1     
    var b float64=0.2     
    // 0.30000000000000004     
    fmt.Println(a+b) 
}

字符串比較

一般的比較運(yùn)算符(==、!=、<、<=、>=、>)是通過在內(nèi)存中按字節(jié)比較來實(shí)現(xiàn)字符串比較的,因此比較的結(jié)果是字符串自然編碼的順序。字符串所占的字節(jié)長度可以通過函數(shù) len() 來獲取,例如 len(str)

比較兩個字符是否相等

package golangbase

import (
	"fmt"
	"testing"
)

func TestString(t *testing.T) {
	str1 := "哈哈"
	str2 := "哈哈"
	fmt.Println(str1 == str2)
}

輸出結(jié)果為true

引用類型

slice、map

  • 切片之間不允許比較。切片只能與nil值比較
  • map之間不允許比較。map只能與nil值比較
  • 兩個nil也不能比較,會panic

slice、map比較

使用reflect.DeepEqual()

對比規(guī)則

  • 相同類型的值是深度相等的,不同類型的值永遠(yuǎn)不會深度相等。
  • 當(dāng)數(shù)組值(array)的對應(yīng)元素深度相等時,數(shù)組值是深度相等的。
  • 當(dāng)結(jié)構(gòu)體(struct)值如果其對應(yīng)的字段(包括導(dǎo)出和未導(dǎo)出的字段)都是深度相等的,則該值是深度相等的。
  • 當(dāng)函數(shù)(func)值如果都是零,則是深度相等;否則就不是深度相等。
  • 當(dāng)接口(interface)值如果持有深度相等的具體值,則深度相等。
  • 當(dāng)切片(slice)序號相同,如果值,指針都相等,那么就是深度相等的
  • 當(dāng)哈希表(map)相同的key,如果值,指針都相等,那么就是深度相等的。

使用示例

package golangbase

import (
	"reflect"
	"testing"
)

type StructA struct {
	Name  string
	Hobby []string
}

type StructB struct {
	Name string
}

func TestDeepEqual(t *testing.T) {
	s1 := StructA{Name: "test", Hobby: []string{"唱", "跳"}}
	s2 := StructA{Name: "test", Hobby: []string{"唱", "跳"}}
	println(reflect.DeepEqual(s1, s2))// true
	mp1 := map[int]int{1: 10, 2: 20}
	mp2 := map[int]int{1: 10, 2: 20}
	println(reflect.DeepEqual(mp1, mp2))// true
}

channel、指針

指針可比較,只要指針指向的地址一樣,則相等

由于通過make創(chuàng)建channel后,返回的是一個指針,所以可以比較

c1 := make(chan int, 2) 
 
c2 := make(chan int, 2) 
 
c3 := c1 
 
fmt.Println(c3 == c1) // true 
 
fmt.Println(c2 == c1) // false 

聚合類型

數(shù)組

數(shù)組在go中是必須先確定長度的,也就是長度不能再去擴(kuò)容。并且它是個值拷貝,做參數(shù)傳到一個函數(shù)中被修改,那么外部的值還是一樣的不變的。Slice則相反。那么數(shù)組是否可以比較呢,看下面的例子:

package main
import "fmt"
func main() {
    a := [2]int{1, 2}
    b := [2]int{1, 2}
    c := [2]int{1, 3}
    d := [3]int{1, 2, 4}
    fmt.Println(a == b) // true
    fmt.Println(a == c) // false
    fmt.Println(a == d) // invalid operation: a == d (mismatched types [2]int and [3]int)
}

可以看出,相同長度的數(shù)組是可以比較的,而不同長度的數(shù)組是不能進(jìn)行比較的。原因是什么呢?這是因?yàn)閿?shù)組類型中,數(shù)組的長度也是類型的一部分,不同長度的數(shù)組那么他們的類型也就被認(rèn)為不同的,所以無法比較

結(jié)構(gòu)體

只包含可比較的類型情況下可比較

package main
import "fmt"
type A struct {
    id int
    name string
}
func main() {
    a := A{id:5,name:"123"}
    b := A{id:5,name:"123"}
    c := A{id:5,name:"1234"}
    fmt.Println(a == b) // true
    fmt.Println(a == c) // false
}

反例,因?yàn)閟lice不可比較,如果結(jié)構(gòu)體包含了slice,則不可比較

package main
import "fmt"
type A struct {
    id int
    name string
    son []int
}
func main() {
    a := A{id:5,name:"123",son:[]int{1,2,3}}
    b := A{id:5,name:"123",son:[]int{1,2,3}}
    fmt.Println(a == b) // invalid operation: a == b (struct containing []int cannot be compared)
}

接口

Go 語言根據(jù)接口類型是否包含一組方法將接口類型分成了兩類:

  • 使用 runtime.iface結(jié)構(gòu)體表示包含方法的接口
  • 使用 runtime.eface結(jié)構(gòu)體表示不包含任何方法的 interface{} 類型
type eface struct { // 16 字節(jié)
    _type *_type
    data  unsafe.Pointer
}

type iface struct { // 16 字節(jié)
    tab  *itab
    data unsafe.Pointer
}

一個接口值是由兩個部分組成的,即該接口對應(yīng)的類型和接口對應(yīng)具體的值

接口值的比較涉及這兩部分的比較,只有當(dāng)類型和值都相等(動態(tài)值使用==比較),兩個接口值才是相等的??磦€例子:

var a interface{} = 0
var b interface{} = 2
var c interface{} = 0
var d interface{} = 0.0
fmt.Println(a == b) // false
fmt.Println(a == c) // true
fmt.Println(a == d) // false

a和c類型相同(都是int),值也相同(都是0,基本類型比較),故兩者相等。 a和b類型相同,值不等,故兩者不等。 a和d類型不同,a為int,d為float64,故兩者不等

最后做個練習(xí)

func TestJson(t *testing.T) {
	var x, y Data
	x = Data{
		UUID:    "856f5555806443e98b7ed04c5a9d6a9a",
		Content: 1,
	}
	bytes, _ := json.Marshal(x)
	_ = json.Unmarshal(bytes, &y)
	println(x)
	println(y)
	println(reflect.DeepEqual(x, y))
}

為什么結(jié)果為false?

debug看一下

原因是json.Unmarshal默認(rèn)會將所有的數(shù)字類型轉(zhuǎn)為float64

針對這種情況,可以封裝一個DeepEqual方法

func DeepEqual(v1, v2 interface{}) bool {
	if reflect.DeepEqual(v1, v2) {
		return true
	}
	bytesA, _ := json.Marshal(v1)
	bytesB, _ := json.Marshal(v2)
	return bytes.Equal(bytesA, bytesB)
}

![在這里插入圖片描述](https://img-blog.csdnimg.cn/55d294d1ab7740aba7b547d1a6165b5a.png)




以上就是Golang數(shù)據(jù)類型比較詳解的詳細(xì)內(nèi)容,更多關(guān)于Golang數(shù)據(jù)類型比較的資料請關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • 深入了解Golang中reflect反射基本原理

    深入了解Golang中reflect反射基本原理

    反射是這樣一種機(jī)制,它是可以讓我們在程序運(yùn)行時(runtime)訪問、檢測和修改對象本身狀態(tài)或行為的一種能力。本文主要帶大家來看看Golang中reflect反射基本原理,需要的可以參考一下
    2023-01-01
  • go語言實(shí)現(xiàn)銀行卡號Luhn校驗(yàn)

    go語言實(shí)現(xiàn)銀行卡號Luhn校驗(yàn)

    這篇文章主要為大家介紹了go語言Luhn校驗(yàn)測試銀行卡號碼的示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-05-05
  • 詳解Go語言中Goroutine退出機(jī)制的原理及使用

    詳解Go語言中Goroutine退出機(jī)制的原理及使用

    goroutine是Go語言提供的語言級別的輕量級線程,在我們需要使用并發(fā)時,我們只需要通過?go?關(guān)鍵字來開啟?goroutine?即可。本文就來詳細(xì)講講Goroutine退出機(jī)制的原理及使用,感興趣的可以了解一下
    2022-07-07
  • Go語言數(shù)據(jù)結(jié)構(gòu)之單鏈表的實(shí)例詳解

    Go語言數(shù)據(jù)結(jié)構(gòu)之單鏈表的實(shí)例詳解

    鏈表由一系列結(jié)點(diǎn)(鏈表中每一個元素稱為結(jié)點(diǎn))組成,結(jié)點(diǎn)可以在運(yùn)行時動態(tài)生成。本文將通過五個例題帶大家深入了解Go語言中單鏈表的用法,感興趣的可以了解一下
    2022-08-08
  • go如何刪除字符串中的部分字符

    go如何刪除字符串中的部分字符

    這篇文章主要介紹了go刪除字符串中的部分字符操作,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2021-04-04
  • golang:json 反序列化的[]和nil操作

    golang:json 反序列化的[]和nil操作

    這篇文章主要介紹了golang:json 反序列化的[]和nil操作,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2020-12-12
  • golang打包成帶圖標(biāo)的exe可執(zhí)行文件

    golang打包成帶圖標(biāo)的exe可執(zhí)行文件

    這篇文章主要給大家介紹了關(guān)于golang打包成帶圖標(biāo)的exe可執(zhí)行文件的相關(guān)資料,文中通過實(shí)例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友可以參考下
    2023-06-06
  • GoLand安裝與環(huán)境配置的完整步驟

    GoLand安裝與環(huán)境配置的完整步驟

    作為一個go語言程序員,覺得自己有義務(wù)為go新手開一條更簡單便捷的上手之路,下面這篇文章主要給大家介紹了關(guān)于GoLand安裝與環(huán)境配置的完整步驟,文中通過圖文介紹的非常詳細(xì),需要的朋友可以參考下
    2022-12-12
  • 詳解Go語言中調(diào)度器的原理與使用

    詳解Go語言中調(diào)度器的原理與使用

    這篇文章主要介紹了Go語言運(yùn)行時調(diào)度器的實(shí)現(xiàn)原理,其中包含調(diào)度器的設(shè)計與實(shí)現(xiàn)原理、演變過程以及與運(yùn)行時調(diào)度相關(guān)的數(shù)據(jù)結(jié)構(gòu),希望對大家有所幫助
    2023-07-07
  • Go語言題解LeetCode268丟失的數(shù)字示例詳解

    Go語言題解LeetCode268丟失的數(shù)字示例詳解

    這篇文章主要為大家介紹了Go語言題解LeetCode268丟失的數(shù)字示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-12-12

最新評論

张家港市| 祁东县| 永德县| 平乐县| 远安县| 重庆市| 新安县| 黎川县| 若尔盖县| 百色市| 浠水县| 新安县| 东港市| 灵武市| 大渡口区| 天峨县| 平泉县| 从江县| 绍兴市| 共和县| 凭祥市| 抚松县| 永胜县| 根河市| 濮阳县| 保山市| 兴化市| 疏附县| 闽侯县| 宁晋县| 开鲁县| 光泽县| 会宁县| 云和县| 新野县| 双峰县| 横山县| 无极县| 阳原县| 明水县| 遵化市|