一、jsonomitempty簡介
Jsonomitempty是指可以在構建json數據時,自動判斷是否將該字段加入json字符串中的標誌,如果該字段的值為空 或者該字段為零值,則在編碼成json時不會輸出該字段。(json中沒有顯式表示為null或者””)。
以下為一個簡單的示例:
type Person struct {
Name string `json:"name,omitempty"`
Age int `json:"age,omitempty"`
Gender string `json:"gender,omitempty"`
}
func main() {
person := Person{
Name: "Lily",
Gender: "female",
}
data, err := json.Marshal(person)
if err != nil {
fmt.Println("json.Marshal error:", err)
}
fmt.Println(string(data))
}
輸出結果為:
{"name":"Lily","gender":"female"}可以看到,由於Age字段為空值,所以在編碼為json字符串時並未加入該字段。
二、jsonomitempty的使用場景
Jsonomitempty非常適用於那些需要在向前端傳遞數據時,盡量減小json數據大小的情況。比如在微服務中,不少服務需要向前端提供json數據作為返回。在數據中有大量數據為空值的情況下,使用jsonomitempty可以將返回結果中不必要的數據剔除,降低數據傳輸的負擔。
舉個栗子:
type UserInfo struct {
UserName string `json:"user_name"`
UserId int64 `json:"user_id"`
Email string `json:"email,omitempty"`
Phone string `json:"phone,omitempty"`
Avatar string `json:"avatar,omitempty"`
Gender string `json:"gender,omitempty"`
}
func GetUserInfo(userId int64) UserInfo {
userInfo := UserInfo{
UserName: "jack",
UserId: userId,
}
//... 查詢數據庫...
return userInfo
}
以上代碼演示了一個獲取用戶信息的函數,這個函數從數據庫中查詢用戶信息,並將其組裝成UserInfo對象返回。在返回結果中,由於郵箱、電話、頭像和性別可能為空值,所以我們使用jsonomitempty標記,將這些字段從json字符串中剔除,如下所示。
假設該用戶userId為1,接口返回結果如下:
{"user_name":"jack","user_id":1}可以看到,由於郵箱、電話、頭像及性別都為空值,因此在編碼成json字符串時並未加入這些字段。
三、jsonomitempty的限制
儘管jsonomitempty看起來非常有用,但它並不是萬能的。在使用jsonomitempty時,需要注意以下幾點限制。
1、”omitempty”字段可能會帶來歧義
在Go中,有些零值不等於空值。如果您的字段具有零值,並且您使用omitempty標記,則在組合json對象時,該字段將被視為空。因此,在使用jsonomitempty時,必須協調解決方案,以使一致性得到維護。
以Time類型為例,在默認情況下,它被視為 “非空” 。因此,使用omitempty標記,將清空Time類型的零值。
type StructA struct {
Time time.Time `json:"time,omitempty"`
}
sa := StructA{Time: time.Time{}}
執行結果:
{}2、Tag中不得使用”omitempty”字段進行json解碼
您在集合json字符串時使用omitempty。您可以忽略其中某些不是必須的值,但在反序列化JSON時卻無法使用此字段。在從json字符串構造結構體時,字段的零值應保留並由程序員手動驗證是否為零值。例如:
type StructB struct {
Time time.Time `json:"time,omitempty"`
}
sbJsonStr := `{"time":"2014-11-12T11:45:30.918Z"}`
sbParsed := StructB{}
err := json.Unmarshal([]byte(sbJsonStr), &sbParsed)
if err != nil {
fmt.Println(err)
}
fmt.Println(sbParsed)
執行結果:
{}在json.Unmarshal中使用`omitempty`字段標記,無法正常反序列化json字符串。
3、omitempty會自動忽略零值
如果您希望保留結構的默認值,而不管它是否為空,哪怕是零值您也不要使用omitempty。
type StructC struct {
Num int `json:"num,omitempty"`
}
sc := StructC{}
jb, _ := json.Marshal(sc)
fmt.Println(string(jb)) // 輸出 {}
如果刪除”omitempty”標記,則輸出為{“num”:0}。
四、總結
在我們的日常開發中,json字符串的交換、以及對不同源代碼的調用,已經成為編寫更好軟件的不可缺少的一部分。這種數據交換可能涉及到客戶端之間的交互,或者是從API向外提供服務。對於此類情況使用jsonomitempty是非常必要的。
通過本文的介紹,相信大家對jsonomitempty有了更深入的理解,並且在日常編碼中也更加熟練掌握它的使用。不管是在Go語言還是其他的編程語言中,jsonomitempty都是一種很實用的編碼和解碼技巧,值得我們掌握。
原創文章,作者:小藍,如若轉載,請註明出處:https://www.506064.com/zh-hant/n/286881.html
微信掃一掃
支付寶掃一掃