在 2 个 Spark 数据框列之间使用 "IS IN"
Use "IS IN" between 2 Spark dataframe columns
我有上面的数据框:
from pyspark.sql.types import *
rdd = sc.parallelize([
('ALT', ['chien', 'chat'] , 'oiseau'),
('ALT', ['oiseau'] , 'oiseau'),
('TDR', ['poule','poulet'], 'poule' ),
('ALT', ['ours'] , 'chien' ),
('ALT', ['paon'] , 'tigre' ),
('TDR', ['tigre','lion'] , 'lion' ),
('ALT', ['chat'] ,'chien' ),
])
schema = StructType([StructField("ClientId",StringType(),True),
StructField("Animaux",ArrayType(StringType(),True),True),
StructField("Animal",StringType(),True),])
test = rdd.toDF(schema)
test.show()
+--------+---------------+------+
|ClientId| Animaux|Animal|
+--------+---------------+------+
| ALT| [chien, chat]|oiseau|
| ALT| [oiseau]|oiseau|
| TDR|[poule, poulet]| poule|
| ALT| [ours]| chien|
| ALT| [paon]| tigre|
| TDR| [tigre, lion]| lion|
| ALT| [chat]| chien|
+--------+---------------+------+
我想创建一个新列,如果列 "Animal" 中的字符串在列 "Animaux" 的列表中,则该列的值为“1”,否则为“0”。
我试过了:
test2=test.withColumn("isinlist", F.when("Animal in Animaux", 'ok').otherwise('pas ok'))
test2=test.withColumn("isinlist", F.when(test.Animal.isin(*test.Animaux), 'ok').otherwise('pas ok'))
test.where("Animal in (Animaux)").show()
test.where("Animal in Animaux").show()
test2=test.withColumn("isinlist", F.when(test.Animal.isin(test.Animaux), 'ok').otherwise('pas ok'))
但是 none 有效...
有谁知道如何在不使用 udf 的情况下做到这一点...有直接的方法吗?
您可以使用 array_contains
:
from pyspark.sql.functions import expr
test.withColumn("isinlist", expr("array_contains(Animaux, Animal)")).show()
# +--------+---------------+------+--------+
# |ClientId| Animaux|Animal|isinlist|
# +--------+---------------+------+--------+
# | ALT| [chien, chat]|oiseau| false|
# | ALT| [oiseau]|oiseau| true|
# | TDR|[poule, poulet]| poule| true|
# | ALT| [ours]| chien| false|
# | ALT| [paon]| tigre| false|
# | TDR| [tigre, lion]| lion| true|
# | ALT| [chat]| chien| false|
# +--------+---------------+------+--------+
来源 by zero323 (Scala)。
我有上面的数据框:
from pyspark.sql.types import *
rdd = sc.parallelize([
('ALT', ['chien', 'chat'] , 'oiseau'),
('ALT', ['oiseau'] , 'oiseau'),
('TDR', ['poule','poulet'], 'poule' ),
('ALT', ['ours'] , 'chien' ),
('ALT', ['paon'] , 'tigre' ),
('TDR', ['tigre','lion'] , 'lion' ),
('ALT', ['chat'] ,'chien' ),
])
schema = StructType([StructField("ClientId",StringType(),True),
StructField("Animaux",ArrayType(StringType(),True),True),
StructField("Animal",StringType(),True),])
test = rdd.toDF(schema)
test.show()
+--------+---------------+------+
|ClientId| Animaux|Animal|
+--------+---------------+------+
| ALT| [chien, chat]|oiseau|
| ALT| [oiseau]|oiseau|
| TDR|[poule, poulet]| poule|
| ALT| [ours]| chien|
| ALT| [paon]| tigre|
| TDR| [tigre, lion]| lion|
| ALT| [chat]| chien|
+--------+---------------+------+
我想创建一个新列,如果列 "Animal" 中的字符串在列 "Animaux" 的列表中,则该列的值为“1”,否则为“0”。
我试过了:
test2=test.withColumn("isinlist", F.when("Animal in Animaux", 'ok').otherwise('pas ok'))
test2=test.withColumn("isinlist", F.when(test.Animal.isin(*test.Animaux), 'ok').otherwise('pas ok'))
test.where("Animal in (Animaux)").show()
test.where("Animal in Animaux").show()
test2=test.withColumn("isinlist", F.when(test.Animal.isin(test.Animaux), 'ok').otherwise('pas ok'))
但是 none 有效... 有谁知道如何在不使用 udf 的情况下做到这一点...有直接的方法吗?
您可以使用 array_contains
:
from pyspark.sql.functions import expr
test.withColumn("isinlist", expr("array_contains(Animaux, Animal)")).show()
# +--------+---------------+------+--------+
# |ClientId| Animaux|Animal|isinlist|
# +--------+---------------+------+--------+
# | ALT| [chien, chat]|oiseau| false|
# | ALT| [oiseau]|oiseau| true|
# | TDR|[poule, poulet]| poule| true|
# | ALT| [ours]| chien| false|
# | ALT| [paon]| tigre| false|
# | TDR| [tigre, lion]| lion| true|
# | ALT| [chat]| chien| false|
# +--------+---------------+------+--------+
来源