英文:
Can I reference an imported type without using dot notation
问题
考虑以下接口定义:
package repos
import (
resources "unit/pkg/resources"
)
type IRepo interface {
fetch(int32) (resources.IResource, error)
update(resources.IResource) (resources.IResource, error)
new() resources.IResource
create(resources.IResource) (resources.IResource, error)
delete(int32) error
}
有没有一种方法可以“使用”导入的包(类似于C++的命名空间),这样我在引用其类型(IResource
)时就不需要使用点符号显式命名它了?
(说实话,这可能意味着IResource
应该属于repos
包而不是resources
包)
英文:
Consider the following interface definition:
package repos
import (
resources "unit/pkg/resources"
)
type IRepo interface {
fetch(int32) (resources.IResource, error)
update(resources.IResource) (resources.IResource, error)
new() resources.IResource
create(resources.IResource) (resources.IResource, error)
delete(int32) error
}
Is there a way to 'use' the imported package (in the sense of C++ namespaces), so that I don't need to explicitly name it using dot notation each time I reference one of its types (IResource
)
(TBH - this may just mean that IResource
belongs in the repos
package and not in resources
)
答案1
得分: 3
你可以在import
声明前加上名称.
来导入其所有标识符:
package repos
import (
. "unit/pkg/resources"
)
然而,import .
几乎从不是合适的解决方案。如果将来在resources
包中添加了新的标识符,它们可能会与repos
包中的现有标识符冲突,并导致构建失败。
此外,包名与类型名重复的事实可能表明,无论是包还是该包中的类型,都应该有一个更好的名称(请参阅Package names博文以获取更多详细信息)。
在这种情况下,也许resources
和repos
之间的抽象边界对你造成的伤害大于好处。你处理的是什么类型的资源?Resource
类型是否可以移动到某个更高级别的包中?
最后,我想指出IRepo
接口似乎非常庞大,可能不合适。与Java接口不同,Go接口通常属于_使用_该接口的API,而不是_提供_该接口实现的API。
有关该原则的更多信息,请参阅:
- https://golang.org/wiki/CodeReviewComments#interfaces
- https://hyeomans.com/golang-and-interfaces-misuse/
- https://dave.cheney.net/2016/08/20/solid-go-design
- https://dave.cheney.net/practical-go/presentations/gophercon-israel.html#_prefer_single_method_interfaces
英文:
You can prefix the import
declaration with the name .
to import all of its identifiers:
package repos
import (
. "unit/pkg/resources"
)
However, import .
is almost never the appropriate solution. If new identifiers are added to the resources
package in the future, they can collide with existing identifiers in the repos
package and break your build.
Furthermore, the fact that the package name is redundant with the type name may indicate that either the package or the types within that package should have a better name (see the Package names blog post for much more detail).
In this case, perhaps the abstraction boundary between resources
and repos
is doing more harm than good. What kind of resources are you dealing with here? Could the Resource
type be moved into some higher-level package?
Finally, I would note that the IRepo
interface seems very large and likely out-of-place. Go interfaces — unlike, say, Java interfaces — generally belong with the API that consumes the interface, not the API that provides implementations of that interface.
For more on that principle, see:
答案2
得分: 2
你可以使用类型别名。
type IRes = resources.IResource
与类型定义不同,类型别名只是同一类型的另一个名称,而不是一个新的不同类型。类型定义不会使用 =
。
英文:
You can use a type alias.
type IRes = resources.IResource
In contrast to a type definition, an alias is just another name for the same type and not a new distinct type. A type definition would be without the =
.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论