在Kotlin,我们val
是最终的,不能改变。 e.g。
val something = "Something"
如果稍后初始化了某个值,我们会使用lateinit var
。
lateinit var something: String
但这是var
而不是val
。我想设置一次(不是在构造函数中),并将其作为final。我怎么能做到这一点?
答案 0 :(得分:3)
阅读Kotlin的惯例,一个最终的初始化变量是不可能的。
考虑its use case:
通常,声明为具有非null类型的属性必须在构造函数中初始化。但是,这通常不方便。例如,可以通过依赖注入或单元测试的设置方法初始化属性。在这种情况下,您不能在构造函数中提供非null初始值设定项,但是在引用类体内的属性时仍然希望避免空值检查。
lateinit var
在处理可能尚未初始化的变量时提供了相对的健全性,例如注入字段的情况(如Spring和@Autowired
)。然后,严格地说在依赖注入的上下文中,如果不有一种方法在编译时具体实例化变量,那么你不能把它留作最终字段。
从Java到Kotlin世界,有一个迟到的初始化变量作为最终版本看起来像Spring中的矛盾:
@Autowired
private final Interface something;
答案 1 :(得分:1)
当您尝试再次设置时,您认为该行为应该是什么?您是否希望在编译时强制执行此操作?它应该在运行时导致崩溃还是什么都不做?
如果您希望它在编译时发生,我很确定编译器无法捕获这样的内容。
如果您想要其他一些行为,可以使用公共集方法将其设为私有变量,如果已经设置了该方法,则可以执行任何操作。
或者您可以将其封装在自定义类的实例中,该类可以执行您想要的任何行为。
答案 2 :(得分:0)
您可以使用您可以为属性创建自定义委托,该属性是现有notNull
委托和您自己set once
的想法的组合。阅读有关property delegates的更多信息,了解有关如何创建可以执行任何操作的自定义操作的信息,包括您在此处所需的用例。然后,您将不使用lateinit
,而是使用此委托。