Justification for Go Method Syntax

Well, I have to admit that I really don't use Go very much, but I just watched something that amazes me as strange for a language that tends to be minimal and all the good things that Go does. I would be surprised if there is no legal justification behind it, so I'm looking.

So, when you have a method, you define it as follows:

func (s *SomeStruct) Foo(x int) { } 

but why do you have an additional list of parameters only for the "receiver", as it seems to me, is it called? Wouldn't it be a simpler and more elegant design to just make

 func Foo(s *SomeStruct, x int) { } 

and then s.Foo(5) just translate into a call to the function Foo(s, 5) ?

+8
go
source share
4 answers

Methods are fundamentally special and differ from ordinary functions.

  • Methods should work in the same package as the receiver type.
  • Methods are used to satisfy interfaces.
  • Receiver parameters are the only parameters that can be overloaded.
  • When fields of an anonymous structure have methods, these methods are "inherited."

With your proposal, the line between the function and the method becomes very blurry, and it is difficult to understand how to solve the above problems.

However, I think it would be very interesting to design the language using multimethods and interfaces. However, this language will not be Go.

+19
source share

Your question correctly states that any method is a function. However, the Go language must clearly distinguish between methods and functions. The reason for this is that methods have functions whose functions do not. The choice of whether Foo function or a way should be made by the programmer.

Go minimalism means that a language defines only a small set of keywords. Go authors could choose a new keyword, for example method , to distinguish methods from functions:

 method Foo(receiver *T, arg1 int) {} // 'Foo' is a method, not a function 

Looking back at the Go programming language, we see that the philosophy is to reuse existing keywords, rather than have a separate keyword for each case. A key example of this approach is the for keyword:

 for {} // Infinite loop for a>0 {a--} // A while-do loop for i := range channel {} // Receive values from a channel for i:=0; i<N; i++ {} // C-style for loop 

The main idea is that for the parser (and Go programmers) to distinguish between different types of for loops from each other, there is no need to enter a new keyword if the parameters can be distinguished by the syntax of what happens after the for:; := range identifier ..., their sequential order and their presence / absence.

The func keyword follows the same pattern. It can be used in several contexts:

  • function definitions: func f() {}
  • Function Types: type F func(int) int
  • method definitions: func (t T) SomeMethod() {}
  • closing: { ...; go func(){c<-1}(); ...} { ...; go func(){c<-1}(); ...}

From a minimalist point of view, one func keyword is simpler and more elegant than several keywords.

Optional parameter list for receiver only

 func (t *T) Foo(x int) {} 

allows the parser to distinguish between methods and functions:

 func IDENTIFIER ... This is going to be a function func ( ... This is going to be a method 

Thus, the parser (like Go programmers) can make a difference based on matching the func keyword with an identifier or ( .

+6
source share

The proposed replacement is not semantically identical to the current state, that is, not only to the syntactic change. It [will try] to automatically create methods of any type [local package], which will be the first parameter of the function. Given how the underlying method sets meet the requirements of the concept of automatically matching the Go interface, this is likely to lead to a lot of big mess.

In short, I think that such a change in the Go language does not improve anything, while it damages many of its nice features related to methods and interfaces.

+3
source share

Perhaps because go is not Python.

Also, since a function declared this way is not a method .

You cannot declare a method outside the package of an object. Therefore, I believe that the main explanation of syntax differences between methods and functions is the ability to differentiate them.

+1
source share

All Articles