By using Point{1, 2}.ScaleBy(2) you are trying to call pointer receiver method ScaleBy with value: Point{1, 2}:
The method set of any other type T consists of all methods declared
with receiver type T.
but if you use addressable type:
The method set of the corresponding pointer type *T is the set of all
methods declared with receiver *T or T (that is, it also contains the
method set of T).
then it is possible: meaning you or the compiler should get the address of temporary value (Taking the address of a composite literal):
Address operators:
For an operand x of type T, the address operation &x generates a
pointer of type *T to x. The operand must be addressable, that is,
either a variable, pointer indirection, or slice indexing operation;
or a field selector of an addressable struct operand; or an array
indexing operation of an addressable array. As an exception to the
addressability requirement, x may also be a (possibly parenthesized)
composite literal. If the evaluation of x would cause a run-time
panic, then the evaluation of &x does too.
ref: https://golang.org/ref/spec#Address_operators
You may call (&Point{1, 2}).ScaleBy(2)
like this working sample code (pointer receiver):
package main
import "fmt"
func main() {
p := (&Point{1, 2}).ScaleBy(2)
fmt.Println(p) // &{2 4}
}
type Point struct {
X, Y int
}
func (p *Point) ScaleBy(factor float64) *Point {
p.X *= 2
p.Y *= 2
return p
}
you may call Point{1, 2}.ScaleBy(2)
like this working sample code (value receiver):
package main
import "fmt"
func main() {
p := Point{1, 2}.ScaleBy(2)
fmt.Println(p) // &{2 4}
}
type Point struct {
X, Y int
}
func (p Point) ScaleBy(factor float64) *Point {
p.X *= 2
p.Y *= 2
return &p
}
output:
&{2 4}
also see this working sample code (pointer receiver):
package main
import "fmt"
func main() {
p := Point{1, 2}
p.ScaleBy(2)
fmt.Println(p) // {2 4}
}
type Point struct {
X, Y int
}
func (p *Point) ScaleBy(factor float64) {
p.X *= 2
p.Y *= 2
}
output:
{2 4}