我有以下图像的json结构:
{"image": [
{
"bytesize": "-2",
"default": "redlight_drdefault"
},
{
"active": "JV77tdMcHkChFaF2H9uoDHepPhUcrlprYEsQr-r-1lg=",
"bytesize": "566806"
}
]}
我想更改名为" active"的字段到"不活跃"不改变存储在字段中的值,如下所示:
{"image": [
{
"bytesize": "-2",
"default": "redlight_drdefault"
},
{
"inactive": "JV77tdMcHkChFaF2H9uoDHepPhUcrlprYEsQr-r-1lg=",
"bytesize": "566806"
}
]}
有没有人有解决方法如何做到这一点?如果你能在游乐场展示这一点,那就太棒了。
我很难追加新值:
mapactive := map[string]string{"active": "gj65vn768=",
"bytesize":"76878768" }
如何将此附加到提供给我的解决方案?这应该在使所有活动密钥无效时结束。
答案 0 :(得分:1)
预定义结构的解决方案。 https://play.golang.org/p/Y3xpESlbbN3
package main
import (
"encoding/json"
"fmt"
)
type (
images struct {
Image []image `json:"image"`
}
image struct {
Active string `json:"active,omitempty"`
common
}
newImages struct {
Image []newImage `json:"image"`
}
newImage struct {
common
Inactive string `json:"inactive,omitempty"`
}
common struct {
Bytesize string `json:"bytesize"`
Default string `json:"default,omitempty"`
}
)
var i = []byte(`
{"image": [
{
"bytesize": "-2",
"default": "redlight_drdefault"
},
{
"active": "JV77tdMcHkChFaF2H9uoDHepPhUcrlprYEsQr-r-1lg=",
"bytesize": "566806"
}
]}
`)
func main() {
var images images
e := json.Unmarshal(i, &images)
if e != nil {
panic(e)
}
var newImages newImages
for k, _ := range images.Image {
newImg := newImage{}
if len(images.Image[k].Active) > 0 {
newImg.Inactive = images.Image[k].Active
}
newImg.Default = images.Image[k].Default
newImg.Bytesize = images.Image[k].Bytesize
newImages.Image = append(newImages.Image, newImg)
}
result, e := json.Marshal(newImages)
if e != nil {
panic(e)
}
fmt.Println(string(result))
}
答案 1 :(得分:0)
package main
import (
"fmt"
"encoding/json"
)
func main() {
fmt.Println("Hello, playground")
var x S
json.Unmarshal(data,&x)
for _,img:=range x.Image {
Deactive(img)
}
b,_:=json.Marshal(x)
fmt.Println(string(b))
}
type S struct {
Image []map[string]interface{} `json:"image"`
}
func Deactive(x map[string]interface{}) {
if v,ok := x["active"]; ok {
delete(x,"active")
x["inactvie"]=v
}
}
var data = []byte(` {"image": [
{
"bytesize": "-2",
"default": "redlight_drdefault"
},
{
"active": "JV77tdMcHkChFaF2H9uoDHepPhUcrlprYEsQr-r-1lg=",
"bytesize": "566806"
}
]}
`)
正如我所说,使用map[string]interface{}
。但是在嵌套结构中尽可能地深入它,因为它很麻烦而且很棘手。
Deactive
接收地图并查找active
密钥,如果有,则会获取该值,插入带有该值的inactive
密钥,然后删除{ {1}}。
答案 2 :(得分:-2)
Golang允许在类型相同的结构之间进行直接转换,即使它们在字段标记中不同。也就是说,您可以直接转换:
type Active struct {
Active string `json:"active"`
ByteSize string `json:"bytesize"`
}
和
type Inactive struct {
Active string `json:"inactive"`
ByteSize string `json:"bytesize"`
}
使用以下内容:
var a Active
// decode JSON into a
var b Inactive = Inactive(a) // direct conversion allowed
然而,您的输入JSON不会轻易支持此功能。您的输入JSON将image
字段列为列表,尽管列表中的各个条目在类型或字段中实际上并不相同。在这种情况下唯一真正的选择是将其解析为map[string]interface{}
:
https://play.golang.org/p/4NgiKLlHg8c
parsed := make(map[string]interface{})
if err := json.Unmarshal([]byte(input), &parsed); err != nil {
panic(err)
}
img, ok := parsed["image"]
if ok {
if imglist, ok := img.([]interface{}); ok {
for i, mi := range imglist {
if m, ok := mi.(map[string]interface{}); ok {
for k, v := range m {
if k == "active" {
m["inactive"] = v
delete(m, "active")
imglist[i] = m
}
}
}
}
}
}
b, err := json.Marshal(img)
if err != nil {
panic(err)
}
请注意,我已从此代码中删除了大量健全性检查,以使其更短且更易读。使用嵌套接口映射来处理JSON本质上是混乱的。如果您可以更改输入JSON的格式化方式,那么您将拥有 lot 更好的运气,以及更易于维护的代码。