Spark中Vector转变成Array

Convert a Spark Vector of features into an array

在spark处理数据的时候经常会有某个字段处理成Vector的情况,这样的字段在很多的数据固化组件中可能不能直接存储,这个时候需要我们变通一下,把得到的向量转变成Array或者字符串的格式,便于存储

Spark 3.0 增加了 vector_to_array 的UDF. 不需要自我实现了,直接调用即可。但是如果spark的版本较低,则需要自己实现转换逻辑。

时光机:https://github.com/apache/spark/pull/26910

提供两个代码示例,如果读者明确知道自己的数据是什么格式的向量,例如

import org.apache.spark.ml.linalg.DenseVector
val toArr: Any => Array[Double] = _.asInstanceOf[DenseVector].toArray
val toArrUdf = udf(toArr)
val dataWithFeaturesArr = dataWithFeatures.withColumn("features_arr",toArrUdf('features))

但是如果读者不清楚自己的向量是哪个,那就尽可能去兼容一下,如下

import org.apache.spark.ml.linalg.{SparseVector, Vector}
import org.apache.spark.mllib.linalg.{Vector => OldVector}

private val vectorToArrayUdf = udf { vec: Any =>
    vec match {
      case v: Vector => v.toArray
      case v: OldVector => v.toArray
      case v => throw new IllegalArgumentException(
        "function vector_to_array requires a non-null input argument and input type must be " +
        "`org.apache.spark.ml.linalg.Vector` or `org.apache.spark.mllib.linalg.Vector`, " +
        s"but got ${ if (v == null) "null" else v.getClass.getName }.")
    }
  }.asNonNullable()

发表回复