より良いエンジニアを目指して

1日1つ。良くなる!上手くなる!

読書感想「Go言語ハンズオン」

Go言語 ハンズオン

Go言語について自分の知りたいことが書いてある本でした。

Go言語といえば、並列処理なのですが、go メソッド名とするとメインスレッドとは別スレッドで処理が流れるのはわかった。

しかし、その処理はどこで待つんだという疑問がやっとこの本を読んで解けました。

チャンネルから値を取得する場合、その値が送られるまで処理を待つ

です。

package main

import "fmt"

func total(n int, c chan int) {
    t := 0
    for i := 1; i <= n; i++ {
        t += i
    }
    c <- t
}

func main() {
    c := make(chan int)
    go total(100, c)
    // チャンネルから値を取得する場合、その値が送られるまで処理を待つ
    fmt.Println("total:", <-c)
}

select

select文を使うことで値が操作したチャンネルに対して処理を行うこともできます。これも初耳でしたね。

package main

import (
    "fmt"
    "time"
)

func count(n int, s int ,c chan int) {
    for i := 1; i <= n; i++ {
        c <-i
        time.Sleep(time.Duration(s) * time.Millisecond)
    }
}

func main()  {
    n1,n2,n3 := 3,5,10
    m1,m2,m3 := 100,75,50
    c1 := make(chan int)
    go count(n1,m1,c1)
    c2 := make(chan int)
    go count(n2,m2,c2)
    c3 := make(chan int)
    go count(n3,m3,c3)


    for i:= 0; i< n1+n2+n3; i++ {
        // select文で値の操作があったものに対して処理が発生する
        select {
        case re:= <-c1:
            fmt.Println(" * first",re)
        case re:= <-c2:
            fmt.Println(" * second",re)
        case re:= <-c3:
            fmt.Println(" * third",re)
        }
    }
    fmt.Println("*** finish ***")
}

Go言語でGUI

Fyneというのがあるそうです。

fyne.io

f:id:rimever:20210627155610p:plain
警告は出てくるが、きちんと小さいウインドウが表示された

本書では、私が試した時にはAPIが変わったのかwidget.NewVBoxとなっていますが、container.NewVBoxにする必要がありました。

package main

import (
    "fyne.io/fyne/v2/app"
    "fyne.io/fyne/v2/container"
    "fyne.io/fyne/v2/widget"
)

func main() {
    a := app.New()
    w := a.NewWindow("Hello")
    w.SetContent(container.NewVBox(
        widget.NewLabel("Hello Fyne!"), widget.NewLabel("This is sample application"),
        ))
}

これが動かせると俄然楽しくなってきますね。

タブ

https://developer.fyne.io/tour/container/

以下を参考に

package main

import (
    "fyne.io/fyne/v2/app"
    "fyne.io/fyne/v2/container"
    "fyne.io/fyne/v2/widget"
)

func main() {
    a := app.New()
    w := a.NewWindow("Hello")
    tabs := container.NewAppTabs(
        container.NewTabItem("First", widget.NewLabel("This is First tab item.")),
        container.NewTabItem("Second",widget.NewLabel("This is Second tab item.")),
        )
    tabs.SetTabLocation(container.TabLocationTop)
    w.SetContent(tabs)
    w.ShowAndRun()
}

f:id:rimever:20210701200807p:plain
電卓も作れる