鉴于此功能,我无法修改:
def numbers(c: Char): Iterator[Int] =
if(Character.isDigit(c)) Iterator(Integer.parseInt(c.toString))
else Iterator.empty
// numbers: (c: Char)Iterator[Int]
这个输入数据:
val data = List('a','b','c','1','d','&','*','x','9')
// data: List[Char] = List(a, b, c, 1, d, &, *, x, 9)
如何使这个函数变得懒惰,以便data
仅处理到第一个出现的数字字符?
def firstNumber(data: List[Char]) :Int = data.flatMap(numbers).take(1)
答案 0 :(得分:6)
data.iterator.flatMap(numbers).take(1).toList
不要使用溪流;您不需要存储旧数据。不要使用观点;他们没有得到精心维护,无论如何都是矫枉过正的。
如果您需要Int
,则需要一些默认行为。根据具体情况,您可以选择
data.iterator.flatMap(numbers).take(1).headOption.getOrElse(0)
或类似
{
val ns = data.iterator.flatMap(numbers)
if (ns.hasNext) ns.next
else throw new NoSuchElementException("Number missing")
}
答案 1 :(得分:2)
只需在数据上调用.toStream
即可:
firstNumber(data.toStream)
答案 2 :(得分:2)
一种可能性是使用Scala的集合视图: http://www.scala-lang.org/docu/files/collections-api/collections_42.html
在集合上调用.view
可以让您在集合上调用map
,flatMap
等函数,而不会生成中间结果。
所以在你的情况下你可以写:
data.view.flatMap(numbers).take(1).force
这会为List[Int]
提供最多一个元素,并且仅将data
处理到第一个数字。
答案 3 :(得分:-1)
你可以使用Streams:
http://www.scala-lang.org/api/current/index.html#scala.collection.immutable.Stream
流创建的一种方式:
1 #:: 2 #:: empty