【发布时间】:2021-12-08 10:45:13
【问题描述】:
如果我有一个值序列,我将如何根据谓词函数找到元素的索引?例如,如果我有以下序列:
let values = @["pie", "cake", "ice cream"]
如何找到具有四个字符的第一个元素的索引?我知道find,但它似乎只能通过相等来查找索引,并且不允许传递谓词。我可以自己实现它,但如果find 是,感觉它应该在标准库中。
【问题讨论】:
如果我有一个值序列,我将如何根据谓词函数找到元素的索引?例如,如果我有以下序列:
let values = @["pie", "cake", "ice cream"]
如何找到具有四个字符的第一个元素的索引?我知道find,但它似乎只能通过相等来查找索引,并且不允许传递谓词。我可以自己实现它,但如果find 是,感觉它应该在标准库中。
【问题讨论】:
一个简单的解决方案是使用sequtils 中的map 将谓词映射到输入序列,然后使用find 获取结果中第一个true 值的索引。当序列中没有元素满足谓词时,这将返回 -1:
import sequtils
proc isLen4(s: string): bool =
len(s) == 4
echo map(@["pie", "cake", "ice cream"], isLen4).find(true) #--> 1
这可行,但对大序列不利,因为map 处理整个序列。因此,即使第一个元素满足谓词,整个序列也会被处理。最好只编写一个findIf 过程,当谓词满足时返回当前索引,而不是继续处理其余的输入:
proc findIf[T](s: seq[T], pred: proc(x: T): bool): int =
result = -1 # return -1 if no items satisfy the predicate
for i, x in s:
if pred(x):
result = i
break
echo @["pie", "cake", "ice cream"].findIf(isLen4) #--> 1
【讨论】: