Method Expressions

A method is a function associated to a type. The Go method declaration is a variation of a function declaration in which a initial parameter appears before the method name. The parameter has the type of the object designed to receive the method or is a pointer of that type.
In this example the type Order has two methods, the AddProduct and the CalculateTotalCost.
    type Order struct {
        Id          int32
        ProductList []Product

    func (o *Order) AddProduct(p Product) {
        o.ProductList = append(o.ProductList, p)

    func (o *Order) CalculateTotalCost() (cost float32) {
        for _, p := range o.ProductList {
             cost += p.Price

We can call a method on an instance of the type Order or we can use a method value
    o := Order{Id: 1}
    o.AddProduct(Product{Id: 1, Name: "milk", Price: 1.1})
    // method value
    addProduct := o.AddProduct
    addProduct(Product{Id: 2, Name: "bread", Price: 2.11})

The variable addProduct refers the method value that is a function that binds the method AddProduct to the instance of the type Order. These methods values can be useful when we do not want pass to a function a type or a pointer to a type, but only the method that will be executed within the function.

To define a method value we need the instance of a type, but if we want to call a method as if it was a function, we can use a method expression
    // method expression
    calculateTotalCost := (*Order).CalculateTotalCost
    // the first parameter is the receiver of the method
    cost := calculateTotalCost(&o)
    fmt.Printf(" Total Cost : $%f\r\n", cost)

We call the method expression passing the receiver of the method as the first parameter.

Method expression can be used also with interfaces. Let we define the interface PriceCalculator
    // single method interface
    type PriceCalculator interface {
        CalculateTotalCost() (cost float32)

We define the calculatePrice method expression and we call it

    // method expression using interface
    calculatePrice := PriceCalculator.CalculateTotalCost
    // the first parameter is always the receiver of the method
    cost = calculatePrice(&o)
    fmt.Printf(" Total Cost : $%f\r\n", cost)
    o2 := Order{Id: 2}
    o2.AddProduct(Product{Id: 1, Name: "milk", Price: 1.1})
    cost = calculatePrice(&o2)
    fmt.Printf(" Total Cost : $%f\r\n", cost)

Method expression can be used to choose a method and call it on many receiver.


Post popolari in questo blog

OAuth 2.0 Server & Authorization Middleware for Gin-Gonic

Data Model Generation for PostgreSQL

From the database schema to RESTful API with DinGo