相关疑难解决方法(0)

自定义Guice范围,还是更好的方法?

这是我的问题:

首先要知道我正在编写模拟.这是一个独立的应用程序,是单线程的.我基本上有两类具有不同范围要求的对象.

  1. 在整个模拟过程中应该用作单例的类.以Random为例,作为一个例子.

  2. 一起创建的类组以及组内的每个实例都应该被视为Singleton.例如,假设RootObject是顶级类,并且具有依赖性,ClassA并且ClassB两者都具有依赖性ClassD.对于任何给定的RootObject,它的两个依赖(ClassAClassB)应该依赖于相同的实例ClassD.但是,ClassD不应在不同的实例之间共享实例RootObject.

希望这是有道理的.我可以想到两种方法.一种是将所有注入的对象标记为单例,创建根注入器,并在每次需要创建新RootObject实例时分离子注入器.然后,将其实例RootObject和所有依赖项创建为单例,但下次我创建另一个时,该范围信息将被丢弃RootObject.

第二种方法是实现某种类型的自定义范围.

Guice文档给出了相互矛盾的建议......一方面,它说你应该有一个注入器,理想情况下它被调用一次来创建一些顶级类.另一方面,它表示要远离自定义范围.

scope design-patterns guice

22
推荐指数
3
解决办法
5852
查看次数

Guice渴望/懒惰的单身实例化

我有一些麻烦,了解Guice的单例实例化是如何工作的.我已经阅读了可用的文档(此处为http://code.google.com/p/google-guice/wiki/Scopes),但我仍然无法弄清楚一些事情:

1)我已经将Guice与Tomcat集成在一起,我在ServletModule中设置了一些绑定:

bind(MyServlet.class).asEagerSingleton();
serve("myUrl").with(MyServlet.class);
serve("myOtherUrl").with(MyOtherServlet.class);
Run Code Online (Sandbox Code Playgroud)

(其中MyOtherServlet类上面有一个@Singleton注释)我的意图是有两个servlet,其中一个是急切实例化的,而另一个则不是.然而,似乎"serve ... with ..."行自动实例化servlet对象,即使该类未被绑定为急切的单例.我上面提到的链接提到了在Stage.Development和Stage.Production下运行的Guice之间的区别 - 但是即使我明确地使用了Stage.Development(无论如何都是默认的),这仍然会发生.有什么方法可以避免这种情况吗?

2)(继续1)尝试确保MyServlet首先被实例化,即使所有servlet现在急切地实例化,我在创建Injector时修改了模块(和绑定语句)的顺序,以便首先显示MyServlet的绑定.但是,我发现它仍然比其他一些绑定(非servlet类)实例化,其形式如下:

bind(MyInterface.class).to(MyClass.class).asEagerSingleton()
Run Code Online (Sandbox Code Playgroud)

即使这些其他绑定稍后出现在modules/bindings顺序中.我调查了一下,发现Guice只是实例化了那些受"bind ... to ... asEagerSingleton()"形式约束的热切单体,然后再进行"bind ... asEagerSingleton()",所以我通过修改行来解决它:bind(MyServlet.class).asEagerSingleton(); into:bind(MyServletDummyInterface.class).to(MyServlet.class).asEagerSingleton()

这实际上有效.不过,我宁愿避免使用虚拟接口来解决这个问题,所以我想知道是否有人有更好的解决方案..?

3)我有两个Guice模块 - 一个ServletModule和一个AbstractModule.ServletModule configureServlets()中包含以下绑定:

serve("aUrl").with(SomeServlet.class);
Run Code Online (Sandbox Code Playgroud)

AbstractModule的configure()具有以下绑定:

bind(SomeImpl.class).asEagerSingleton();
bind(SomeInterface.class).to(SomeImpl.class).in(Singleton.class);
Run Code Online (Sandbox Code Playgroud)

此外,SomeServlet类具有SomeInterface类型的注入字段,并且在类的顶部具有@Singleton注释.

现在,可以预期在创建注入器时,SomeImpl类将被实例化,并且相同的实例将被注入SomeServlet实例.如前所述,带有"serve ... with ..."语句的servlet似乎也得到了热切的实例化,但无论哪种方式,都应该只有一个SomeImpl对象被实例化.但由于某种原因,我在执行此操作时实例化了两个SomeImpl对象.为了解决这个问题,我在configure()中混合了两行,而不是上面的代码,我有以下几行:

bind(SomeImpl.class).in(Singleton.class)
bind(SomeInterface.class).to(SomeImpl.class).asEagerSingleton();
Run Code Online (Sandbox Code Playgroud)

然后它工作正常,我只有一个实例化SomeImpl的实例.我真的不明白为什么开关应该重要 - 我可以看到后一种方式是如何"更好",但我希望两者都能正常工作,所以我只是想知道我是否在这里弄错了.. ?



抱歉长度,
谢谢你的帮助!

java singleton eager guice

10
推荐指数
1
解决办法
3万
查看次数

标签 统计

guice ×2

design-patterns ×1

eager ×1

java ×1

scope ×1

singleton ×1