Kotlin多变量let,在下一个let中使用前面的变量

Kotlin多变量let,在下一个let中使用前面的变量,kotlin,optional,let,Kotlin,Optional,Let,我希望能够有多个let,并且下一个let只能在前一个变量不为null时使用前一个变量。我想要这个的原因是因为我只想要一个:?尽管如此。这可能吗 关于我希望它是怎样的示例: fun example() { firstVariable?.let a -> && exampleFunction(a, 3)?.let { a, b -> // Use a and b freely since they are not null and not optional

我希望能够有多个let,并且下一个let只能在前一个变量不为null时使用前一个变量。我想要这个的原因是因为我只想要一个:?尽管如此。这可能吗

关于我希望它是怎样的示例:

fun example() {
  firstVariable?.let a -> &&
  exampleFunction(a, 3)?.let { a, b ->
    // Use a and b freely since they are not null and not optionals
  } ?: run {
    // Runs if either one of the let is failing
  }
}

// a is NOT optional
fun exampleFunction(a: Int, b: Int?): Int? {
  if (b == null) {
    return null
  }

  return a + b
}
愚蠢的例子,但它只是为了显示我需要什么。。。我想检查第一个变量是否为null,并运行一个函数,该函数返回一个可选参数,其中一个非可选参数是第一个变量-如果其中任何一个失败,我想运行其他一些

我知道如何在没有let的情况下做到这一点,但我想知道是否有可能或计划能够做到这一点?(在Swift中是可能的)

如何在Swift中执行此操作:

// First check a, then use a in the same expression if its validated
if let a = firstVariable,
   let b = exampleFunction(a) {
  // Use a and b as non-optionals
} else {
  // a or b failed
}

您可以从Kotlin中获益,并为您的案例编写sot扩展函数
vararg
因为我们不知道要传递多少个变量,所以请检查是否所有变量都不是null,如果是,则返回所有变量。如果任何一个变量都为null,那么什么也不会发生

fun <T: Any> multipleLetCheck(vararg variables: T?, block: (List<T>) -> Unit): Unit? {
    return if (variables.all { variable -> variable != null }) {
        block(variables.filterNotNull())
    } else {
        null
    }
}

// usage
multipleLetCheck(firstVariable, 3){ (firstVariable, secondVariable) ->
    // work with firstVariable and secondVariable
} ?: run {

}
fun multipletcheck(vararg变量:T?,块:(列表)->单位):单位?{
返回if(variables.all{variable->variable!=null}){
块(variables.filterNotNull())
}否则{
无效的
}
}
//用法
MultipleTech(第一个变量,3){(第一个变量,第二个变量)->
//使用第一个变量和第二个变量
}?:运行{
}

你可能误解了
如何工作。我要解释一下。简而言之,所需的行为在kotlin中是不可能的,或者至少你不能习惯性地模仿它而没有任何缺点

我不知道swift,但似乎使用的
let
是语言本身提供的某种语法结构。它允许您定义具有某些局部范围的变量,并且可以链接(如短路
&&

然而,在Kotlin中,
let
只是一个普通函数。 看。基本上只不过是

fun <T, R> T.let(block: (T) -> R): R = block(this)
其中
a+b
只是使用这两个值的示例。但是,如果长度超过一行,这将变得不方便。如果仍要定义局部变量,可以使用
run
创建一个块,并在
?:
的右侧使用跳转语句

run {
    val a = firstValue ?: return@run null
    val b = exampleFunction(a, 3) ?: return@run null
    return@run a + b
} ?: run{}

虽然上面的代码与所有这些
return@run空
重复可能有一些方法可以减少重复代码的数量,例如使用匿名函数(去除
@run
部分)或返回
单位
并通过一些副作用操作保护最后一个值。(为了摆脱
null
和最后一个返回语句)

我相信现在还没有这样的功能,但是如果您满意的话,您可以创建自己的扩展函数。我不确定如何编写这样的函数。你能举个例子吗?:)@Eugene链接并不能解决我的问题,因为下一个let不能使用第一个结果(正如我在那里评论的那样)。如上所述:示例函数很愚蠢,但只是为了证明我的观点。并不能解决我的问题。我只想在第一个变量不为空的情况下使用第一个变量的结果。@Eugene更新了问题,以便更清楚地说明我想做什么。这很好,但这并不能解决我的问题:我只想在第一个变量不为null的情况下运行一个函数。我还想让let的返回值能够有不同类型的
block(variables.filterNotNull())
filterNotNull,这里不需要,因为你的.all{}all{}返回数组not list我不确定是否得到@Otziii,但是请看编辑。现在,如果任何变量为null,则执行
run{}
。这就是你想要的?谢谢你的回答。我明白这在let本身是不可能的,我想知道这在其他方面是否可能。你的跑步方式解决了这个问题。(是的,它很难看,但它正是我想要的功能!)也许一种更好的方式将成为未来的一项功能
run {
    val a = firstValue ?: return@run null
    val b = exampleFunction(a, 3) ?: return@run null
    return@run a + b
} ?: run{}