List 如何在scala中将列表按周分组

List 如何在scala中将列表按周分组,list,scala,split,List,Scala,Split,如何将数据分成组,每组有一周的数据,如果一周不完整,也有一组。因此,团队应该 case class Test(dayOfWeek:Int,b:Int=Random.nextInt) val data=(3 to 100).map(_ % 7).map(Test(_)) 您可以通过折叠来完成: Group 1: (3,4,5,6) // the number here is the dayOfWeek Group 2: (0,1,2,3,4,5,6) Group 3: (0,1,2,3,4,

如何将数据分成组,每组有一周的数据,如果一周不完整,也有一组。因此,团队应该

case class Test(dayOfWeek:Int,b:Int=Random.nextInt)
val data=(3 to 100).map(_ % 7).map(Test(_))

您可以通过折叠来完成:

Group 1: (3,4,5,6)   // the number here is the dayOfWeek
Group 2: (0,1,2,3,4,5,6)
Group 3: (0,1,2,3,4,5,6)
...
last Group:(0,1,2)

这是一个递归版本,它可以处理一般序列,现在需要一个
工作日
函数

Group 0: (3,4,5,6)
Group 1: (0,1,2,3,4,5,6)
Group 2: (0,1,2,3,4,5,6)
Group 3: (0,1,2,3,4,5,6)
Group 4: (0,1,2,3,4,5,6)
Group 5: (0,1,2,3,4,5,6)
Group 6: (0,1,2,3,4,5,6)
Group 7: (0,1,2,3,4,5,6)
Group 8: (0,1,2,3,4,5,6)
Group 9: (0,1,2,3,4,5,6)
Group 10: (0,1,2,3,4,5,6)
Group 11: (0,1,2,3,4,5,6)
Group 12: (0,1,2,3,4,5,6)
Group 13: (0,1,2,3,4,5,6)
Group 14: (0,1,2)
这样称呼:

def groupByWeek[T](s: Seq[T], maxDay: Int = 6, weekDay: T => Int) = {
  @scala.annotation.tailrec
  def recurse(r: Seq[T], results: Seq[Seq[T]]): Seq[Seq[T]] =
    r.splitAt(r.indexWhere(item => weekDay(item) == maxDay)) match {
      case (hd, tl) if (hd.isEmpty && tl.isEmpty) => results
      case (hd, tl) if (hd.isEmpty) => results :+ tl
      case (hd, tl) => recurse(tl.tail, results :+ (hd :+ tl.head))
    }
  recurse(s,Seq.empty)
  }
}
您可以看到以下组:

val weeks = groupByWeek(data, weekDay = (x:Test) => x.dayOfWeek)
哪些产出:

println(weeks.zipWithIndex.map {
  case (week, i) => s"Group $i: (${week.map(_.dayOfWeek).mkString(",")})"
}.mkString("\n"))

Scala的集合功能非常强大,这需要几行代码:

Group 0: (3,4,5,6)
Group 1: (0,1,2,3,4,5,6)
Group 2: (0,1,2,3,4,5,6)
[snip]
Group 12: (0,1,2,3,4,5,6)
Group 13: (0,1,2,3,4,5,6)
Group 14: (0,1,2)
查看文档中的
span
分组

产出:

println(weeks.zipWithIndex.map {
  case (week, i) => s"Group $i: (${week.map(_.dayOfWeek).mkString(",")})"
}.mkString("\n"))

我认为,如果第一个元素是0,那么在开始时将得到一个空组。例如,
val data=(0到10).map(%7).map(Test(%7))
Yes,这就是我想要的优雅@意志,如果一个答案满足你,考虑接受它()。
val (firstWeek, nextWeeks) = data.span(_.dayOfWeek != 0)
val weeks = (firstWeek :: nextWeeks.grouped(7).toList).dropWhile(_.isEmpty)
println(weeks.zipWithIndex.map {
  case (week, i) => s"Group $i: (${week.map(_.dayOfWeek).mkString(",")})"
}.mkString("\n"))
Group 0: (3,4,5,6)
Group 1: (0,1,2,3,4,5,6)
Group 2: (0,1,2,3,4,5,6)
[snip]
Group 12: (0,1,2,3,4,5,6)
Group 13: (0,1,2,3,4,5,6)
Group 14: (0,1,2)