服务定位器不仅仅是全局变量/状态吗?
为了解耦代码,您可以使用服务定位器,但这与全局变量/状态不一样吗?
我知道这些通常会脱离接口,因此您传入一个接口并返回一个具体的类,但我的问题仍然存在。
例如:
class Something {
void DoSomething() {
IMyType myType = ServiceLocator.GetSerivceTypeOf(IMyType);
}
}
这里的类需要在其他地方创建的 MyType,但不是通过链向下传递 MyType(通过构造函数等...),而是以这种方式获取。
我在作为开发人员的职业生涯早期就提出了这个问题 - 在此之前我没有遇到过这种模式。 安东尼已经明确了我对服务定位器的看法(因此现在是选定的答案) - 事实上,我将它们视为像其他人一样的反模式。 提供的链接是一个很好的起点 - 但为了在某种程度上回答我自己的问题,它们充当全局状态,应该避免。 更喜欢标准依赖注入;)
In order to decouple code you can have service locater's but is this not the same as global variables/state?.
I know these often run off interfaces, so you pass in an interface and get a concrete class back but still my question stands.
For example:
class Something {
void DoSomething() {
IMyType myType = ServiceLocator.GetSerivceTypeOf(IMyType);
}
}
Here the class requires MyType which is created somewhere else, but rather than passing MyType down through the chains (via constructors etc...) it is acquired in this manner.
I asked this question early in my professional career as a developer - prior to then I'd not come across this pattern. Anthony has nailed my opinion (and therefore is the selected answer now) on service locator's - in fact I see them as anti-patterns like others. The links provided are a good starting point - but to somewhat answer my own question after all this time, they act as global state and should be avoided. Prefer standard dependency injection ;)
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
是的,它们是全局变量。 虽然很复杂,但它们仍然具有相同的基本缺点。 因此,依赖注入更可取。
有关构造函数注入替代方案的更详细讨论,另请参阅问题 依赖注入和服务定位器模式有什么区别?
和其他网页 单身人士是病态的骗子 和 依赖注入模式
Yes they are global variables. Sophisticated ones, but they still have the same basic drawbacks. For that reason, dependency injection is preferable.
For more detailed discussion of the alternative of constructor injection, see also the question What’s the difference between the Dependency Injection and Service Locator patterns?
And other web pages Singletons are Pathological Liars and Dependency Injection pattern
通常支持服务定位器模式的名称服务确实使用全局名称空间。
然而,我们必须考虑“全局变量”被认为不好的原因。 其中许多都围绕着修改程序中任何位置的全局变量的能力。 然而,大多数命名服务可以限制对绑定对象的修改。 对象本身可能是不可变的。
服务定位器不仅仅是一个全局变量,它是一个专门化的变量。 这种专业化往往可以缓解全局变量可能引起的许多问题。
The name service that typically backs up the service locator pattern does indeed use a name space that is global.
However, one has to consider the reasons "global variables" are considered bad. Many of these revolve around the ability to modify a global variable anywhere in the program. However, most naming services can restrict modifications to a bound object. The object itself may be immutable.
Service locator is not simply a global variable, it is a specialization. And that specialization tends to mitigate many of the problems that can arise from global variables.
在某些时候,您需要一个具体的实现来完成一些工作。 该服务是“全局”的,因为它对您的应用程序“可用”。 但您不必将其设为代码中的全局变量。
你可以颠倒论证。 如果您需要访问应用程序中的服务,您将使用什么模式来访问它,而不将其绑定到具体的实现。 没有太多选择。
有些资源对于您的应用程序来说本质上是“全局”的,例如操作系统、文件系统、窗口系统……
这种讨论更多的是哲学性的,而不是解决问题的。 无论如何,希望它有所帮助。
At some point you need a concrete implementation to do some work. The service is "global" in a sense that it is "available" to your application. But you do not have to make it a global variable in your code.
You can reverse the argument. If you need to access a service in your application, what pattern would you use to access it, and without binding it to a concrete implementation. There are not many alternatives.
Some resources are intrinsically "global" to your application, take the operating system, the file system, the windowing system, ...
The discussion is more philosophical one than a problem solving one. Anyway, hope it helps.