Resolving import cycles

polaris · · 413 次点击    
这是一个分享于 的资源,其中的信息可能已经有所发展或是发生改变。
<p>A simplified version of the code:</p> <pre><code>// package character type Character struct {Inventory: []item.Ttem} // package item type Item struct {Name: string, Actions: action.Action} // package action type Action struct { Names: []string, Action: func(*character.Character) int </code></pre> <p>This causes an import cycle of <code>character -&gt; item -&gt; action -&gt; character</code> how would you resolve this?</p> <p>Moving everything into an interface wouldn&#39;t work unless they were still in the same package and would require a number of get/set functions.</p> <hr/>**评论:**<br/><br/>itsmontoya: <pre><p>Why can&#39;t they all be part of the same package?</p></pre>ROFLLOLSTER: <pre><p>They can be, it just moves a lot of mostly unrelated code together which I was trying to avoid. Definitely works though.</p></pre>shovelpost: <pre><p>They are not really unrelated. If your project was named <code>foo</code>then it makes total sense to see in the code <code>foo.Character</code> and <code>foo.Action</code>. The package name becomes very descriptive. On the other hand <code>character.Character</code> what does that even mean? We have to go up and look at the import to see that <code>character</code> belongs to project <code>foo</code>, not to mention the stuttering.</p> <p>Check out the article <a href="https://medium.com/@benbjohnson/standard-package-layout-7cdbc8391fc1" rel="nofollow">Standard Package Layout</a>.</p></pre>ROFLLOLSTER: <pre><p>Thanks, I think that is the approach I&#39;ll take.</p> <p>Edit: It ends up being a lot of code in one package because most of the application in this case is methods on those types rather than things that have external dependencies. I guess that&#39;s not too bad.</p></pre>Rudd-X: <pre><p>Put them in the same package but different files, brother.</p></pre>shovelpost: <pre><p>In my opinion these methods belong in the same package unless they call database code or something.</p></pre>TheMerovius: <pre><p>The fact that they import each other contradicts the claim, that the code is unrelated. It&#39;s related, it belongs in the same package.</p></pre>JHunz: <pre><pre><code>// package action type ActionTarget interface { // Necessary interaction methods } type Action struct { Names: []string, Action: func(*ActionTarget) int } // package character type Character struct {Inventory: []item.Item} // implementation of action.ActionTarget for Character // package item type Item struct { Name: string, Actions: []action.Action } </code></pre> <p>This has the added advantage of being able to implement actions that affect other items or even other actions, rather than being limited to affecting characters.</p></pre>ROFLLOLSTER: <pre><p>That&#39;s a really good idea. Thanks.</p></pre>blueblank: <pre><p>A package local interface in item that corresponds to the behavior of action.Action.</p></pre>

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

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