Gopher道場 #1 受講メモ
2018年4月12日に開催されたメルペイ主催の「Gopher道場」の受講メモ。 復習も兼ねて公式ドキュメント等へのリンクを追記しました。
init関数は複数あってもおk
- 全体で一つしか認めないとでかいinit.goになってしまう
- 同一ファイルに複数あってもよい
- 明示的に
init()
のように呼び出すことはNG 実行される順序はtenntenn氏のQiita記事参照
initの中でgo routine呼べるか
- 可能ではある(が状態管理に失敗すると積む)
行末にセミコロンを補う仕様がある
以前のバージョンではセミコロンを補った状態でコンパイラのエラーが表示されることがあったそう。 詳細は言語仕様 The Go Programming Language Specification - The Go Programming Language を確認。JavaScriptでもセミコロンの自動挿入は罠ですね。
配列とスライス、マップの扱い
リテラルが似てるので注意
[...]int{1, 2, 3}
は配列
[]int{1, 2, 3}
はスライス。
- 配列は値コピーでスライスは参照コピーされる違いがある。
- 配列に追加する要素の数が初めから分かっていたら、あらかじめcapacityを確保しておく
- capacity不足になったときに順次メモリが拡張されるため。
要素の操作
スライスに対する
append
: スライスがnilもおk。A Tour of Go の15ページ目に例がある。- 一方で nilのMapに
append
: NG、空のオブジェクトを作る必要がある。
- 一方で nilのMapに
Mapの for range は取り出される順序は保障されないし、Go1.3から積極的に乱すようになった
Mapを値コピーしたい
- 標準の関数にはないので手でやる必要がある
- スライスは標準のcopyでおk
型エイリアス
戻り値
名前付戻り値
- 緯度経度のような同じ型の複数戻り値の場合わかりやすい
- これを使わないとできないパターンもある
- Effective Go の Named result parameters が詳しい
複数戻り値
- 自作の関数だと複数戻り値の一部を捨てることはできないけど、mapの値取得でok省略できるのはどうして
- 特別に扱われているから(for range の
i, v
でv
を無視できるのも同じですね)
- 特別に扱われているから(for range の
定数
定数は書きやすさ優先で、型やキャストを意識させすぎないようにしている
10 * time.Second
をDuration * Duration にキャストしなくていい。
変数に代入しようとした時点で
int, float, string, bool, ... になる
クラス型オブジェクト指向との違い
- 構造体でなくても、組み込み型でも新しい型を定義すればメソッドのレシーバになれる
- スライスや配列もOK
- ベクトルを扱うために配列にメソッドつけることもある
スコープ
- Fileスコープってどういうこと?→import文の有効範囲がそのファイル内に閉じていること
- Universeスコープは?組み込みの値が定義されている空間
true
,false
はキーワードではなく、代入可能なのでtrue := false
も(言語仕様上は)おk- ECMAScript5より前の仕様で
undefined
に代入可能だったのに似てる
defer
- リソースの開放は
defer
を使うことが多い - deferの引数は呼んだ時点で評価された値が使われるので、defer文の後に書き換えても書き換わらない