8
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Goで埋め込んだ構造体データを取り出す

Last updated at Posted at 2015-08-04

Go言語の構造体の埋め込みは継承のようなものだと思い込んでいたので、以下のコードで動くものだと勘違いしていたのだが、実際は動かない。

json-ng.go
package main

import (
    "encoding/json"
    "fmt"
)

type Info struct {
    Id   int    `json:"id"`
    Name string `json:"name"`
}

type JsonInfo struct {
    Info // ←埋め込む
    SubInfo *Info `json:"sub_info"`
}

const (
    json_string1 = "{\"id\":1,\"name\":\"test1\",\"sub_info\":{\"id\":2,\"name\":\"test2\"}}"
    json_string2 = "{\"id\":1,\"name\":\"test1\",\"sub_info\":null}"
)

func show_json(in_json_string string) {
    var json_data JsonInfo
    err := json.Unmarshal([]byte(in_json_string), &json_data)
    if err != nil {
        fmt.Println(err)
        return
    }
    var show_info Info
    if json_data.SubInfo != nil {
        show_info = *json_data.SubInfo
    } else {
        //show_info = json_data // ←エラーになる
    }
    fmt.Printf("%d : %s\n", show_info.Id, show_info.Name)
}

func main() {
    show_json(json_string1)
    show_json(json_string2)
}
実行結果
2 : test2
0 :

構造体に取り出し用のメソッドを実装することにより取り出すことが可能となった。
(2015/08/05 追記) コメントでご指摘いただきました。取り出しのメソッドは必要なく、埋め込んだ型名で取り出せることを確認しました。ご指摘ありがとうございます。

json-ok.go
package main

import (
    "encoding/json"
    "fmt"
)

type Info struct {
    Id   int    `json:"id"`
    Name string `json:"name"`
}

///*
// * 取り出し用のメソッド
// */
//func (info Info) getInfo() Info {
//    return info
//}

type JsonInfo struct {
    Info
    SubInfo *Info `json:"sub_info"`
}

const json_string1 = "{\"id\":1,\"name\":\"test1\",\"sub_info\":{\"id\":2,\"name\":\"test2\"}}"
const json_string2 = "{\"id\":1,\"name\":\"test1\",\"sub_info\":null}"

func show_json(in_json_string string) {
    var json_data JsonInfo
    err := json.Unmarshal([]byte(in_json_string), &json_data)
    if err != nil {
        fmt.Println(err)
        return
    }
    var show_info Info
    if json_data.SubInfo != nil {
        show_info = *json_data.SubInfo
    } else {
        //show_info = json_data.getInfo()
        show_info = json_data.Info // ←これで取り出せる
    }
    fmt.Printf("%d : %s\n", show_info.Id, show_info.Name)
}

func main() {
    show_json(json_string1)
    show_json(json_string2)
}
実行結果
2 : test2
1 : test1

他にもっといい方法がありましたら教えてください。。

参考サイト

http://golang.org/pkg/encoding/json/
http://postd.cc/is-go-object-oriented/

8
10
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
8
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?