doucuo8618 2018-08-15 01:57
浏览 136
已采纳

Golang映射结构映射

Here is my data structure and trying to create a struct for this data but failing within error.

{
                "data": {
                  "image": {
                    "url": "tests.jpg"
                  }
                }
              }

Error:-

prog.go:16:20: invalid field name "Data" in struct initializer
prog.go:16:22: missing type in composite literal

Code:-

package main

import (
    "fmt"
)

type Images struct {
    Data struct {
        Image struct {
            url string
        }
    }
}

func main() {
    i := Images{"Data": {"Image": {"url": "test.jpg"}}}
    fmt.Println(i)
}

After reading the below answer, I tried this -

package main

import (
    "fmt"
)

//{ "data": {
//                  "image": {
//                    "url": "tests.jpg"
//                  }
//                }
//              }

type Images struct {
    Data Data
}
type Data struct {
    Image Image
}

type Image struct {
    url string
}

func main() {
    i := Images{
        Data: Data{
            Image: Image{url: "test.jpg"}}}
    fmt.Println(i)
}

Final output:-

{{{test.jpg}}}
  • 写回答

1条回答 默认 最新

  • duandang9434 2018-08-15 05:21
    关注

    There are a number of easy to conflate issues going on here.

    Output:

    First and foremost is you're not specifying any particular output formatting. Using fmt.Println to output data structures is really just for easy debugging, the formatting is pretty arbitrary you could get more reliably formatted output in correct Go if you used fmt.Printf("%#v ", i). The default Println outputs the equvelent of Printf's "%v".

    To get output in a particular format (other then Go itself) you'll need to import a package that can generate that format. Luckily a few popular formats are included in the standard library. But before we can get to that there are a few other things to fix / understand.

    Exports:

    Capitalized members of a struct are exported lower case members are not. This means that "url"in your image structure MUST be capitalized or else packages such as encoding/json will be unable to access the member to export it.

    Anonymous Types:

    Others emphasize creating explicit definitions for each of the structured data types in the overall structure, and I think that is generally good advice. However, it is also often silly to have so many one off type definitions floating around, so it is completely acceptable in the language to use inline anonymous structure definitions. Also a nice touch is that identically structured anonymous types are accepted as the same type unlike defined types.

    Here's an, admittedly pathological, example of doing the above with anonymous structs.

    i := struct{
        Data interface{} `json:"data"`
    }{
        Data:struct{
            Image interface{} `json:"image"`
        } {
            Image:struct{
                Url string `json:"url"`
            }{
                Url:"test.jpg",
            },
        },
    }
    

    While this works it's pretty messy. But notice you can even add tags to the fields of anonymous types so json formatting translates as intended.

    Another way to do it anonymously and avoid all this type definition crazy is just use a map. Here's that example. Note however, that some Go cargo cultists will yell at you if they see you using map[string]interface{} everywhere. Nevertheless there's actually nothing wrong with it either in practice or in philosophy.

    j := map[string]interface{} {
        "data":map[string]interface{}{
            "image":map[string]interface{}{
                "url":"test.jpg",
            },
        },
    }
    

    Generally however, you want to take advantage of what a typed language can give you. Strongly typed languages like Go are very good at finding otherwise subtile bugs early on.

    And isn't this better looking:

    type Object map[string]interface{}
    
    // ...
    
    j := Object{
        "data": Object{
            "image": Object{
                "url":"test.jpg",
            },
        },
    }
    

    Once More With Encoding

    Here's your program in a more idiomatic style. Which, not coincidentally, is also more readable in my opinion.

        package main
    
        import (
            "fmt"
            "encoding/json"
        )
    
        type data struct {
            Image image `json:"image"`
        }
    
        type image struct {
            Url string `json:"url"`
        }
    
        type images struct {
            Data data `json:"data"`
        }
    
    
        func main() {
            i := images{Data: data{Image: image{Url: "test.jpg"}}}
    
            data, _ := json.Marshal(i)
            fmt.Println(string(data))
    
        }
    

    Also note that while you must export the members to have them appear in the json, you do not have to export the types themselves.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 微信会员卡等级和折扣规则
  • ¥15 微信公众平台自制会员卡可以通过收款码收款码收款进行自动积分吗
  • ¥15 随身WiFi网络灯亮但是没有网络,如何解决?
  • ¥15 gdf格式的脑电数据如何处理matlab
  • ¥20 重新写的代码替换了之后运行hbuliderx就这样了
  • ¥100 监控抖音用户作品更新可以微信公众号提醒
  • ¥15 UE5 如何可以不渲染HDRIBackdrop背景
  • ¥70 2048小游戏毕设项目
  • ¥20 mysql架构,按照姓名分表
  • ¥15 MATLAB实现区间[a,b]上的Gauss-Legendre积分