I don't understand the benefit of Go methods

blov · · 588 次点击    
这是一个分享于 的资源,其中的信息可能已经有所发展或是发生改变。
<p>I cannot see or understand the benefits of functions with receivers (methods) over simple parameters.</p> <p>When I see something like this:</p> <pre><code>package main import &#34;fmt&#34; type User struct { Firstname, Lastname string } func (u User) Greeting() string { return fmt.Sprintf(&#34;Dear %s %s&#34;, u.Firstname, u.Lastname) } func main() { u := User{&#34;Foo&#34;, &#34;Bar&#34;} fmt.Println(u.Greeting()) } </code></pre> <p>I immediately want to do this instead:</p> <pre><code>package main import &#34;fmt&#34; type User struct { Firstname, Lastname string } func Greeting(u User) string { return fmt.Sprintf(&#34;Dear %s %s&#34;, u.Firstname, u.Lastname) } func main() { u := User{&#34;Foo&#34;, &#34;Bar&#34;} fmt.Println(Greeting(u)) } </code></pre> <p>And the result is exactly the same.</p> <p>What is the point of receivers in Go?</p> <hr/>**评论:**<br/><br/>element131: <pre><p>The main reason they are useful is that it is only through receivers that a type can implement an interface. It also allows you to have two functions with the same name that operate on different types.</p></pre>joncalhoun: <pre><p>Another benefit is being able to pass a method around as if it were a function and having the user object available still. You can also achieve this with closures, so methods aren&#39;t necessary here, but I prefer to use them. </p> <p>Eg <code>user.Greeting</code> in the provided example matches <code>func() string</code> whereas the original doesn&#39;t, so we could pass it to a function like <code>func a(fn func() string) { ... }</code></p> <p>On mobile so sorry the example kinda sucks.</p></pre>gohacker: <pre><p>Still another is to be able to pass a variable to a template and invoke its methods for free, without the need of passing a FuncMap when creating the template.</p> <p><a href="https://play.golang.org/p/lPnc_f_HtF">https://play.golang.org/p/lPnc_f_HtF</a></p></pre>tomcam: <pre><p>Excellent question, absolutely correct answer. Thanks, all!</p></pre>cbarrick: <pre><p>As mentioned, methods enable <em>interface</em> types that allow you to reason about behaviour independent of implementation.</p> <p>More formally, this pattern is called <a href="https://en.m.wikipedia.org/wiki/Polymorphism_(computer_science">polymorphism</a>) and is a key tenant of object oriented programming and software engineering.</p></pre>HelperBot_: <pre><p>Non-Mobile link: <a href="https://en.wikipedia.org/wiki/Polymorphism_(computer_science" rel="nofollow">https://en.wikipedia.org/wiki/Polymorphism_(computer_science</a></p> <hr/> <p><sup>HelperBot</sup> <sup>v1.1</sup> <sup><a href="/r/HelperBot_" rel="nofollow">/r/HelperBot_</a></sup> <sup>I</sup> <sup>am</sup> <sup>a</sup> <sup>bot.</sup> <sup>Please</sup> <sup>message</sup> <sup><a href="/u/swim1929" rel="nofollow">/u/swim1929</a></sup> <sup>with</sup> <sup>any</sup> <sup>feedback</sup> <sup>and/or</sup> <sup>hate.</sup> <sup>Counter:</sup> <sup>26681</sup></p></pre>joncalhoun: <pre><p>Traditional OOP isn&#39;t really a great design pattern in Go, so I&#39;m not entirely sure I would use this as a justification for methods.</p></pre>cbarrick: <pre><p>Go is not &#34;classical&#34; OO since there are no classes, but I would argue that it is still OO. Polymorphism, encapsulation, and composition are well supported in the traditional definitions and Go&#39;s &#34;type embedding&#34; can be seen as an evolution of classical inheritance.</p> <p>Go is not Java or C++, but it&#39;s still OO IMO.</p></pre>nosmileface: <pre><p>Another not widely used thing about methods. It&#39;s the only way to get a list of functions in Go via reflection. You can&#39;t get a list of functions in a package, but you can get a list of methods of a type.</p></pre>callcifer: <pre><p>True, but that&#39;s more of a downside of the current reflection support than an upside of methods in general.</p></pre>VerilyAMonkey: <pre><p>As others have noted, there are actual functional differences, for example</p> <ol> <li>Implement interfaces</li> <li>Allow you to pass around partially-applied methods that know which struct they came from</li> <li>List the methods through reflection</li> <li>Gain access to the methods when you embed the type</li> </ol> <p>However, there&#39;s another point to be made. What you&#39;re saying here is actually equally true in virtually every object oriented language. Java and C++, methods are like a Go method with a pointer receiver named &#34;this&#34;. Python, methods take in &#34;self&#34; as a first, automatically populated parameter, also essentially a pointer receiver. So there is also an answer which is... Whatever reason there is to have methods in other languages.</p></pre>yamiodymel: <pre><p>Sometimes you can just do:</p> <pre><code>u := User{&#34;Foo&#34;, &#34;Bar&#34;} p := Post{&#34;Hello&#34;, &#34;World&#34;} u.Create() p.Create() </code></pre> <p>instead of</p> <pre><code>u := User{&#34;Foo&#34;, &#34;Bar&#34;} p := Post{&#34;Hello&#34;, &#34;World&#34;} CreateUser(u) CreatePost(p) </code></pre></pre>

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

588 次点击  
加入收藏 微博
暂无回复
添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传