将正则表达式转换应用于String列时,任务不可序列化错误

时间:2017-10-09 09:58:04

标签: scala apache-spark serialization spark-dataframe apache-spark-2.0

我想重新格式化DataFrame的String列。来自格式

(p:str_1,1)(p:str_2,2) ...

格式化

str_1:1|str_2:2 ...

我编写了以下代码[2],但由于org.apache.spark.SparkException: Task not serializable [3]导致Caused by: java.io.NotSerializableException: scala.util.matching.Regex$MatchIterator异常。

有人可以帮助理解为什么Regex$MatchIterator不可序列化以及如何解决这个问题,Iterator返回的findAllIn(xs)似乎对for-statement的{{{{{ 1}} [1]。

非常感谢!

- β

[1]如果我将elem <- mi更改为使用随机迭代器(例如elem <- mi),则没有编译错误并且代码运行 - 但显然不能完成我需要它做的事情。我也试图得到一个正常的迭代器elem <- Iterator(1, 2, 3),但同样的异常发生。

[2]代码

findAllIn(xs).toIterator

[3] StackTrace

val df = spark.sparkContext.parallelize(Seq(("(p:some_string,6)(p:some_other_string,4)", "foo"), ("(p:yet_another_string,1) ", "bar"))).toDF("my_p", "my_s")

val regexStr: String = "\\((?:p|p2)?:(?<q>.+?),(?<s>\\d+)\\)"
def _reformat(xs: String): String = {
    val re: scala.util.matching.Regex = regexStr.r
    val mi = re.findAllIn(xs)

    val d: Iterator[String] = for {
        elem <- mi
        val q: String = mi.group(1)
        val s: String = mi.group(2)
        val pair: String = s"${q}:${s}"
    } yield pair
    d.mkString("|")
}
def reformat: UserDefinedFunction = udf[String, String](_reformat)

val dfReformated: DataFrame = df
    .withColumn("my_p", reformat($"my_p"))

0 个答案:

没有答案