Slide 1

Slide 1 text

A T O U R O F G O ⼀ 緒 に G O の 世 界 を 冒 険 し よ う ︕ EngineerX.go #1 The Gopher character is based on the Go mascot designed by Renée French.

Slide 2

Slide 2 text

G o っ て ど ん な ⾔ 語 ︖

Slide 3

Slide 3 text

ABOUT GO G o は 、 シ ン プ ル で 信 頼 性 の ⾼ い 効 率 的 な ソ フ ト ウ ェ ア を 簡 単 に 構 築 で き る オ ー プ ン ソ ー ス の プ ロ グ ラ ミ ン グ ⾔ 語 で す 。 (By https://golang.org/)

Slide 4

Slide 4 text

GO RELEASE HISTORY 2012.03.28 go1 2013.05.13 go1.1 2013.12.01 go1.2 2014.06.18 go1.3 2014.12.10 go1.4 2015.08.19 go1.5 2016.02.17 go1.6 2016.08.15 go1.7 2017.02.16 go1.8 2017.08.24 go1.9 2018.02.16 go1.10 2018.08.24 go1.11 2019.02.25 go1.12 2019.09.03 go1.13

Slide 5

Slide 5 text

GO HISTORY • What is the history of the project? Robert Griesemer, Rob Pike and Ken Thompson started sketching the goals for a new language on the white board on September 21, 2007. Within a few days the goals had settled into a plan to do something and a fair idea of what it would be. Design continued part-time in parallel with unrelated work. By January 2008, Ken had started work on a compiler with which to explore ideas; it generated C code as its output. By mid-year the language had become a full-time project and had settled enough to attempt a production compiler. In May 2008, Ian Taylor independently started on a GCC front end for Go using the draft specification. Russ Cox joined in late 2008 and helped move the language and libraries from prototype to reality. Go became a public open source project on November 10, 2009. Countless people from the community have contributed ideas, discussions, and code. There are now millions of Go programmers—gophers—around the world, and there are more every day. Go's success has far exceeded our expectations. (By https://golang.org/doc/faq#history) Robert Griesemer Rob Pike Ken Thompson

Slide 6

Slide 6 text

GO HISTORY • What is the history of the project? Robert Griesemer, Rob Pike and Ken Thompson started sketching the goals for a new language on the white board on September 21, 2007. Within a few days the goals had settled into a plan to do something and a fair idea of what it would be. Design continued part-time in parallel with unrelated work. By January 2008, Ken had started work on a compiler with which to explore ideas; it generated C code as its output. By mid-year the language had become a full-time project and had settled enough to attempt a production compiler. In May 2008, Ian Taylor independently started on a GCC front end for Go using the draft specification. Russ Cox joined in late 2008 and helped move the language and libraries from prototype to reality. Go became a public open source project on November 10, 2009. Countless people from the community have contributed ideas, discussions, and code. There are now millions of Go programmers—gophers—around the world, and there are more every day. Go's success has far exceeded our expectations. (By https://golang.org/doc/faq#history) ロバート・グリーズマーのツイート(Fumiの意訳) 今⽇(9⽉21⽇)から12年前、2007年9⽉20⽇、 私は私が信頼しているロブ・パイク、ケン・トンプソンとともに数分間仕事を忘れ、 そしてその時より良いコードが書ける⽅法を決めた。 9⽉25⽇にロブはGoという名前を提案し、それがすべての始まりだ。右肩上がり、前向きに進む、苦あれば楽あり。

Slide 7

Slide 7 text

よく⾔われること Goが成功している理由 Goの成功している理由 • コンパイルの速さ • 実⾏の速さ • デプロイの容易さ • ツール(go tool) • 標準ライブラリ (By Go Conference 2014 Autumn) ⾔語の特徴 • 並⾏プログラム • インターフェース etc. Pob Pike⽒が考える成功の理由 GoのSimplicity(単純さ)

Slide 8

Slide 8 text

Goの世界を旅しよう︕ A TOUR OF GO

Slide 9

Slide 9 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ https://tour.golang.org/

Slide 10

Slide 10 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ https://tour.golang.org/ 説明 実⾏環境 (エディタ)

Slide 11

Slide 11 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ https://tour.golang.org/ 最初書いてあったコードにリセットされる。

Slide 12

Slide 12 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ https://tour.golang.org/ Go標準ツール gofmt でコードを整形する import ONの時は、 goimports が使われる

Slide 13

Slide 13 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ https://tour.golang.org/ コードを実⾏する

Slide 14

Slide 14 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ https://tour.golang.org/ 「Imports Off」と表⽰してある時︓ 機能OFF状態 「Imports On」と表⽰してある時︓ 「Format」をクリックして整形する際に、 必要なパッケージのimport⽂を⾃動で書いてくれ、 不要な場合は取り除いてくれる

Slide 15

Slide 15 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ https://tour.golang.org/ 「Syntax Off」と表⽰してある時︓ 機能OFF状態 「 Syntax On」と表⽰してある時︓ エディタ内のコードをシンタックスハイライトする

Slide 16

Slide 16 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ • 基本構⽂ – パッケージ、変数、関数 – 制御⽂︓for, if, else, switch, defer – その他の型︓struct, slices, maps • メソッドとインタフェース – メソッドとインタフェース • 並⾏性 – 並⾏性 A Tour of Goの構成

Slide 17

Slide 17 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ • 基本構⽂ – パッケージ、変数、関数 – 制御⽂︓for, if, else, switch, defer – その他の型︓struct, slices, maps • メソッドとインタフェース – メソッドとインタフェース • 並⾏性 – 並⾏性 本 ⽇ の 範 囲 A Tour of Goの構成 ※練習問題(Exercise)はやりません

Slide 18

Slide 18 text

休 憩 タ イ ム

Slide 19

Slide 19 text

A TOUR OF GO ⼀緒にGoの世界を冒険しよう︕ • 基本構⽂ – パッケージ、変数、関数 – 制御⽂︓for, if, else, switch, defer – その他の型︓struct, slices, maps • メソッドとインタフェース – メソッドとインタフェース • 並⾏性 – 並⾏性 本 ⽇ の 範 囲 A Tour of Goの構成 ※練習問題(Exercise)はやりません

Slide 20

Slide 20 text

基礎構⽂ パッケージ・変数・関数

Slide 21

Slide 21 text

PACKAGE ファイルの先頭でこのファイル は何のパッケージかを宣⾔する

Slide 22

Slide 22 text

PACKAGE パッケージを インポートしている

Slide 23

Slide 23 text

PACKAGE DirPath: $GOROOT ./math/rand ├── example_test.go ├── exp.go ├── gen_cooked.go ├── normal.go ├── race_test.go ├── rand.go ├── rand_test.go ├── regress_test.go ├── rng.go └── zipf.go

Slide 24

Slide 24 text

PACKAGE DirPath: $GOROOT ./math/rand ├── example_test.go ├── exp.go ├── gen_cooked.go ├── normal.go ├── race_test.go ├── rand.go ├── rand_test.go ├── regress_test.go ├── rng.go └── zipf.go

Slide 25

Slide 25 text

IMPORTS “factored import statement” ファクタード・インポート・ステートメント

Slide 26

Slide 26 text

IMPORTS “factored import statement” ファクタード・インポート・ステートメント 「グループ化」という意味

Slide 27

Slide 27 text

IMPORTS と書いても問題ないが、 “factored import statement” で書いた⽅が好ましい

Slide 28

Slide 28 text

EXPORTED NAMES mathパッケージのpiを利⽤しようとしている

Slide 29

Slide 29 text

EXPORTED NAMES これを実⾏すると…

Slide 30

Slide 30 text

EXPORTED NAMES 「math.piって名前はエクスポートされてなくて参照できないよ」 「math.piなんて定義されてないよ」 って怒られる

Slide 31

Slide 31 text

EXPORTED NAMES 「math.piって名前はエクスポートされてなくて参照できないよ」 「math.piなんて定義されてないよ」 って怒られる

Slide 32

Slide 32 text

EXPORTED NAMES 「math.piって名前はエクスポートされてなくて参照できないよ」 「math.piなんて定義されてないよ」 って怒られる 「他のパッケージからも使っていいよ」となっている状態のこと

Slide 33

Slide 33 text

EXPORTED NAMES 「math.piって名前はエクスポートされてなくて参照できないよ」 「math.piなんて定義されてないよ」 って怒られる 「他のパッケージからも使っていいよ」となっている状態のこと ⼤⽂字から始まっている名前はエクスポートされる︕

Slide 34

Slide 34 text

EXPORTED NAMES math.piからmath.Piに変更 math.piからmath.Piに変更

Slide 35

Slide 35 text

EXPORTED NAMES DirPath: $GOROOT ./math ├── … ├── atan.go ├── atan2.go ├── atanh.go ├── bits.go ├── cbrt.go ├── const.go ├── copysign.go ├── dim.go ├── erf.go …

Slide 36

Slide 36 text

FUNCTIONS 整数型(int)の変数x, yを引数にもち、 整数型(int)を返すadd関数 戻り値の型 引数 関数は0以上の引数もつ

Slide 37

Slide 37 text

FUNCTIONS func add(x int, y int) int { return x + y } 変数名の後に型を書く

Slide 38

Slide 38 text

FUNCTIONS func add(x int, y int) int { return x + y } ちなみに、以下のようには書けない

Slide 39

Slide 39 text

FUNCTIONS CONTINUED 関数の2つ以上の引数が同じ型である場合には、 最後の型を残して省略して記述できる

Slide 40

Slide 40 text

MULTIPLE RESULTS 複数の戻り値を返せる

Slide 41

Slide 41 text

NAMED RETURN VALUES Goの戻り値には名前を付けることができ、 関数の上部で定義された変数として扱われる

Slide 42

Slide 42 text

NAMED RETURN VALUES “naked” return という ネイキッド ”naked”とは「裸の」という意味 return⽂があることで プログラマが意図してここで終わり としてることが分かっていい

Slide 43

Slide 43 text

VARIABLES varステートメントを使って 変数(variable)を定義する

Slide 44

Slide 44 text

VARIABLES int型の初期値は0 bool型の初期値はfalse

Slide 45

Slide 45 text

VARIABLES int型の初期値は0 bool型の初期値はfalse ゼロ値(Zero Values)

Slide 46

Slide 46 text

VARIABLES WITH INITIALIZERS var宣⾔時に、 変数毎に初期化⼦(initializer)を与えられる 初期化⼦が与えられている場合、型の記述を省略できる 変数の型は、初期化⼦が持つ型になる → 複数の型宣⾔でも1⾏で書ける

Slide 47

Slide 47 text

SHORT VARIABLES DECLARATIONS 関数の中では、 Var宣⾔の代わりに、 := の代⼊⽂を使い、 暗黙的な型宣⾔ができる ※ 関数の外では、 := の代⼊⽂は使⽤できない

Slide 48

Slide 48 text

BASIC TYPES 基本型(組み込み型)︓20種類 bool string int int8 int16 int32 int64 uint uint8 uint16 uint32 uint64 uintptr byte // uint8 の別名 rune // int32 の別名 // Unicode の符号点(code point) float32 float64 complex64 complex128 error https://golang.org/ref/spec#Predeclared_identifiers

Slide 49

Slide 49 text

bool string int int8 int16 int32 int64 uint uint8 uint16 uint32 uint64 uintptr byte // uint8 の別名 rune // int32 の別名 // Unicode の符号点(code point) float32 float64 complex64 complex128 error BASIC TYPES int, uint, uintprt型は 32-bitシステムでは32bit(4byte)で、 64-bitシステムでは64bit(8byte)になる 基本型(組み込み型)︓20種類 https://golang.org/ref/spec#Predeclared_identifiers

Slide 50

Slide 50 text

BASIC TYPES 基本型(組み込み型)︓20種類 bool string int int8 int16 int32 int64 uint uint8 uint16 uint32 uint64 uintptr byte // uint8 の別名 rune // int32 の別名 // Unicode の符号点(code point) float32 float64 complex64 complex128 error https://golang.org/ref/spec#Predeclared_identifiers サイズ、符号なし(unsigned)整数の型を使う特別な理由がない限り、 整数の変数が必要な時は int を使いましょう

Slide 51

Slide 51 text

BASIC TYPES 変数宣⾔は、importと同様に、 中括弧で囲んで まとめて(factored)宣⾔可能

Slide 52

Slide 52 text

ZERO VALUES ゼロ値は型によって それぞれ以下のように与えられる 数値型(int, floatなど) 0 bool型 false string型 " " (空⽂字列) 変数に初期値を与えずに宣⾔すると ゼロ値(Zero Value)が与えられる

Slide 53

Slide 53 text

TYPE CONVERSIONS math.Sqrt関数はfloat64を型に取るため、 intからfloat64へ型変換を⾏なっている Goでの型変換は、 明⽰的な型変換を強制されている 型変換 変数 v 、型 T があった場合、 T(v) は、変数 v を T 型へ変換 暗黙的な型変換が⾏われないため、 適切な型を扱ってコードが書ける ゆえに、バグを作りにくくしている

Slide 54

Slide 54 text

TYPE INFERENCE 明⽰的な型を指定せずに変数を宣⾔する場合 ( := や var = で初期化⼦を与えて宣⾔した場合)、 変数の型は右側の変数から型推論される

Slide 55

Slide 55 text

TYPE INFERENCE 右側の変数が型を持っている場合 右側に型を指定しない定数である場合 var i int j := i // j は i と同じint型になる i := 42 // int f := 3.142 // float64 g := 0.867 + 0.5i // complex128

Slide 56

Slide 56 text

TYPE INFERENCE fmt.Printf(“v is of type %T¥n”, v ) 書式演算⼦のひとつ 「%T」は値の型をGoの構⽂で表現する

Slide 57

Slide 57 text

CONSTANTS const キーワードは、 定数(constant)を定義する

Slide 58

Slide 58 text

CONSTANTS const キーワードは、 定数(constant)を宣⾔する 定数のため、 定義後は値を変更できず、 下記の型にしか適⽤できない ・⽂字 (character) ・⽂字列 (string) ・boolean ・数値 (numeric) ※ := を使って宣⾔することはできない

Slide 59

Slide 59 text

NUMERIC CONSTANTS intは64-bit整数値を保持できるが、 このBigは1を左に100シフトしているので、100-bitである。 通常のint型では⾜りない。 しかし、定数であれば値として保持できる。

Slide 60

Slide 60 text

(By https://play.golang.org/p/9tgG5J1e_KH)

Slide 61

Slide 61 text

蛇足

Slide 62

Slide 62 text

0 0 0 1 0 0 1 0 0 0 1 1 0 1 0 0 (例)16-bitのデータがった時、 元のデータ (16-bit, 0x2468) 蛇足

Slide 63

Slide 63 text

格納領域 (8-bit, 0x????) 0 0 0 1 0 0 1 0 0 0 1 1 0 1 0 0 元のデータ (16-bit, 0x2468) (例) 16-bitのデータがった時、8-bitの領域に格納しようとすると… 蛇足

Slide 64

Slide 64 text

0 0 0 1 0 0 1 0 0 0 1 1 0 1 0 0 0 1 1 0 1 0 0 0 格納領域 (8-bit, 0x0068) 上位8-bitのデータ消失 0 0 0 1 0 0 1 0 0 0 1 1 0 1 0 0 元のデータ (16-bit, 0x2468) (例) 16-bitのデータがった時、8-bitの領域に格納しようとすると… 蛇足

Slide 65

Slide 65 text

NUMERIC CONSTANTS Bigは定数であるため、 '0b10000000000000000000000000000000000000 0000000000000000000000000000000000000000 00000000000000000000000' という値として保持できる

Slide 66

Slide 66 text

基礎構⽂ 制御⽂ FOR, IF, ELSE, SWITCH, DEFER

Slide 67

Slide 67 text

FOR for⽂(for loop) C⾔語とは違い丸括弧は不要

Slide 68

Slide 68 text

FOR for i := 0 ; i < 10 ; i++ { … } 初期化⽂ (the init statement) 条件式 (the condition expression) 後処理⽂ (the post statement) for ⽂は、セミコロン(;)によって、以下の3つの部分に分かれている

Slide 69

Slide 69 text

FOR for i := 0 ; i < 10 ; i++ { … } 初期化⽂ (the init statement) 条件式 (the condition expression) 後処理⽂ (the post statement) for ⽂は、セミコロン(;)によって、以下の3つの部分に分かれている 短い変数宣⾔によく利⽤する その変数はfor⽂のスコープ内のみ有効

Slide 70

Slide 70 text

FOR for i := 0 ; i < 10 ; i++ { … } 初期化⽂ (the init statement) 条件式 (the condition expression) 後処理⽂ (the post statement) for ⽂は、セミコロン(;)によって、以下の3つの部分に分かれている for ループの処理(下記では「…」のところ)が 終わった後に実⾏する処理

Slide 71

Slide 71 text

FOR for i := 0 ; i < 10 ; i++ { … } 初期化⽂ (the init statement) 条件式 (the condition expression) 後処理⽂ (the post statement) for ⽂は、セミコロン(;)によって、以下の3つの部分に分かれている 条件式が falseになるまで 繰り返される

Slide 72

Slide 72 text

FOR for i := 0 ; i < 10 ; i++ { … } true false ※上記は正しいフローチャートの 書き⽅ではありません

Slide 73

Slide 73 text

FOR CONTINUED • 初期化⽂と後処理⽂の記述は任意

Slide 74

Slide 74 text

FOR IS GO’S “WHILE” • 初期化⽂と後処理⽂の記述がない時セミコロン(;)も省略できる つまり、C⾔語などにある while はGoでは for だけを使う

Slide 75

Slide 75 text

FOREVER • ループ条件を省略すれば、無限ループ( infinite loop )になる。

Slide 76

Slide 76 text

IF • if⽂はfor⽂同様、丸括弧は不要

Slide 77

Slide 77 text

IF WITH A SHORT STATEMENT • for⽂のように条件式の前に、初期化⽂を書ける • 初期化⽂で宣⾔した変数は、if⽂のスコープ内のみ有効

Slide 78

Slide 78 text

IF AND ELSE • if⽂の初期化⽂で宣⾔した変数は elseブロック内でも使⽤可能である ※ else if も使⽤可能

Slide 79

Slide 79 text

SWITCH • switch⽂を使うことでIf-else⽂と同等のことを シンプルにかける • switch⽂もfor⽂のように条件式の前に、 初期化⽂を書ける • 他⾔語とは違い、 選択された case だけを実⾏して それに続く全ての case は実⾏されない • caseも定数である必要はなく、 関係する値は整数である必要もない

Slide 80

Slide 80 text

SWITCH EVALUATIONS ORDER • switch⽂は上から下へcaseを評価する • caseの条件が⼀致すれば、そこで停⽌(⾃動的 にbreak)する ※Go playground上の時間は、 いつも "2009-11-10 23:00:00 UTC"

Slide 81

Slide 81 text

SWITCH EVALUATIONS ORDER ※Go playground上の時間は、 いつも "2009-11-10 23:00:00 UTC" (問題) 左記が⽰している⽇時は何の⽇でしょう︖ 「Go 1」が リリースされた⽇ Goが公のオープンソース プロジェクトになった⽇ Goという名前がついた⽇ A B C

Slide 82

Slide 82 text

SWITCH EVALUATIONS ORDER ※Go playground上の時間は、 いつも "2009-11-10 23:00:00 UTC" (問題) 左記が⽰している⽇時は何の⽇でしょう︖ 「Go 1」が リリースされた⽇ Goが公のオープンソース プロジェクトになった⽇ Goという名前がついた⽇ A B C 2012.03.28 2007.09.25

Slide 83

Slide 83 text

SWITCH EVALUATIONS ORDER • switch⽂は上から下へcaseを評価する • caseの条件が⼀致すれば、そこで停⽌(⾃動的 にbreak)する ※Go playground上の時間は、 いつも "2009-11-10 23:00:00 UTC" (答え) Goプロジェクトが 公のオープンソースプロジェクトになった⽇

Slide 84

Slide 84 text

SWITCH WITH NO CONDITION • 条件のないswitchは、 switch true と書くことと同じ • switch⽂を使えば⻑くなりがちな “if-then-else” のつながりをシンプルに表現できる

Slide 85

Slide 85 text

DEFER • defer⽂は、deferへ渡した関数の実⾏を、 呼び出し元の関数の終わりまで遅延させる • defer へ渡した関数の引数はすぐに評価されるが、 その関数⾃体は呼び出し元の関数がreturnするまで実⾏されない

Slide 86

Slide 86 text

DEFER (問題) 左記のコードを実⾏した時、出⼒結果はどうなる︖ まず「1」が出⼒されて、 次に「3」が出⼒される まず「3」が出⼒されて、 次に「0」が出⼒される まず「1」が出⼒されて、 次に「0」が出⼒される A B C

Slide 87

Slide 87 text

DEFER (問題) 左記のコードを実⾏した時、出⼒結果はどうなる︖ まず「1」が出⼒されて、 次に「3」が出⼒される まず「3」が出⼒されて、 次に「0」が出⼒される まず「1」が出⼒されて、 次に「0」が出⼒される A B C

Slide 88

Slide 88 text

STACKING DEFERS • defer へ渡した関数が複数ある場合、 その呼び出しは スタック( stack )される • 呼び出し元の関数が returnするとき、 defer へ渡した関数は LIFO(last-in-first-out) の順番で 実⾏される

Slide 89

Slide 89 text

STACKING DEFERS fmt.Println(0) main関数 deferスタック領域 i = 0 の時 LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 90

Slide 90 text

STACKING DEFERS fmt.Println(1) fmt.Println(0) main関数 deferスタック領域 i = 1 の時 LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 91

Slide 91 text

STACKING DEFERS fmt.Println(2) fmt.Println(1) fmt.Println(0) main関数 deferスタック領域 i = 2 の時 LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 92

Slide 92 text

STACKING DEFERS fmt.Println(9) … fmt.Println(2) fmt.Println(1) fmt.Println(0) main関数 deferスタック領域 i = 9 の時 LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 93

Slide 93 text

STACKING DEFERS fmt.Println(9) … fmt.Println(2) fmt.Println(1) fmt.Println(0) main関数 deferスタック領域 main関数終了時 Call LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 94

Slide 94 text

STACKING DEFERS … fmt.Println(2) fmt.Println(1) fmt.Println(0) main関数 deferスタック領域 main関数終了時 Call … LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 95

Slide 95 text

STACKING DEFERS fmt.Println(2) fmt.Println(1) fmt.Println(0) main関数 deferスタック領域 main関数終了時 Call LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 96

Slide 96 text

STACKING DEFERS fmt.Println(1) fmt.Println(0) main関数 deferスタック領域 main関数終了時 Call LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 97

Slide 97 text

STACKING DEFERS fmt.Println(0) main関数 deferスタック領域 main関数終了時 Call LIFO(last-in-first-out) ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 98

Slide 98 text

STACKING DEFERS 実⾏結果 ※プロダクトコードでfor文内でdeferはアンチパターンなので注意

Slide 99

Slide 99 text

基礎構⽂ その他の型 STRUCT, SLICES, MAPS

Slide 100

Slide 100 text

POINTERS

Slide 101

Slide 101 text

POINTERS メモリアドレス 値 … … … … … … 0x00414020 42 0x00414024 2701 … … 出⼒

Slide 102

Slide 102 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414020 … … 0x00414020 42 0x00414024 2701 … … &(アドレス演算⼦)でメモリアドレスを取得 出⼒

Slide 103

Slide 103 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414020 … … 0x00414020 42 0x00414024 2701 … … pの型は*int型 出⼒ int型のポインタ

Slide 104

Slide 104 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414020 … … 0x00414020 42 0x00414024 2701 … … pの型は*int型 出⼒ ゼロ値は nil が宣⾔される

Slide 105

Slide 105 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414020 … … 0x00414020 42 0x00414024 2701 … … *pでpに格納されたアドレスを参照し、 参照先の値を取得する 出⼒ 42

Slide 106

Slide 106 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414020 … … 0x00414020 21 0x00414024 2701 … … *pでpに格納されたアドレス先に 値を格納する 出⼒ 42

Slide 107

Slide 107 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414020 … … 0x00414020 21 0x00414024 2701 … … *pでpに格納されたアドレス先に 値を格納する 出⼒ 42 間接参照(dereferencingまたはindirecting)

Slide 108

Slide 108 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414020 … … 0x00414020 21 0x00414024 2701 … … 出⼒ 42 21

Slide 109

Slide 109 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414024 … … 0x00414020 21 0x00414024 2701 … … 出⼒ 42 21 &(アドレス演算⼦)でメモリアドレスを取得

Slide 110

Slide 110 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414024 … … 0x00414020 21 0x00414024 2701 … … 出⼒ 42 21 *pでpに格納されたアドレス先から 値(2701)を参照する

Slide 111

Slide 111 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414024 … … 0x00414020 21 0x00414024 73 … … 出⼒ 42 21 2701÷37をした結果得た「73」を 参照先に格納する

Slide 112

Slide 112 text

POINTERS メモリアドレス 値 … … 0x0040C140 0x00414024 … … 0x00414020 21 0x00414024 73 … … 出⼒ 42 21 73

Slide 113

Slide 113 text

POINTERS 余談 GoはCのような、 ポインタ演算はもっていない ポインタ演算 →誤って意図しないアドレスに アクセスすることを防ぐため

Slide 114

Slide 114 text

POINTERS nil について By Package builtin (https://golang.org/pkg/builtin) 事前定義された識別⼦ 蛇⾜

Slide 115

Slide 115 text

POINTERS nil について By Package builtin (https://golang.org/pkg/builtin) 事前定義された識別⼦ Goで予約されている キーワードでは無い 蛇⾜

Slide 116

Slide 116 text

POINTERS By The Go Programming Language Specification (https://golang.org/ref/spec) Goの予約語(識別⼦としては使えない) 蛇⾜

Slide 117

Slide 117 text

POINTERS By The Go Programming Language Specification (https://golang.org/ref/spec) Goの予約語(識別⼦としては使えない) 蛇⾜

Slide 118

Slide 118 text

STRUCTS struct { X int Y int } 構造体

Slide 119

Slide 119 text

... (By https://golang.org/ref/spec#Struct_types) 構造体はフィールドの集まり

Slide 120

Slide 120 text

STRUCTS 構造体(struct)を Vertexというユーザ定義型で 宣言している

Slide 121

Slide 121 text

STRUCTS Vertex{ 1 , 2 } X Y

Slide 122

Slide 122 text

STRUCT FIELDS ドット(.)を使って 構造体のフィールドにアクセスできる

Slide 123

Slide 123 text

POINTERS TO STRUCTS 構造体のフィールドは、 構造体ポインタ越しにアクセスできる

Slide 124

Slide 124 text

POINTERS TO STRUCTS 構造体のフィールドは、 構造体ポインタ越しにアクセスできる ポインタの知識を使えば、 構造体の X フィールドに、 構造体ポインタ p でアクセスする時 (*p).X と記述する

Slide 125

Slide 125 text

POINTERS TO STRUCTS 構造体のフィールドは、 構造体ポインタ越しにアクセスできる ポインタの知識を使えば、 構造体の X フィールドに、 構造体ポインタ p でアクセスする時 (*p).X と記述する しかし、この記述は⾯倒なため、 代わりに露⾻な参照なしの p.X と書くことも認められている

Slide 126

Slide 126 text

STRUCT LITERALS Xフィールドに1, Yフィールドに2が 割り当てられる ただしこの場合、 全フィールドに値を与える必要がある

Slide 127

Slide 127 text

STRUCT LITERALS Name:⽂法を使うことで、 Xだけ値を割り当てることができる この場合、 Yは0が暗黙的に割り当てられる

Slide 128

Slide 128 text

STRUCT LITERALS 何も与えない場合は、 Xは0、Yは0が割り当てられる

Slide 129

Slide 129 text

STRUCT LITERALS pは*Vertex(Vertexのポインタ型)になる

Slide 130

Slide 130 text

ARRAYS [n]T 型は、T型の値をn個もつ配列

Slide 131

Slide 131 text

ARRAYS [n]T 型は、T型の値をn個もつ配列 2個のstring型をもつ配列と宣⾔している

Slide 132

Slide 132 text

ARRAYS [n]T 型は、T型の値をn個もつ配列 2個のstring型をもつ配列と宣⾔している 配列の⻑さも配列型の⼀部のため、 配列の⻑さを変えることはできない。

Slide 133

Slide 133 text

SLICES スライスは可変⻑ 配列は固定⻑ 型 []T は型 T のスライスを表す この例の場合、 int型のスライスを表している

Slide 134

Slide 134 text

SLICES コロンで区切られた⼆つのインデックス low と high で 境界を指定することによりスライスが形成される a[low : high] この例の場合、 primesからインデックス1からインデックス4までをスライ スとするため、sは以下のようになる [3 5 7]

Slide 135

Slide 135 text

SLICES ARE LIKE REFERENCES TO ARRAYS スライスは配列の参照のようなもの (By https://github.com/golang/go/blob/master/src/runtime/slice.go)

Slide 136

Slide 136 text

SLICES ARE LIKE REFERENCES TO ARRAYS スライスは配列の参照のようなもの 実態の先頭アドレスを指し⽰すポインタ (By https://github.com/golang/go/blob/master/src/runtime/slice.go)

Slide 137

Slide 137 text

SLICES ARE LIKE REFERENCES TO ARRAYS スライスは配列の参照のようなもの 取り出せる⻑さ(length) (By https://github.com/golang/go/blob/master/src/runtime/slice.go)

Slide 138

Slide 138 text

SLICES ARE LIKE REFERENCES TO ARRAYS スライスは配列の参照のようなもの 本スライスの容量(capacity) (By https://github.com/golang/go/blob/master/src/runtime/slice.go)

Slide 139

Slide 139 text

SLICES ARE LIKE REFERENCES TO ARRAYS スライスは配列の参照のようなもの capサイズ内でlenサイズが可変である (By https://github.com/golang/go/blob/master/src/runtime/slice.go)

Slide 140

Slide 140 text

スライスはどんなデータも格納しておらず、 単に元の配列の部分列を指し⽰している メモリアドレス 値 0x004C0000 “John” 0x004C0004 “Paul” 0x004C0008 “George” 0x004C000C “Ringo” ※説明をイメージしてもらうためにメモリマップを書いているが、実際とは異なる。 names

Slide 141

Slide 141 text

スライスはどんなデータも格納しておらず、 単に元の配列の部分列を指し⽰している メモリアドレス 値 0x004C0000 “John” 0x004C0004 “Paul” 0x004C0008 “George” 0x004C000C “Ringo” ※説明をイメージしてもらうためにメモリマップを書いているが、実際とは異なる。 names フィールド 値 array 0x004C0000 len 2 cap 4 a

Slide 142

Slide 142 text

スライスはどんなデータも格納しておらず、 単に元の配列の部分列を指し⽰している メモリアドレス 値 0x004C0000 “John” 0x004C0004 “Paul” 0x004C0008 “George” 0x004C000C “Ringo” ※説明をイメージしてもらうためにメモリマップを書いているが、実際とは異なる。 names フィールド 値 array 0x004C0000 len 2 cap 4 フィールド 値 array 0x004C0004 len 2 cap 3 a b

Slide 143

Slide 143 text

スライスはどんなデータも格納しておらず、 単に元の配列の部分列を指し⽰している メモリアドレス 値 0x004C0000 “John” 0x004C0004 “XXX” 0x004C0008 “George” 0x004C000C “Ringo” ※説明をイメージしてもらうためにメモリマップを書いているが、実際とは異なる。 names フィールド 値 array 0x004C0000 len 2 cap 4 フィールド 値 array 0x004C0004 len 2 cap 3 a b

Slide 144

Slide 144 text

SLICE LITERALS q := []int{2, 3, 5, 7, 11, 13} 上記はまず、 [6]int{2, 3, 5, 7, 11, 13} という配列ができ、 それを参照するスライスが 作成され、 qに初期化⼦として定義される

Slide 145

Slide 145 text

SLICE DEFAULTS スライスするときは、 既定値を代わりに使⽤することで 上限(high)または下限(low)を 省略することができる 規定値 上限(high) ︓スライスの⻑さ 下限(low) ︓0

Slide 146

Slide 146 text

SLICE DEFAULTS メモリアドレス 値 0x00456000 2 0x00456004 3 0x00456008 5 0x0045600C 7 0x00456010 11 0x00456014 13 フィールド 値 array 0x00456000 len 6 cap 6 orignal s 出⼒

Slide 147

Slide 147 text

SLICE DEFAULTS メモリアドレス 値 0x00456000 2 0x00456004 3 0x00456008 5 0x0045600C 7 0x00456010 11 0x00456014 13 フィールド 値 array 0x00456004 len 3 cap 5 orignal s 出⼒ [3 5 7]

Slide 148

Slide 148 text

SLICE DEFAULTS メモリアドレス 値 0x00456000 2 0x00456004 3 0x00456008 5 0x0045600C 7 0x00456010 11 0x00456014 13 フィールド 値 array 0x00456004 len 2 cap 5 orignal s 出⼒ [3 5 7] [3 5]

Slide 149

Slide 149 text

SLICE DEFAULTS メモリアドレス 値 0x00456000 2 0x00456004 3 0x00456008 5 0x0045600C 7 0x00456010 11 0x00456014 13 フィールド 値 array 0x00456008 len 1 cap 4 orignal s 出⼒ [3 5 7] [3 5] [5]

Slide 150

Slide 150 text

SLICE LENGTH AND CAPACITY スライスの⻑さ︓ スライスに含まれる要素の数 スライスの容量︓ スライス内の最初の要素から数えた、 基礎となる配列内の要素の数 スライスの⻑さを 取得している スライスの容量を 取得している

Slide 151

Slide 151 text

(by https://golang.org/pkg/builtin/)

Slide 152

Slide 152 text

NIL SLICES スライスのゼロ値は nil である nilスライスは⻑さと容量が0で、 基本となる配列をもっていない

Slide 153

Slide 153 text

CREATING A SLICE WITH MAKE 組み込み関数であるmake関数を使うことで、 動的サイズの配列を作成できる

Slide 154

Slide 154 text

(by https://golang.org/pkg/builtin/)

Slide 155

Slide 155 text

フィールド 値 array 0x00456000 len 5 cap 5 a 出⼒ a len=5 cap=5 [0 0 0 0 0] メモリアドレス 値 0x00456000 0 0x00456004 0 0x00456008 0 0x0045600C 0 0x00456010 0 a orignal

Slide 156

Slide 156 text

フィールド 値 array 0x00456040 len 0 cap 5 b 出⼒ a len=5 cap=5 [0 0 0 0 0] b len=0 cap=5 [] b orignal メモリアドレス 値 0x00456040 0 0x00456044 0 0x00456048 0 0x0045604C 0 0x00456050 0

Slide 157

Slide 157 text

出⼒ a len=5 cap=5 [0 0 0 0 0] b len=0 cap=5 [] c len=2 cap=5 [0 0] フィールド 値 array 0x00456040 len 0 cap 5 b b orignal メモリアドレス 値 0x00456040 0 0x00456044 0 0x00456048 0 0x0045604C 0 0x00456050 0 フィールド 値 array 0x00456040 len 2 cap 5 c

Slide 158

Slide 158 text

出⼒ a len=5 cap=5 [0 0 0 0 0] b len=0 cap=5 [] c len=2 cap=5 [0 0] d len=3 cap=3 [0 0 0] フィールド 値 array 0x00456040 len 0 cap 5 b b orignal メモリアドレス 値 0x00456040 0 0x00456044 0 0x00456048 0 0x0045604C 0 0x00456050 0 フィールド 値 array 0x00456040 len 2 cap 5 c フィールド 値 array 0x00456048 len 3 cap 3 d

Slide 159

Slide 159 text

SLICES OF SLICES スライスには要素として 他のスライスを含む任意のタイプを 含めることができる 多次元スライスが表現可能

Slide 160

Slide 160 text

APPENDING TO A SLICE スライスへ新しい要素を追加する

Slide 161

Slide 161 text

(by https://golang.org/pkg/builtin/)

Slide 162

Slide 162 text

フィールド 値 array nil len 0 cap 0 s メモリアドレス 値 s orignal 出⼒ len=0 cap=0 []

Slide 163

Slide 163 text

フィールド 値 array 0x00414028 len 1 cap 2 s メモリアドレス 値 0x00414028 0 0x0041402C 0 s orignal 出⼒ len=0 cap=0 [] len=1 cap=2 [0] 容量が不⾜しているため、 新たに配列が割り当てられた

Slide 164

Slide 164 text

フィールド 値 array 0x00414028 len 1 cap 2 s メモリアドレス 値 0x00414028 0 0x0041402C 0 s orignal 出⼒ len=0 cap=0 [] len=1 cap=2 [0] 容量が不⾜しているため、 新たに配列が割り当てられた 新たに割り当てられる容量は、 おおよそ2倍ずつ確保される

Slide 165

Slide 165 text

フィールド 値 array 0x00414028 len 1 cap 2 s メモリアドレス 値 0x00414028 0 0x0041402C 0 s orignal 出⼒ len=0 cap=0 [] len=1 cap=2 [0] 容量が不⾜しているため、 新たに配列が割り当てられた 新たに割り当てられる容量は、 おおよそ2倍ずつ確保される 「TCMalloc (Thread-Caching Malloc)」 というアルゴリズムを使って、高速に動的メモリを確保している TCMallocについての参考: Google が公開しているソフトウェアの解説(その4)- Performance tools - (https://japan.googleblog.com/2009/05/google-4-performance- tools.html) の後半でTCMallocについて説明されている

Slide 166

Slide 166 text

フィールド 値 array 0x00414028 len 2 cap 2 s メモリアドレス 値 0x00414028 0 0x0041402C 1 s orignal 出⼒ len=0 cap=0 [] len=1 cap=2 [0] len=2 cap=2 [0 1] 容量があるため、 スライスし直されて 値がセットされた

Slide 167

Slide 167 text

フィールド 値 array 0x0045E020 len 5 cap 8 s メモリアドレス 値 0x0045E020 0 0x0045E024 1 0x0045E028 2 0x0045E02C 3 0x0045E030 4 s orignal 出⼒ len=0 cap=0 [] len=1 cap=2 [0] len=2 cap=2 [0 1] len=5 cap=8 [0 1 2 3 4] 容量が不⾜しているため、 新たに配列が割り当てられた

Slide 168

Slide 168 text

RANGE for ループに利用する range は、 ・スライス(slice) ・マップ(map) ・配列 ・チャネル に対して反復処理を行う (by https://github.com/golang/go/wiki/Range)

Slide 169

Slide 169 text

RANGE インデックス インデックスの場所の要素のコピー 詳細は、以下のURL先を参照。 https://github.com/golang/go/wiki/Range

Slide 170

Slide 170 text

RANGE CONTINUED インデックスだけ取得する場合 または for i, _ := range pow 要素だけ取得する場合 for _, v := range pow for i := range pow

Slide 171

Slide 171 text

MAPS map はキーと値とを関連付ける make 関数は指定された型の マップを初期化し、 使⽤可能な状態で返す マップのゼロ値は nil nil マップはキーがなく、 またキーを追加することもできない 詳細は、以下のURL先を参照。 https://blog.golang.org/go-maps-in-action https://github.com/golang/go/blob/master/src/runtime/map.go

Slide 172

Slide 172 text

MAP LITERALS mapリテラルは、 structリテラルに似ているが、 キー ( key )が必要

Slide 173

Slide 173 text

MAP LITERALS mapリテラルは、 structリテラルに似ているが、 キー ( key )が必要

Slide 174

Slide 174 text

(By https://golang.org/ref/spec#Composite_literals) コンポジット型のリテラルは、 構造体、配列、スライス、マップの値を構築し、評価されるたびに新しい値を作成します。 これらは、リテラルのタイプと、それに続く中括弧で区切られた要素のリストで構成されます。 オプションで、各要素の前に対応するキーを置くことができます。

Slide 175

Slide 175 text

MAP LITERALS CONTINUED 最上位の型が単なる型名である場合、 リテラルの要素から省略できる 省略していない書き⽅

Slide 176

Slide 176 text

MUTATING MAPS 要素(elem)の挿⼊や更新: m[key] = elem 要素の取得: elem = m[key] 要素の削除: delete(m, key) キーに対する要素が存在するかどうかは、2つめの値で確認する: elem, ok = m[key] ok はキーが存在しる場合は true 、存在しない場合は false となる mapに key が存在しない場合、 elem はmapの要素の型のゼロ値となる

Slide 177

Slide 177 text

FUNCTION VALUES 他の変数のように 関数を代⼊することができる 関数値( function value )は、 関数の引数に取ることもでき、 戻り値としても利⽤できる

Slide 178

Slide 178 text

FUNCTION CLOSURES Goの関数は クロージャ( closure )の場合がある クロージャは、 それ⾃⾝の外部から変数を参照する関数値 関数は、参照された変数にアクセスして 割り当てることができる この意味で、 関数は変数に「バインド(bound)」される

Slide 179

Slide 179 text

pos neg func(x int) int { sum += x return sum } func(x int) int { sum += x return sum } sum int sum int 出⼒ 0 0 1 -2 3 -6 6 -12 10 -20 15 -30 21 -42 28 -56 36 -72 45 -90

Slide 180

Slide 180 text

⼀緒に読むと良い記事 • Go⾔語の初⼼者が⾒ると幸せになれる場所 #golang (https://qiita.com/tenntenn/items/0e33a4959250d1a55045) • 他⾔語プログラマがgolangの基本を押さえる為のまとめ (https://qiita.com/tfrcm/items/e2a3d7ce7ab8868e37f7) • 実装して理解するスライス #golang (https://qiita.com/tenntenn/items/5229bce80ddb688a708a) • Goを学びたての⼈が誤解しがちなtypeと構造体について #golang (https://qiita.com/tenntenn/items/45c568d43e950292bc31) • ゼロ値を使おう #golang (https://qiita.com/tenntenn/items/c55095585af64ca28ab5) • Goのスコープについて考えてみよう #golang (https://qiita.com/tenntenn/items/ac5940dfbca703183fdf) • STRING と RUNE (https://text.baldanders.info/golang/string-and-rune/)

Slide 181

Slide 181 text

⼀緒に読むと良い記事 • 忘れがちなGo⾔語の書式指定⼦を例付きでまとめた (https://qiita.com/Sekky0905/items/c9cbda2498a685517ad0) • Go⾔語 if⽂のサンプル (https://itsakura.com/golang-if#s1) • エキスパートGo (https://www.slideshare.net/takuyaueda967/go-77689475) • Goのnil,true,falseは変数名に使えるという話 (https://shogo82148.github.io/blog/2018/11/22/go-nil/) • Goのスライス容量拡張量がどのように決まるのか追った / 180713 LT (https://speakerdeck.com/kaznishi/180713-lt) • goimportsを使ってIntellij IDEAでGoのコードのimportを⼿軽に整理する (https://qiita.com/dmnlk/items/c423d5853cc129ab77a4) • Goの定数の話 (https://qiita.com/hkurokawa/items/a4d402d3182dff387674)

Slide 182

Slide 182 text

THANKS • A Tour of Go (http://tour.golang.org/) • A Tour of Go (⽇本語翻訳版) (https://go-tour-jp.appspot.com) • gopherize.me (https://gopherize.me/) • egonelbre/gophers (https://github.com/egonelbre/gophers)