我在scala中有一个函数,向该函数发送参数,我这样使用它:
val evega = concat.map(_.split(",")).keyBy(_(0)).groupByKey().map{case (k, v) => (k, f(v))}
我的函数f是:
val formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd")
implicit val localDateOrdering: Ordering[LocalDate] = Ordering.by(_.toEpochDay)
def f(v: Array[String]): Int = {
val parsedDates = v.map(LocalDate.parse(_, formatter))
parsedDates.max.getDayOfYear - parsedDates.min.getDayOfYear}
这是我得到的错误:
found : Iterable[Array[String]]
required: Array[String]
我已经尝试使用:
val evega = concat.map(_.split(",")).keyBy(_(0)).groupByKey().map{case (k, v) => (k, for (date <- v) f(date))}
但是我遇到了很多错误。
为了获得更好的图像,concat中的数据是:
1974,1974-06-22
1966,1966-07-20
1954,1954-06-19
1994,1994-06-27
1954,1954-06-26
2006,2006-07-04
2010,2010-07-07
1990,1990-06-30
...
它是RDD [String]类型。 我如何正确地对此进行迭代并从该函数f中获得一个Int?
答案 0 :(得分:2)
管道旁边的RDD类型为:
concat.map(_.split(","))
给出RDD[Array[String]]
Array("1954", "1954-06-19")
concat.map(_.split(",")).keyBy(_(0))
给出RDD[(String, Array[String])]
("1954", Array("1954", "1954-06-19"))
concat.map(_.split(",")).keyBy(_(0)).groupByKey()
给出RDD[(String, Iterable[Array[String]])]
Iterable(("1954", Iterable(Array("1954", "1954-06-19"), Array("1954", "1954-06-24"))))
因此,当您最后map
时,值的类型为Iterable[Array[String]]
。
由于您的输入为"1974,1974-06-22"
,因此解决方案可以包括将keyBy
转换替换为map
:
input.map(_.split(",")).map(x => x(0) -> x(1)).groupByKey().map{case (k, v) => (k, f(v))}
实际上,.map(x => x(0) -> x(1))
(而不是.map(x => x(0) -> x)
的语法keyBy(_(0))
的{{1}})将为分割数组的第二个元素(而不是数组本身)提供值。因此,在第二步中提供RDD[(String, String)]
而不是RDD[(String, Array[String])]
。