科特林。在嵌套列表中按参数查找元素
Kotlin. Find element by param in nested lists
我有一些data clases
data class Data(val docNumber: Int?,
val docType: Int?,
val fiscprops: List<FiscProp>,
val name: String?
) {
fun getFiscProp(tag: Int) = fiscprops.firstOrNull { it.tag == tag }
}
data class FiscProp(val caption: String?,
val printable: String?,
val tag: Int?,
val value: Any?,
val fiscprops: List<FiscProp>?)
我需要在嵌套的 lists
中通过 tag
找到 FiscProp
。如果我使用 getFiscProp
,我只能在第一层找到 FiscProp
。
如何在所有级别上找到元素?不知道会到几级
您可以为此使用基本的递归搜索:
fun List<FiscProp>.getFiscProp(tag: Int): FiscProp? {
for (fiscProp in this) {
if (fiscProp.tag == tag)
return fiscProp
val found = fiscProp.fiscprops?.getFiscProp(tag)
if (found != null)
return found
}
return null
}
我觉得这个功能版应该也可以,但是我没测试过:
fun List<FiscProp>.getFiscProp(tag: Int): FiscProp? = firstNotNullOfOrNull {
if (it.tag == tag) it else it.fiscprops?.getFiscProp(tag)
}
val FiscProp.allProps: Sequence<FiscProp>
get() = sequence {
yield(this@allProps)
fiscprops?.forEach {
yieldAll(it.allProps)
}
}
class Data(...) {
fun getFiscProp(tag: Int) = fiscprops.asSequence()
.flatMap { it.allProps}
.firstOrNull { it.tag == tag }
}
这是一个尾递归版本。
data class Data(...) {
fun findByTag(tag: Int) = findByTag(fiscprops, tag)
private tailrec fun findByTag(fiscprops: List<FiscProp>, tag: Int): FiscProp? =
if (fiscprops.isEmpty()) null
else {
val fiscprop = fiscprops.first()
if (fiscprop.tag == tag) fiscprop
else findByTag(fiscprops.drop(1) + fiscprop.fiscprops.orEmpty(), tag)
}
}
我有一些data clases
data class Data(val docNumber: Int?,
val docType: Int?,
val fiscprops: List<FiscProp>,
val name: String?
) {
fun getFiscProp(tag: Int) = fiscprops.firstOrNull { it.tag == tag }
}
data class FiscProp(val caption: String?,
val printable: String?,
val tag: Int?,
val value: Any?,
val fiscprops: List<FiscProp>?)
我需要在嵌套的 lists
中通过 tag
找到 FiscProp
。如果我使用 getFiscProp
,我只能在第一层找到 FiscProp
。
如何在所有级别上找到元素?不知道会到几级
您可以为此使用基本的递归搜索:
fun List<FiscProp>.getFiscProp(tag: Int): FiscProp? {
for (fiscProp in this) {
if (fiscProp.tag == tag)
return fiscProp
val found = fiscProp.fiscprops?.getFiscProp(tag)
if (found != null)
return found
}
return null
}
我觉得这个功能版应该也可以,但是我没测试过:
fun List<FiscProp>.getFiscProp(tag: Int): FiscProp? = firstNotNullOfOrNull {
if (it.tag == tag) it else it.fiscprops?.getFiscProp(tag)
}
val FiscProp.allProps: Sequence<FiscProp>
get() = sequence {
yield(this@allProps)
fiscprops?.forEach {
yieldAll(it.allProps)
}
}
class Data(...) {
fun getFiscProp(tag: Int) = fiscprops.asSequence()
.flatMap { it.allProps}
.firstOrNull { it.tag == tag }
}
这是一个尾递归版本。
data class Data(...) {
fun findByTag(tag: Int) = findByTag(fiscprops, tag)
private tailrec fun findByTag(fiscprops: List<FiscProp>, tag: Int): FiscProp? =
if (fiscprops.isEmpty()) null
else {
val fiscprop = fiscprops.first()
if (fiscprop.tag == tag) fiscprop
else findByTag(fiscprops.drop(1) + fiscprop.fiscprops.orEmpty(), tag)
}
}