【问题标题】:How to find whether df column name contains substring in Scala如何在Scala中查找df列名是否包含子字符串
【发布时间】:2021-09-10 18:01:24
【问题描述】:
我的 df 有多个列。我想检查一个列名是否包含子字符串。如 SQL 中的 %。
我尝试使用这个,但似乎不起作用。我不想给出全名来查找该列是否存在。
如果我能找到该列,我还想使用.withColumnRename 重命名该列
像这样的
if (df.columns.contains("%ABC%" or "%BCD%")) df.withColumnrename("%ABC%" or "%BCD%","ABC123") else println(0)
【问题讨论】:
标签:
scala
dataframe
apache-spark
【解决方案1】:
也许你可以试试这个。
- 过滤器可以帮助您选择需要更新的列。
- 在
flodLeft()() 方法中编写更新逻辑。
flodLeft 是 scala 中一个有用的方法。如果您想了解更多关于 flodLeft 的信息,可以在 google 中搜索 scala foldLeft example。
所以,祝你好运。
df.schema.fieldNames.map(_.toUpperCase).filter(x => !x.contains("")).foldLeft(df)((a,b) => {
a.withColumnRenamed(b, ("abc_" + b).toLowerCase() )
})
【解决方案2】:
首先,找到符合您条件的列:
df.columns
.filter(c => c.contains("ABC") || c.contains("BCD"))
.take(1)
如果不存在这样的列,这将返回一个空的Array[String],或者如果该列存在,则返回一个包含单个元素的数组。 take(1) 是为了确保您不会使用相同的新名称重命名多个列。
继续前面的表达式,重命名列归结为调用foldLeft,它遍历集合,将其第二个参数链接到“零”(在本例中为df):
.foldLeft(df)((ds, c) => ds.withColumnRenamed(c, "ABC123"))
如果数组为空,则不会调用任何内容,结果将是原始的df。
它在行动:
df.printSchema
// root
// |-- AB: integer (nullable = false)
// |-- ABCD: string (nullable = true)
df.columns
.filter(c => c.contains("ABC") || c.contains("BCD"))
.take(1)
.foldLeft(df)(_.withColumnRenamed(_, "ABC123"))
.printSchema
// root
// |-- AB: integer (nullable = false)
// |-- ABC123: string (nullable = true)