Guice学习------ 工厂模式和依赖注入的好处
Posted 儒雅随和狗粉丝
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Guice学习------ 工厂模式和依赖注入的好处相关的知识,希望对你有一定的参考价值。
1.工厂模式介绍
2.使用工厂模式的好处
https://www.cnblogs.com/vigorz/p/10501955.html
3.使用依赖注入的好处
https://github.com/google/guice/wiki/GettingStarted
官方介绍使用依赖注入的好处主要在于,如果使用工厂模式,全局使用静态变量在内存保存一个对象:
public class CreditCardProcessorFactory {
// 工厂模式 整个项目过程中使用 instance保存该类在内存中的唯一对象,
//使用前需要初始化,即通过 setInstance方法创建
//使用完需要用setInstance(null)销毁
private static CreditCardProcessor instance;
public static void setInstance(CreditCardProcessor processor) {
instance = processor;
}
public static CreditCardProcessor getInstance() {
if (instance == null) {
return new SquareCreditCardProcessor();
}
return instance;
}
}
public class RealBillingServiceTest extends TestCase {
private final PizzaOrder order = new PizzaOrder(100);
private final CreditCard creditCard = new CreditCard("1234", 11, 2010);
private final InMemoryTransactionLog transactionLog = new InMemoryTransactionLog();
private final FakeCreditCardProcessor processor = new FakeCreditCardProcessor();
@Override public void setUp() {
TransactionLogFactory.setInstance(transactionLog);
CreditCardProcessorFactory.setInstance(processor);
}
@Override public void tearDown() {
TransactionLogFactory.setInstance(null);
CreditCardProcessorFactory.setInstance(null);
}
public void testSuccessfulCharge() {
RealBillingService billingService = new RealBillingService();
Receipt receipt = billingService.chargeOrder(order, creditCard);
assertTrue(receipt.hasSuccessfulCharge());
assertEquals(100, receipt.getAmountOfCharge());
assertEquals(creditCard, processor.getCardOfOnlyCharge());
assertEquals(100, processor.getAmountOfOnlyCharge());
assertTrue(transactionLog.wasSuccessLogged());
}
}
这段代码逻辑是:
1.初始时使用创建对象:
private final InMemoryTransactionLog transactionLog = new InMemoryTransactionLog();
private final FakeCreditCardProcessor processor = new FakeCreditCardProcessor();
2. 传给工厂类的静态变量,使得该类全局保存一个唯一的对象,使用该类都用该对象
@Override public void setUp() {
TransactionLogFactory.setInstance(transactionLog);
CreditCardProcessorFactory.setInstance(processor);
}
3.使用该对象时直接从工厂类里获取,因为前面经过初始化,所以get可以直接得到原来初始化时new的对象,而不会重复创建,造成内存浪费,内存里没有该对象时,就会返回Null.
public static CreditCardProcessor getInstance() {
if (instance == null) {
return new SquareCreditCardProcessor();
}
return instance;
}
4.使用完后销毁工厂类那个静态变量维护的对象
@Override public void tearDown() {
TransactionLogFactory.setInstance(null);
CreditCardProcessorFactory.setInstance(null);
}
存在问题:
这段代码很笨拙。一个全局变量保存模拟实现,所以我们需要小心设置和拆除它。如果tearDown
失败,全局变量将继续指向我们的测试实例。这可能会导致其他测试出现问题。它还阻止我们并行运行多个测试。
但最大的问题是依赖关系隐藏在代码中。如果我们添加一个依赖CreditCardFraudTracker
,我们必须重新运行测试以找出哪些会中断。如果我们忘记为生产服务初始化工厂,我们在尝试收费之前不会发现。随着应用程序的增长,保姆工厂对生产力的消耗越来越大。
总结就是:
1.忘记初始化,导致每次都new新对象
2.用完忘记销毁,对其它方法造成影响
这时候使用依赖注入,把对象的创建销毁全交给Guice去做,自己无序关心对象的创建问题,注意,这里所讨论的问题是,全局维护一个共享变量时会出现的问题,如果每次都重新new,自然有GC来回收,无序担心内存溢出问题。
以上是关于Guice学习------ 工厂模式和依赖注入的好处的主要内容,如果未能解决你的问题,请参考以下文章