Apache spark PySpark:withColumn()具有两个条件和三个结果
我和Spark和Pypark一起工作。我试图实现与以下伪代码等效的结果:Apache spark PySpark:withColumn()具有两个条件和三个结果,apache-spark,hive,pyspark,apache-spark-sql,hiveql,Apache Spark,Hive,Pyspark,Apache Spark Sql,Hiveql,我和Spark和Pypark一起工作。我试图实现与以下伪代码等效的结果: df=df.withColumn('new_column', 如果FROUT1==FROUT2,则为1,否则为0。如果FROUT1为NULL或FROUT2为NULL,则为3。) 我试图在PySpark中实现这一点,但我不确定语法。有什么建议吗?我查看了expr(),但无法让它工作 请注意,df是一个pyspark.sql.dataframe.dataframe您需要使用如下udf from pyspark.sql.typ
df=df.withColumn('new_column',
如果FROUT1==FROUT2,则为1,否则为0。如果FROUT1为NULL或FROUT2为NULL,则为3。)
我试图在PySpark中实现这一点,但我不确定语法。有什么建议吗?我查看了expr()
,但无法让它工作
请注意,
df
是一个pyspark.sql.dataframe.dataframe
您需要使用如下udf
from pyspark.sql.types import IntegerType
from pyspark.sql.functions import udf
def func(fruit1, fruit2):
if fruit1 == None or fruit2 == None:
return 3
if fruit1 == fruit2:
return 1
return 0
func_udf = udf(func, IntegerType())
df = df.withColumn('new_column',func_udf(df['fruit1'], df['fruit2']))
有几种有效的方法来实现这一点。让我们从所需的导入开始:
from pyspark.sql.functions import col, expr, when
您可以在expr内使用配置单元IF
函数:
new_column_1 = expr(
"""IF(fruit1 IS NULL OR fruit2 IS NULL, 3, IF(fruit1 = fruit2, 1, 0))"""
)
或时
+否则
:
new_column_2 = when(
col("fruit1").isNull() | col("fruit2").isNull(), 3
).when(col("fruit1") == col("fruit2"), 1).otherwise(0)
最后,您可以使用以下技巧:
from pyspark.sql.functions import coalesce, lit
new_column_3 = coalesce((col("fruit1") == col("fruit2")).cast("int"), lit(3))
使用示例数据:
df = sc.parallelize([
("orange", "apple"), ("kiwi", None), (None, "banana"),
("mango", "mango"), (None, None)
]).toDF(["fruit1", "fruit2"])
您可以按如下方式使用它:
(df
.withColumn("new_column_1", new_column_1)
.withColumn("new_column_2", new_column_2)
.withColumn("new_column_3", new_column_3))
结果是:
+------+------+------------+------------+------------+
|结果1 |结果2 |新|列| 1 |新|列| 2 |新|列| 3|
+------+------+------------+------------+------------+
|橙色|苹果| 0 | 0 | 0|
|猕猴桃|空| 3 | 3 | 3|
|空|香蕉| 3 | 3 | 3|
|芒果|芒果| 1 | 1 | 1|
|空|空| 3 | 3 | 3|
+------+------+------------+------------+------------+
pyspark中的withColumn函数使您能够使用条件创建一个新变量,添加when和others函数,这样您就有了一个正常工作的if-then-else结构。
对于所有这些,您需要导入sparksql函数,因为您将看到,如果没有col()函数,下面的代码将无法工作。
在第一位中,我们声明了一个新列-“new column”,然后给出when函数中包含的条件(即,fruth1==fruth2),然后如果条件为true,则给出1;如果条件为false,则控件转到否则,否则它将处理第二个条件(fruth1或fruth2为Null),并使用isNull()函数,如果返回true 3,如果返回false,则再次检查否则,并给出0作为答案
从pyspark.sql导入函数为F
df=df.withColumn('new_column',
F.when(F.col('fruit1')==F.col('fruit2'),1)
。否则(F.when((F.col('grout1').isNull())|(F.col('grout2').isNull()),3))
。否则(0))
我从这个解决方案中得到了几个错误,@David。第一个问题通过pyspark.sql.types import StringType中的解决。第二个是:TypeError:“int”对象不可调用
,我不确定如何解决。请注意,df
是一个pyspark.sql.dataframe.dataframe
@user2205916,我有几个输入错误。在def func(…
行中,我有水果1
(带空格)而不是foult1
。在开始的func_udf=…
行中,我有StringType
而不是IntegerType
。用更新后的代码尝试一下,如果仍然有问题,请告诉我。我会收到相同的错误消息。此外,我认为df=…
末尾缺少一个paren,这是另一个输入错误,从第二位到最后一位ne应该是func\u udf=udf(func,IntegerType())
必须运行,但这很接近(可以承受打字错误)。如果它仍然不起作用,请确保在spark 2.2+中没有类似情况,函数“col”对我不起作用。直接使用不带引号的列名可以起作用。例如:new\u column\u 1=expr(“col\u 1+int(col_2/15)“你能解释一下你的代码吗?这样新来的人就能理解你的代码了done@Nidhi,如果grout1
和grout2
来自不同的数据帧,是否可以执行类似的操作?