恶在关键时刻绑定在Guice中

huangapple go评论94阅读模式
英文:

Just in time binding in guice

问题

Guice中的即时绑定是否会反复注入相同的实例,还是每次注入都会创建新实例?换句话说,它是默认维护单例还是每次都创建新实例?

英文:

Does just in time binding in guice injects the same instance again and again or does it create a new one on every injection. In other words does it maintain singleton by default or does it create new instances everytime ?

答案1

得分: 2

TL;DR: 默认情况下,Guice 每次都创建一个新的实例。

为了测试它,我们可以创建一个小程序。让我们定义一个接口:

public interface SomeInterface {
    int getCounter();
}

以及它的实现:

class SomeInterfaceImpl implements SomeInterface {
   private static int counter = 0;

    @Inject
    public SomeInterfaceImpl() {
       counter++;
   }

    public int getCounter() {
        return counter;
    }
}

主程序将会是:

public static void main(String[] args) {
    Injector injector = Guice.createInjector(binder -> {
        binder.bind(SomeInterface.class).to(SomeInterfaceImpl.class);
    });

    for (int i = 0; i < 3; i++) {
        SomeInterface impl = injector.getInstance(SomeInterface.class);
        System.out.println(impl.getCounter());
    }
}

这个程序的输出将会是:

0
1
2

为了使你的类成为单例,你有4个选项:

  1. 在一个单例类中定义该类:
Injector injector = Guice.createInjector(binder -> {
    binder.bind(SomeInterface.class).to(SomeInterfaceImpl.class).in(Singleton.class);
});
  1. 在一个单例范围内定义该类:
Injector injector = Guice.createInjector(binder -> {
    binder.bind(SomeInterface.class).to(SomeInterfaceImpl.class).in(Scopes.SINGLETON);
});
  1. SomeInterfaceImpl 定义为单例:
@Singleton
class SomeInterfaceImpl implements SomeInterface {
  1. 调用 asEagerSingleton
Injector injector = Guice.createInjector(binder -> {
    binder.bind(SomeInterface.class).to(SomeInterfaceImpl.class).asEagerSingleton();
});

要了解更多关于这4个选项之间的区别,你可以参考文档,或者阅读Jeff 的帖子

英文:

TL;DR: By default, Guice creates a new instance every time.

In order to test it, we can create a small program. Let's define an interface:

public interface SomeInterface {
    int getCounter();
}

And implementation:

class SomeInterfaceImpl implements SomeInterface {
   private static int counter = 0;

    @Inject
    public SomeInterfaceImpl() {
       counter++;
   }

    public int getCounter() {
        return counter;
    }
}

The main program will be:

public static void main(String[] args) {
    Injector injector = Guice.createInjector(binder -&gt; {
        binder.bind(SomeInterface.class).to(SomeInterfaceImpl.class);
    });

    for (int i = 0; i &lt; 3; i++) {
        SomeInterface impl = injector.getInstance(SomeInterface.class);
        System.out.println(impl.getCounter());
    }
}

The output of that program will be:

0
1
2

In order to have your class singleton you have 4 options:

  1. Define the class in a singleton class:

     Injector injector = Guice.createInjector(binder -&gt; {
         binder.bind(SomeInterface.class).to(SomeInterfaceImpl.class).in(Singleton.class);
     });
    
  2. Define the class in a singlton scope:

     Injector injector = Guice.createInjector(binder -&gt; {
         binder.bind(SomeInterface.class).to(SomeInterfaceImpl.class).in(Scopes.SINGLETON);
     });
    
  3. Define SomeInterfaceImpl as singleton:

    @Singleton
    class SomeInterfaceImpl implements SomeInterface {
    
  4. Call asEagerSingleton:

     Injector injector = Guice.createInjector(binder -&gt; {
         binder.bind(SomeInterface.class).to(SomeInterfaceImpl.class).asEagerSingleton();
     });
    

To understand more about the differences between the 4 options, you can refer to the docs, or read Jeff's post about that.

huangapple
  • 本文由 发表于 2020年10月13日 21:23:04
  • 转载请务必保留本文链接:https://go.coder-hub.com/64336016.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定