I just saw a presentation of the Go programming language and thought I'd try to write a few lines. Everything worked fine until I tried to use an interface in this situation. How do I solve this?
package main
import "fmt"
type entity float32
func (e *entity) inc() {
*e++
}
type incer interface {
inc()
}
func doSomething(i incer) {
i.inc()
}
func main() {
fmt.Println("Hello, 世界")
var e entity = 3
e.inc()
doSomething(e)
fmt.Println(e)
}
I get the compiler error:
prog.go:24: cannot use e (type entity) as type incer in function argument:
entity does not implement incer (inc method requires pointer receiver)
I want to use a pointer so that the inc() will affect the enity outside the function. What is the syntax I should use?
/Ricky
You can declare methods with pointer receivers. This means the receiver type has the literal syntax *T for some type T . (Also, T cannot itself be a pointer such as *int .) For example, the Scale method here is defined on *Vertex .
Pointer receiver passes the address of a type to the function. The function stack has a reference to the original object. So any modifications on the passed object will modify the original object. This shows that the method with value receivers modifies a copy of an object, And the original object remains unchanged.
I think there is some confusion here. inc
is a method of the type *entity
, and not of the type entity
(while you can call methods on values directly on pointers; you cannot generally call methods on pointers directly on values). What you may be confused about is why you could call e.inc()
, instead of having to do (&e).inc()
. This is a little-known special case documented at the bottom of the Calls section in the language specification, that says if x
is addressable, and &x
's method set contains m
, then x.m()
is shorthand for (&x).m()
. This applies to this case because e
is a variable, so it is addressable; but other expressions may not be addressable. I would recommend that you not use this shortcut, however, as it causes confusion; it makes you think that e
conforms to the interface inter
, while it does not.
Change it to: doSomething(&e). func (e *entity) inc() satisfies incer interface only for *entity type. There is no inc() for just entity type and that's what's you're passing to doSomething().
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With