Open3
Golang
A Tour of Go メモ
YouTubeのvideoIDが不正です
Exercise: Errors
注意: Error メソッドの中で、 fmt.Sprint(e) を呼び出すことは、無限ループのプログラムになることでしょう。
switch v := p.arg.(type) {
case error:
handled = true
defer p.catchPanic(p.arg, verb, "Error")
p.fmtString(v.Error(), verb)
return
errorはv.Error()
でエラーを呼んでいるのでループする
package main
import (
"fmt"
"math"
)
const dz = 1e-10
type ErrNegativeSqrt float64
func (e ErrNegativeSqrt) Error() string {
return fmt.Sprintf("cannot Sqrt negative number: %d", float64(e))
}
func Sqrt(x float64) (float64, error) {
if x < 0 {
return 0, ErrNegativeSqrt(x)
}
z, d := x, 0.0
for math.Abs(z - d) > dz {
d, z = z, z-(z*z - x) / (2 * z)
}
return z, nil
}
func main() {
fmt.Println(Sqrt(2))
fmt.Println(Sqrt(-2))
}
埋め込まれたインターフェースの実装を動的に変更する
func main() {
p := NewPerson("ko", "na", 23)
fmt.Println(p) // ko na (23)
p.SetStringer(func(p *Person) string {
return fmt.Sprintf("名前は%s%s。年齢は%dです。", p.FirstName, p.LastName, p.Age)
})
fmt.Println(p) // 名前はkona。年齢は23です。
}
type stringer fmt.Stringer
type Person struct {
stringer
FirstName string
LastName string
Age int
}
type StringerFunc func() string
func (sf StringerFunc) String() string { // StringerFunc型にString()メソッドを実装するための記述(fmt.Stringerを満たすようにする)
return sf()
}
func NewPerson(firstName, lastName string, age int) *Person {
p := &Person{
nil,
firstName,
lastName,
age,
}
p.stringer = StringerFunc(func() string {
return fmt.Sprintf("%s %s (%d)", p.FirstName, p.LastName, p.Age)
})
return p
}
func (p *Person) SetStringer(sf func(p *Person) string) {
p.stringer = StringerFunc(func() string {
return sf(p)
})
}
Goroutines
main関数、GCもgoroutine。
goroutineは、同じアドレス空間で実行される。以下の例では、goroutineを実行する準備をしている間にfor文は5回回りきってしまうため、fmt.Println("world", i)
がiを表示するときには、iは5になっている。
func say(s string) {
for i := 0; i < 5; i++ {
time.Sleep(100 * time.Millisecond)
fmt.Println(s)
}
}
func main() {
for i := 0; i < 5; i++ {
go func() {
time.Sleep(100 * time.Millisecond)
fmt.Println("world", i)
}()
}
say("hello")
}
world 5
hello
world 5
world 5
world 5
world 5
hello
hello
hello
hello
Channels
自分的には、「データ構造がキューである筒」みたいなイメージ。
c <- number
を行うたびに、cという筒にqueueしている。
receiveNumber := <-c
と行うたびに、cという筒からdequeueしている。