- Java 双重比较
- java - 比较器与 Apache BeanComparator
- Objective-C 完成 block 导致额外的方法调用?
- database - RESTful URI 是否应该公开数据库主键?
初始化 val
时类型 Sensor
通过 lazy
编译器忽略返回值可以是 null
注意:val
声明为 Sensor
而不是 Sensor?
private val sensorManager by lazy { getSystemService(Context.SENSOR_SERVICE) as SensorManager }
private val proximitySensor: Sensor by lazy { sensorManager.getDefaultSensor(Sensor.TYPE_PROXIMITY) }
sensorManager.getDefaultSensor(Sensor.TYPE_PROXIMITY)
也可以返回null
并且该方法未使用 @Nullable
注释因此,它不能在编译时检查。
此外,Android Studio 在检查 null 时给出了一个警告,因为我们没有将其声明为 Sensor?
在分配 nullable
时它不应该引发编译时错误到 val
这是non-null
?
当值为proximitySensor
被访问,如果它为 null,它会按预期产生一个运行时异常。 'java.lang.String android.hardware.Sensor.getName()' on a null object reference
lazy()
在 Kotlin 标准库引用中如下:
lazy()
返回 Lazy<T>
存储 lambda 初始值设定项的实例。lazy()
的 lambda和存储其结果。Shouldn't an exception be thrown when the assignment is made and not when we try to access it?
operator fun setValue(
thisRef: Any?,
property: KProperty<*>, value: String
) {
// assign
// An exception should be generated at this point when the assignment happens
}
最佳答案
Shouldn't it raise a compile time error when assigning a nullable to a val which is non-null?
是的,但这不是这里发生的事情 在这种情况下,您要分配一个 platform type为您的值(value)并告诉编译器将其视为不可为空。应该有 IllegalStateException
的运行时错误- 正如@MarkoTopolnik 指出的那样,这是一个错误。
KT-8135 涵盖了此错误.这是与代表直接相关的链接问题,KT-24258 .还有一个包含一些可运行示例的讨论主题 here .
当你使用proximitySensor
时会触发错误以需要非空值的方式,例如:
val s: Sensor = proximitySensor
proximitySensor.someMethod()
println(proximitySensor.someProperty)
但是这样在属性初始化的时候不会抛出异常!我们可以解决这个问题...
自 sensorManager.getDefaultSensor(Sensor.TYPE_PROXIMITY)
在java中实现它返回一个platform type .因此,惰性委托(delegate)的类型是 Lazy<Sensor!>
.
Lazy 类运行初始化程序 lambda。保存 lambda 的结果,然后以 T
类型返回,即 Sensor!
.
如果我们在调用 lazy
时显式声明类型参数功能:
private val proximitySensor: Sensor by lazy<Sensor> { sensorManager.getDefaultSensor(Sensor.TYPE_PROXIMITY) }
那么一旦访问惰性值就会抛出异常。
警告会引导您朝着正确的方向前进,要么不检查是否为空,要么将其声明为可为空。通过将类型显式声明为可为空来告诉编译器该值应被视为可为空:
private val proximitySensor: Sensor? by lazy { sensorManager.getDefaultSensor(Sensor.TYPE_PROXIMITY) }
如您所述,sensorManager.getDefaultSensor(Sensor.TYPE_PROXIMITY)
可能返回 null。我们可以返回一个默认值:
val proximitySensor: Sensor by lazy {
sensorManager.getDefaultSensor(Sensor.TYPE_PROXIMITY) ?: SOME_DEFAULT_VALUE
}
Kotlin 中的平台类型允许您(调用者)决定类型是可为 null 还是不可为 null 的,从而使使用 Java 更加实用。假设 Java 中的所有内容都可以为 null 的替代方案意味着您将不得不进行大量痛苦的 null 检查,即使 Java 代码从不返回 null。
*注意:如果您正在编写 Java 代码,则可以使用 @Nullable
和 @NonNull
为 Kotlin 编译器和其他静态分析工具提供元数据的注解。 Spring Framework 等库 have done this to their APIs .
这是 a talk由 Kotlin 开发人员 Andrey Breslav 撰写,深入探讨了平台类型互操作性的设计决策。
关于android - 访问 Android 传感器的惰性不可空属性时的空属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50173899/
你能比较一下属性吗 我想禁用文本框“txtName”。有两种方式 使用javascript,txtName.disabled = true 使用 ASP.NET, 哪种方法更好,为什么? 最佳答案 我
Count 属性 返回一个集合或 Dictionary 对象包含的项目数。只读。 object.Count object 可以是“应用于”列表中列出的任何集合或对
CompareMode 属性 设置并返回在 Dictionary 对象中比较字符串关键字的比较模式。 object.CompareMode[ = compare] 参数
Column 属性 只读属性,返回 TextStream 文件中当前字符位置的列号。 object.Column object 通常是 TextStream 对象的名称。
AvailableSpace 属性 返回指定的驱动器或网络共享对于用户的可用空间大小。 object.AvailableSpace object 应为 Drive 
Attributes 属性 设置或返回文件或文件夹的属性。可读写或只读(与属性有关)。 object.Attributes [= newattributes] 参数 object
AtEndOfStream 属性 如果文件指针位于 TextStream 文件末,则返回 True;否则如果不为只读则返回 False。 object.A
AtEndOfLine 属性 TextStream 文件中,如果文件指针指向行末标记,就返回 True;否则如果不是只读则返回 False。 object.AtEn
RootFolder 属性 返回一个 Folder 对象,表示指定驱动器的根文件夹。只读。 object.RootFolder object 应为 Dr
Path 属性 返回指定文件、文件夹或驱动器的路径。 object.Path object 应为 File、Folder 或 Drive 对象的名称。 说明 对于驱动器,路径不包含根目录。
ParentFolder 属性 返回指定文件或文件夹的父文件夹。只读。 object.ParentFolder object 应为 File 或 Folder 对象的名称。 说明 以下代码
Name 属性 设置或返回指定的文件或文件夹的名称。可读写。 object.Name [= newname] 参数 object 必选项。应为 File 或&
Line 属性 只读属性,返回 TextStream 文件中的当前行号。 object.Line object 通常是 TextStream 对象的名称。 说明 文件刚
Key 属性 在 Dictionary 对象中设置 key。 object.Key(key) = newkey 参数 object 必选项。通常是 Dictionary 
Item 属性 设置或返回 Dictionary 对象中指定的 key 对应的 item,或返回集合中基于指定的 key 的&
IsRootFolder 属性 如果指定的文件夹是根文件夹,返回 True;否则返回 False。 object.IsRootFolder object 应为&n
IsReady 属性 如果指定的驱动器就绪,返回 True;否则返回 False。 object.IsReady object 应为 Drive&nbs
FreeSpace 属性 返回指定的驱动器或网络共享对于用户的可用空间大小。只读。 object.FreeSpace object 应为 Drive 对象的名称。
FileSystem 属性 返回指定的驱动器使用的文件系统的类型。 object.FileSystem object 应为 Drive 对象的名称。 说明 可
Files 属性 返回由指定文件夹中所有 File 对象(包括隐藏文件和系统文件)组成的 Files 集合。 object.Files object&n
我是一名优秀的程序员,十分优秀!