如果n小于size,则x .sliding(n)的行为不一致



根据scaladoc,滑动()返回…

生成大小为size的可迭代集合的迭代器,除最后一个也是唯一一个元素外,如果元素少于size,则将被截断。

对于我来说,直观地,滑动(n)将返回一个包含n个元素的滑动窗口,如果可用。对于当前的实现,我需要执行一个额外的检查,以确保我没有得到一个包含1或2个元素的列表。

scala> val xs = List(1, 2)
xs: List[Int] = List(1, 2)
scala> xs.sliding(3).toList
res2: List[List[Int]] = List(List(1, 2))

我期望这里是一个空列表。为什么滑动()以这种方式实现?

这是一个错误,但没有修复为2.9。每个人偶尔都会犯设计错误,一旦进入库,删除它就不是一件容易的事。

解决方法:添加一个过滤器。

xs.sliding(3).filter(_.size==3).toList

您可以通过使用GroupedIterator#withPartial修饰符来"解决"这个问题。

scala> val xs = List(1, 2)
xs: List[Int] = List(1, 2)
scala> xs.iterator.sliding(3).withPartial(false).toList
res7: List[Seq[Int]] = List()

(我不知道为什么你需要说xs.iterator,但xs.sliding(3).withPartial(false)不工作,因为你得到一个Iterator而不是GroupedIterator

EDIT:

检查Rex的答案(哪个是正确的)。我离开这里只是因为(正如Rex在评论中所说)这是设计决策背后的原始(错误)想法。

我不知道为什么你会期望一个空列表,返回完整的列表似乎是最好的结果,考虑这个例子:

def slidingWindowsThing(windows : List[List[Int]]) { // do your thing

对于这个方法,您可能希望所有这些调用都能工作:

slidingWindowsThing((1 to 10).sliding(3))
slidingWindowsThing((1 to 3).sliding(3))
slidingWindowsThing((1 to 1).sliding(3))

这就是为什么方法默认为list.length大小的列表而不是Nil(空列表)。

最新更新