Dagger2中的静态提供方法

5

为什么要在提供方法之前加上static修饰符?

即使我删除static修饰符,dagger2仍然可以正常工作。

@Provides static Pump providePump(Thermosiphon pump) {
    return pump;
}

1
我不知道。我认为在这种情况下文档是在撒谎。你怎么覆盖模拟的静态提供者方法呢?你不能这样做。因此,添加“static”是非常愚蠢的,而且文档对此也毫无意义。虽然它以其“咖啡示例”而闻名,但实际上并没有告诉你如何使用该库,所以它做其他一些毫无意义的事情也就不足为奇了。/抱怨 - EpicPandaForce
使用静态函数作为 @Provides 可以减少部分生成的代码。 - Osama Aftab
1个回答

11
两种风格都可以;你是否保持方法静态完全取决于你和在普通的Java中正常的“这应该是一个静态方法”的判断。在这里,pump没有任何用于模块实例的用途,因此该方法可以很容易地是静态的。
静态方法调用更快,特别是在Android上,因为它们避免了虚方法表查找。这也可能使编译器、JIT运行时或静态分析工具更容易内联。我认为,通过将类或方法设为final,您也可以获得类似的优势。
给定静态方法不能受到实例字段的影响,可读性也可能略有提高,但这取决于您。
如果您确信您的@Provides方法的行为不会发生变化,包括在测试中,那么您可以利用性能/可读性的提高。然而,如果您需要引用模块状态或想要允许子类/测试覆盖,则实例方法必然是正确的选择。

谢谢您提供何时以及为什么使用该想法的建议。非常清晰明了。我会将其标记为答案。 - Sandy Lin
嗯,在Dagger文档中,他们使用静态方法进行测试。请参见https://google.github.io/dagger//testing.html底部的`@Provides static AuthManager authManager`,这是他们的错误还是我漏掉了什么? - arekolek
@arekolek 没有错误;该模块是FakeAuthModule,用于测试但从未更改或覆盖,因为它是一个仅供测试的模块,根据“选项2:分离组件配置”而设定。非最终方法用于测试,特别是为了启用“选项1:通过子类化模块覆盖绑定(不要这样做!)”,其标题警告基于该页面列出的限制。我不反对:除非非常快速或受限制的覆盖(或设计用于覆盖的模块),否则您可能需要为测试使用单独的组件,并使用单独的模块(以及抽象或静态的@Provides方法)。 - Jeff Bowman
谢谢,我现在明白了。他们子类化组件并包含不同的模块,但他们不会子类化模块本身。 - arekolek

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接