我有一个很大的'数据集(huge_df
),大于20列。其中一列是id
字段(使用pyspark.sql.functions.monotonically_increasing_id()
生成)。
使用某些条件,我会生成第二个数据帧(filter_df
),其中包含id
值,我希望稍后从huge_df
过滤。
目前我使用SQL语法来执行此操作:
filter_df.createOrReplaceTempView('filter_view')
huge_df = huge_df.where('id NOT IN (SELECT id FROM filter_view)')
问题1:
有没有办法只使用Python,即无需注册TempView
?
问题2: 有没有完全不同的方法来完成同样的事情?
答案 0 :(得分:6)
您可以使用JOIN
huge_df = huge_df.join(filter_df, huge_df.id == filter_df.id, "left_outer")
.where(filter_df.id.isNull())
.select([col(c) for c in huge_df.columns]
然而,这将导致昂贵的洗牌。
逻辑很简单:在id字段上保持与filter_df的连接并检查filter_df是否为null - 如果它为null,则表示filter_df中没有这样的行
答案 1 :(得分:0)
这是另一种方法 -
# Sample data
hugedf = spark.createDataFrame([[1,'a'],[2,'b'],[3,'c'],[4,'d']],schema=(['k1','v1']))
fildf = spark.createDataFrame([[1,'b'],[3,'c']],schema=(['k2','v2']))
from pyspark.sql.functions import col
hugedf\
.select('k1')\
.subtract(fildf.select('k2'))\
.toDF('d1')\
.join(hugedf,col('d1')==hugedf.k1)\
.drop('d1')\
.show()
逻辑很简单,从在hugeDF中找到的id值中减去在filteredDf中找到的id值,留下不在filterDF中的ID值,
我将减去的值标记为列' d1'为了清楚起见,然后在d1值上加入hugeDF表并删除d1以得到最终结果。