对于包含字符串和数字数据类型混合的数据框,目标是创建一个新的features
列,其中包含所有这些数据的minhash
。
虽然可以通过执行dataframe.toRDD
来完成此操作,但在下一步将简单地将RDD
返回转换为数据框时,这样做会很昂贵。< / p>
那么有一种方法可以按以下方式进行udf
:
val wholeRowUdf = udf( (row: Row) => computeHash(row))
Row
当然不是spark sql
数据类型 - 所以这不会如图所示。
更新/澄清我意识到创建在withColumn
内运行的全行UDF很容易。在spark sql
声明中可以使用的内容不太清楚:
val featurizedDf = spark.sql("select wholeRowUdf( what goes here? ) as features
from mytable")
答案 0 :(得分:4)
Row当然不是spark sql数据类型 - 所以这不会如图所示。
我将展示您可以使用Row将所有列或所选列传递给使用struct inbuilt函数的udf函数
首先我定义一个dataframe
val df = Seq(
("a", "b", "c"),
("a1", "b1", "c1")
).toDF("col1", "col2", "col3")
// +----+----+----+
// |col1|col2|col3|
// +----+----+----+
// |a |b |c |
// |a1 |b1 |c1 |
// +----+----+----+
然后我定义一个函数,使一行中的所有元素成为一个由,
分隔的字符串(因为你有computeHash函数)
import org.apache.spark.sql.Row
def concatFunc(row: Row) = row.mkString(", ")
然后我在udf
函数
import org.apache.spark.sql.functions._
def combineUdf = udf((row: Row) => concatFunc(row))
最后,我使用udf
函数和withColumn
内置函数调用struct
函数,将所选列组合为一列并传递给udf
功能
df.withColumn("contcatenated", combineUdf(struct(col("col1"), col("col2"), col("col3")))).show(false)
// +----+----+----+-------------+
// |col1|col2|col3|contcatenated|
// +----+----+----+-------------+
// |a |b |c |a, b, c |
// |a1 |b1 |c1 |a1, b1, c1 |
// +----+----+----+-------------+
所以你可以看到 Row可以用来将整行作为参数传递
您甚至可以一次传递一行中的所有列
val columns = df.columns
df.withColumn("contcatenated", combineUdf(struct(columns.map(col): _*)))
<强>更新强>
你也可以使用sql查询实现相同的,你只需要注册udf函数
df.createOrReplaceTempView("tempview")
sqlContext.udf.register("combineUdf", combineUdf)
sqlContext.sql("select *, combineUdf(struct(`col1`, `col2`, `col3`)) as concatenated from tempview")
它会给你与上面相同的结果
现在,如果您不想对列的名称进行硬编码,那么您可以根据需要选择列名并将其设为字符串
val columns = df.columns.map(x => "`"+x+"`").mkString(",")
sqlContext.sql(s"select *, combineUdf(struct(${columns})) as concatenated from tempview")
我希望答案很有帮助
答案 1 :(得分:0)
我提出了一种解决方法:将列名删除到任何现有的spark sql
函数中以生成新的输出列:
concat(${df.columns.tail.mkString(",'-',")}) as Features
在这种情况下,数据框中的第一列是目标,并被排除在外。这是这种方法的另一个优点:许多列的实际列表都被操作。
这种方法避免了RDD /数据帧的不必要重组。