お元気そうで残念です

仕事とか趣味のメモを残します

Go言語でdeferを使った際のerror処理

Go言語のdefer文,便利ですよね.
でもdefer文を使うと返り値が無視されてしまうので,error処理をどうするべきか悩みます.

Goでdeferの処理中のエラーを返す書き方を工夫してみた
こちらのサイトでもいくつか検証して紹介されています.

対象の処理にもよりますが,個人的にはdefer文を使う時のerrorはキャッチせずにログに吐き出す程度で済まして良いんじゃないかと考えています.
例えば無名関数を使って以下のような感じです.

defer func() {
    err := resp.Body.Close()
    if err != nil {
        log.Println("can't close body!!", err)
    }
}()

close処理系は,すぐには大きな影響がないerrorが多い印象なのでpanicにしたり, mainまで拾い上げる必要は無いんじゃないかなと考えています.ものにもよると思いますが.

埋め込み構造体配列の初期化

Go言語で埋め込み構造体配列の初期化方法についてのメモ.

やり方

v := Foo {
  Bar: []Bar {
    {Value1: 1, Value2: 2},
  },
}

package main

import (
    "fmt"
)

type Foo struct {
    Bar []Bar
    ID int
}

type Bar struct {
    Name string
    Number int
}
func main () {
    m := Foo {
        ID: 1,
        Bar: []Bar {
            {Name:"hoge", Number:1},
            {Name:"poge", Number:2},
        },
    }

    fmt.Println(m)
}

https://play.golang.org/p/7K9SsJdk9E

実行結果

{[{hoge 1} {poge 2}] 1}

参考サイト

お気楽Go言語プログラミング

埋め込み構造体をjsonに変換したときに埋め込み構造体の構造体名を残して欲しい

Go言語の分からない部分についてのぼやき.

以下のように構造体を定義していたとする.

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

type Status struct {
        Power int `json:"power"`
        Speed int `json:"speed"`
}

以下のようにjson.Marshalを使って構造体を分割して出力すると

func main () {
        s1 := Status{5, 6}
        user1 := User{"hoge", 1, s1}
        user1.Status = s1
        j, _ := json.Marshal(user1)
        var buf bytes.Buffer
        buf.Write(j)
        os.Stdout.Write(j)
}

このように出力されるけど,

{"name":"hoge","id":1,"power":5,"speed":6}

できれば下のように出力して欲しい場面があった(送信先で構造体に戻したいときとか)

{"name":"hoge","id":1,"status":{"power":5,"speed":6}}

調べたらありそうな気がするけど,良い調べ方がわからなかった....

とりあえずメモっておく.


追記

type User struct {
Name string `json:"name"`
Id int `json:"id"`
Status `json:"status"`
}

で普通にできた