Kotlin when() 局部变量介绍

2024-04-10

假设我有一个昂贵的函数,名为doHardThings()它可能返回各种不同的类型,我想根据返回的类型采取行动。在 Scala 中,这是一个常见的用法match构造:

def hardThings() = doHardThings() match {
     case a: OneResult => // Do stuff with a
     case b: OtherResult => // Do stuff with b
}

我正在努力弄清楚如何在 Kotlin 中干净地完成此操作,而不需要引入临时变量doHardThings():

fun hardThings() = when(doHardThings()) {
     is OneResult -> // Do stuff... with what?
     is OtherResult -> // Etc...
}

对于这个常见用例来说,惯用的 Kotlin 模式是什么?


更新:现在这是可能的,来自科特林 1.3 https://kotlinlang.org/docs/reference/whatsnew13.html#capturing-when-subject-in-a-variable。语法如下:

fun hardThings() = when (val result = doHardThings()) {
     is OneResult -> // use result
     is OtherResult -> // use result some other way
}

旧答案:

我认为您只需要为该函数提供一个块体并将操作结果保存到局部变量即可。不可否认,这并不像 Scala 版本那么整洁。

预期用途when with is检查的方法是传入一个变量,然后在分支中使用同一变量,因为如果它通过检查,它就会智能转换为检查的类型,并且您可以轻松访问其方法和属性。

fun hardThings() {
    val result = doHardThings()
    when(result) {
        is OneResult ->   // result smart cast to OneResult
        is OtherResult -> // result smart cast to OtherResult
    }
}

您可以以某种方式围绕您的操作编写某种包装器,以便它仅对其求值一次,否则返回缓存的结果,但这可能不值得它引入的复杂性。

通过 @mfulton26 创建变量的另一个解决方案是使用let():

fun hardThings() = doHardThings().let {
    when(it) {
        is OneResult ->   // it smart cast to OneResult
        is OtherResult -> // it smart cast to OtherResult
    }
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Kotlin when() 局部变量介绍 的相关文章

  • Scala:返回布尔值的模式匹配的缩写形式

    我发现自己经常写这样的东西 a match case b gt do stuff case gt do nothing 有没有更短的方法来检查某个值是否与模式匹配 我的意思是 在这种情况下我可以写if a b do stuff 但是如果模式
  • 将源附加到 kotlin 库项目不会显示在 AS 中

    我想将源代码附加到 kotlin 库项目 看起来我成功了 因为我现在在这里有源 jar https jitpack io com github walleth kethereum bip44 0 21 https jitpack io co
  • 如何解决此问题 目标 S+(版本 31 及更高版本)要求 FLAG_IMMUTABLE 或 FLAG_MUTABLE 之一

    一直试图解决这个问题但无法解决 这是 udacity 课程 我尝试使用挂起意图创建通知 但挂起意图可变存在问题 我尝试用这种方式 视图模型 private val REQUEST CODE 0 private val TRIGGER TIM
  • 测试类内的扩展函数

    如果我们想测试某个类型的扩展函数 我们可以创建该类型的实例 调用该函数并检查返回值 但是测试类内部定义的扩展函数又如何呢 abstract class AbstractClass
  • ECDSA KeyPairGenerator 不可用(但在 JUnit 中有效)

    我遇到了运行 Android 应用程序时观察到的异常 当我将下面的代码作为 JUnit 运行时 它不会发生 java security NoSuchAlgorithmException ECDSA KeyPairGenerator not
  • 覆盖 Kotlin 数据类的 getter

    给定以下 Kotlin 类 data class Test val value Int 我将如何覆盖Intgetter 以便如果值为负数则返回 0 如果这是不可能的 有哪些技术可以达到合适的结果 在花了几乎一整年的时间每天编写 Kotlin
  • 使用 gradle kotlin dsl 执行 JavaExec 任务

    我创建了简单的build gradle kts file group com lapots breed version 1 0 SNAPSHOT plugins java java sourceCompatibility JavaVersi
  • 如何使用分页库在回收器视图中添加日期分隔符?

    经过大量搜索 我知道使用常规适配器是可能的 但我不知道如何使用分页库来做到这一点 我不需要代码 只是一个线索 Example 要添加分隔符 您基本上有两个选择 基于视图 您显式地将分隔符作为 项目 包含在列表中 并为这些分隔符定义新的视图类
  • 如何获取 Android 中其他应用程序的屏幕时间?

    我想达到在 Android 系统上运行的每个应用程序的屏幕时间 例如 Facebook 工作时间为 3 小时 但屏幕时间为 1 2 小时 我怎么才能得到它 android app usage 使用情况统计 public final clas
  • 有没有办法理解安装错误代码的实际含义?

    我正在尝试应用内更新功能 但收到 FAILED 安装状态和 100 安装错误代码 有什么办法让我知道可能是什么原因造成的吗 我实现了灵活的应用内更新 并记录了每个步骤 遵循 Android 开发者教程here https developer
  • 从 kotlin 多平台项目创建 fat jar

    我最近从旧的 1 2 多平台切换到 1 3 不同之处在于 每个多平台模块都有一个 build gradle 文件 我有 5 个 因此配置少了很多 但是 我似乎无法配置使用 jvm 平台的所有依赖项创建可运行的 fat jar 我曾经在 jv
  • 如何使用 Jetpack Compose 按钮​​后面的视图检测单击?

    以下代码适用于 Jetbrains Desktop Compose 它显示了一张带有按钮的卡片 现在如果您单击该卡片 单击的卡片 将回显到控制台 如果您单击该按钮 它将回显 已单击按钮 但是 我正在寻找一种方法让卡检测按钮的点击 我想在不更
  • Kotlin 高阶函数参数:传递子类型

    我在 Kotlin 中遇到了函数参数的问题 我将借助一些代码来解释这个问题 我创建了一个类层次结构 当我将子类型传递给需要父类型的函数时 没有问题 open class A val i Int class B val j Int A j f
  • 如何更改 Kotlin 上生成的 TODO() 函数体?

    我需要在我的代码上留下一些稍后要做的事情TODO 自动生成的会产生一个很长的评论 如下所示 TODO not implemented To change body of created functions use File Settings
  • 如何在 Intellij Idea 12 中重命名/移动项目?

    就像声明的那样here http link sheidaei com mozcw人们可以更改项目的名称 但是 它仅更改项目名称 不会更改文件夹结构 例如 如果您的项目名为sample1并且位于 user1 development IdeaP
  • 在 Android 中处理多个回收器视图 [Kotlin]

    我遇到过这样的情况 一个布局上有 3 个 RecyclerView 他们以某种方式相互依赖 数据来自房间数据库 问题原型 问题陈述 假设您有类似 Floor1 Floor2 Floor3 等 的楼层 并且每个楼层内都有类似 Room1 Ro
  • LiveData无法观察到变化

    我正在更新一个ViewModel 中 DialogFragment 的 LiveData 值 但无法获取Fragment中的值 视图模型 class OtpViewModel private val otpUseCase OtpUseCas
  • Haskell/GHC:使用相同模式匹配多个一元构造函数

    所以我正在尝试定义 TrieSet 数据类型 尽管我知道我不需要 http hackage haskell org package TrieMap module Temp where import Data Map data TrieSet
  • Kotlin 1.6.0 的 proguard / R8 删除了数据类元数据

    我有一个包含一些数据类的包 我尝试使用 Kotlin 反射在运行时访问构造函数clazz primaryConstructor 一切都按预期工作 但是当我启用 R8 时 数据类元数据被删除 例如当我检查是否KClass isData它返回
  • 尝试使用资源/使用/多个资源

    我使用的 Java API 大量使用了 Autoclosable Interface 因此在 Java try with resources 中 然而在Java中你可以指定 try res1 res2 res3 我们有办法使用多种资源吗 它

随机推荐