Dagger2

Dagger2_第1张图片
Dagger2类图.png

什么是依赖注入 依赖注入的好处

http://blog.csdn.net/hsk256/article/details/51530667
http://blog.csdn.net/u010961631/article/details/72626134
http://blog.csdn.net/android_study_ok/article/details/52440464

dependencies方式让Component之间更加独立,结构更加清晰,也更利于解耦。
dependencies中Component强调的是在子类Component依赖于某个Component(子类为主角),而Subcomponent中强调的则是在父类Component中提供某个子类的Component(父类为主角)。
Lazy延时加载就是,需要调用两遍才能得到最终的结果,和懒汉模式不一样。

  1. 作用域scope需要自定义
  2. 限定符@Named("app") 根据Class作为key,存在class重复时用@Name标示
  3. 依赖入参怎么办?注入的实例、被注入的引用。实例化对象所需参数分两类:手动传入的、moudle提供的。
  4. component之间的关系分为:继承和依赖,对作用域、对module的作用域的影响

外界有两种使用方式,方法注入(mBindPoiComponent.inject(this);)、Provider注入( mBindPoiComponent.sp();)
private Provider provideContextProvider;
private MembersInjector bindPoiModuleMembersInjector;
都需要在BindPoiComponent中显示声明。

答疑

  • 同Component中Module内部可以共享么?
    可以

  • 同Component中不同Module之间可以共享么?
    可以

  • 依赖关系中当前和依赖跨Componet不同Module之间可以共享么?
    可以,共享条件是,必须在依赖的Componet中显式的声明哪些能被其他Component使用。

  • 依赖关系作用域能共享么
    不能!

  • 继承关系中子类和父类跨Component不同Module之间可以共享么?
    可以,但是要把module传递给父Component中

  • 继承关系中作用域可共享么
    可以

  • Module构造函数带入参的都需要手动初始化了
    是的,并且如果Module内包含需要注入的属性,需要自行解决调用inject。

  • 寻找目标依赖的实例的过程是,先Module再被Inject标注的构造函数
    被Inject标注的构造函数,如果还用到了注入,Dagger会自动帮你注入,这点和Module有很大的不同。Inject方式,很容易在构造函数中手动调用inject(),其实是不需要的。

跨Component依赖关系,Module之间的依赖,需要依赖中对外声明后才能使用。

Module的构造函数存在入参时,如果入参实例能在Dagger依赖中找到,则由系统自动创建,找不到,则由用户初始化,否则抛出IllegalStateException异常。
public BindPoiComponent build() {
      if (bindPoiModule == null) {
        throw new IllegalStateException(BindPoiModule.class.getCanonicalName() + " must be set");
      }
      if (activiyModule == null) {
        this.activiyModule = new ActiviyModule();
      }


单例的实现方式,被DoubleCheck 代理保证只生产一次。生产后对被代理引用置空
this.providePresenterProvider =DoubleCheck.provider(BindPoiModule_ProvidePresenterFactory.create(builder.bindPoiModule));

/* Null out the reference to the provider. We are never going to need it again, so we
           * can make it eligible for GC. */
          provider = null;


Module必须手动inject,否则会发现调用mContext时发生空指针
@Module
public class BindPoiModule {
    private BindPoiContact.View mView;

    @Inject
    @Named("app")
    Context mContext;

    //TODO 如何用AppContext
    public BindPoiModule(BindPoiContact.View mView) {
        this.mView = mView;
    }


多个Component之间,使用依赖Component中的provider时,必须显性声明
    this.contextProvider =
        new Factory() {
          private final ApplicationComponent applicationComponent = builder.applicationComponent;

          @Override
          public Context get() {
            return Preconditions.checkNotNull(
                applicationComponent.context(),
                "Cannot return null from a non-@Nullable component method");
          }
        };

Dagger2_第2张图片
屏幕快照 2017-12-23 下午5.02.40.png

你可能感兴趣的:(Dagger2)