[Go]メソッドはレシーバーが第一引数になる関数として扱われる

type Book struct {
    title string
    author string
}

func (b *Book) profile(header string) string {
    return fmt.Sprintf("%s Profile[title: %s, author: %s]", header, b.title, b.author)
}

// レシーバーは基本的にポインタ型にする。値型にすると呼び出し時にレシーバーそのもののコピーが発生し、レシーバーの構造体に対して値の代入をしても反映されないため。
func (b Book) profile2(header string) string {
    return fmt.Sprintf("%s Profile[title: %s, author: %s]", header, b.title, b.author)
}

func main() {
    book1 := &Book{title: "Good Code Bad Code", author: "Tom Long"}
    fmt.Printf("book1 -> %s\n", book1.profile("***"))

    book2 := Book{title: "xxx books", author: "many people"}
    fmt.Printf("book2 -> %s\n", book2.profile2("@@@"))
}

book1 -> *** Profile[title: Good Code Bad Code, author: Tom Long]
book2 -> @@@ Profile[title: xxx books, author: many people]

f1 := (*Book).profile
f2 := (Book).profile2

fmt.Printf("Book.profile -> %T\n", f1)
fmt.Printf("Book.profile2 -> %T\n", f2)

// メソッドの関数定義を確認してみると第一引数にレシーバーがあることがわかる
Book.profile -> func(*main.Book, string) string
Book.profile2 -> func(main.Book, string) string

【参考】