Maison > développement back-end > Golang > le corps du texte

Comment désorganiser JSON dans des champs à l'aide d'une interface commune

PHPz
Libérer: 2024-02-09 16:51:18
avant
317 Les gens l'ont consulté

如何使用通用接口将 JSON 解组为字段

L'éditeur php Xinyi vous présente comment utiliser une interface commune pour désorganiser JSON dans des champs. En développement, nous devons souvent analyser les données JSON reçues en champs afin que les données puissent être facilement manipulées et traitées. Les interfaces génériques offrent un moyen simple et flexible d'atteindre cet objectif. En utilisant l'interface commune, nous pouvons transmettre une chaîne contenant des données JSON à la méthode de démarchage et obtenir les champs analysés pour un traitement ultérieur. Cette méthode est non seulement simple et facile à utiliser, mais convient également à différents types d'analyse de données JSON. Apprenons à décomposer JSON en champs à l'aide d'une interface commune !

Contenu de la question

J'ai un objet de réponse générique avec la structure suivante :

type response struct {
    data          data   `json:"data"`
    error         string `json:"error,omitempty"`
    nextpagetoken string `json:"next_page_token,omitempty"`
}

Copier après la connexion

data 类型是一个接口,有许多实现(例如 pingresponse 等)。如何将 response 解组为其基础类型?完整的示例如下,它总是触发错误 error: json: cannot unmarshal object into go struct field response.data of type main.data :

type Response struct {
    Data          Data   `json:"data"`
    Error         string `json:"error,omitempty"`
    NextPageToken string `json:"next_page_token,omitempty"`
}

type Data interface{
    Foo()
}

type TypeA struct {
    Field1 string `json:"field1"`
    Field2 int    `json:"field2"`
}

func (a *TypeA) Foo() {}

type TypeB struct {
    Field3 float64 `json:"field3"`
}

func (b *TypeB) Foo() {}

func main() {
    jsonStr := `{
        "data": {
            "field1": "some string",
            "field2": 123
        },
        "error": "",
        "next_page_token": ""
    }`

    var response Response
    err := json.Unmarshal([]byte(jsonStr), &response)
    if err != nil {
        fmt.Println("error:", err)
        return
    }

    switch data := response.Data.(type) {
    case *TypeA:
        fmt.Println("TypeA:", data.Field1, data.Field2)
    case *TypeB:
        fmt.Println("TypeB:", data.Field3)
    default:
        fmt.Println("Unknown type")
    }
}
Copier après la connexion

Solution de contournement

Vous devez indiquer encoding/json vers quel type spécifique démarcher. Ce package ne peut pas faire cela à votre place.

Supposons que typeatypeb soit défini comme :

type typea struct {
    fielda string `json:"field"`
}

type typeb struct {
    fieldb string `json:"field"`
}
Copier après la connexion

Dans ce cas, il est impossible de décider vers quel type démarcher.

Concernant votre exemple, nous pouvons indiquer encoding/json le type à désorganiser comme suit :

- var response response
+ response := response{data: &typea{}}
Copier après la connexion

Si vous ne connaissez pas le type à l'avance, vous pouvez le rassembler vers map[string]interface{} :

type response struct {
-   data          data                   `json:"data"`
+   data          map[string]interface{} `json:"data"`
    error         string                 `json:"error,omitempty"` 
    nextpagetoken string                 `json:"next_page_token,omitempty"`
 }
Copier après la connexion

Et déterminez le type comme suit :

if field1, ok := response.data["field1"]; ok {
    fmt.println("typea:", field1, response.data["field2"])
} else {
    if field3, ok := response.data["field3"]; ok {
        fmt.println("typeb:", field3)
    } else {
        fmt.println("unknown type")
    }
}
Copier après la connexion

Une autre solution consiste à intégrer les informations de type dans json :

jsonStr := `{
     "data": {
         "field1": "some string",
         "field2": 123
     },
+    type": "A",
     "error": "",
     "next_page_token": ""
 }`

 type Response struct {
-   Data          Data            `json:"data"`
+   Data          json.RawMessage `json:"data"`
+   Type          string          `json:"type"`
    Error         string          `json:"error,omitempty"`
    NextPageToken string          `json:"next_page_token,omitempty"`
 }
Copier après la connexion

Ensuite, décodez response.data en fonction de la valeur de response.type. Voir l'exemple fourni par response.type的值解码response.data。请参阅 encoding/json : https://pkg.go.dev/encoding/json#example-rawmessage-unmarshal.

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

source:stackoverflow.com
Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Tutoriels populaires
Plus>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal
À propos de nous Clause de non-responsabilité Sitemap
Site Web PHP chinois:Formation PHP en ligne sur le bien-être public,Aidez les apprenants PHP à grandir rapidement!