所以,我在下面做的是从A
删除一列DataFrame
,因为我想应用转换(这里我只是json.loads
一个JSON字符串)并替换变换后的旧列。转换后,我只加入两个结果数据帧。
df = df_data.drop('A').join(
df_data[['ID', 'A']].rdd\
.map(lambda x: (x.ID, json.loads(x.A))
if x.A is not None else (x.ID, None))\
.toDF()\
.withColumnRenamed('_1', 'ID')\
.withColumnRenamed('_2', 'A'),
['ID']
)
我不喜欢这件事当然是我面临的开销,因为我必须进行withColumnRenamed
操作。
使用熊猫所有我都会这样做:
pdf = pd.DataFrame([json.dumps([0]*np.random.randint(5,10)) for i in range(10)], columns=['A'])
pdf.A = pdf.A.map(lambda x: json.loads(x))
pdf
但以下内容在pyspark中不起作用:
df.A = df[['A']].rdd.map(lambda x: json.loads(x.A))
那么有没有比我在第一个代码剪切时更简单的方法?
答案 0 :(得分:3)
我认为您不需要删除列并进行连接。以下代码 * 应与您发布的内容相同:
1234567 300.0000000 2223456 390-9.00000000000000D+02 1.00000D-06 111 5.2 900.0 95.6
1234567 300.0000000 2723456 10 2.00000000000000D+04 7.83912D-06 111 6.2 900.0 95.6
1234567 300.0000000 2723456 190-3.00000000000000D+03 1.00000D-06 111 7.2 900.0 95.6
1234567 300.0000000 2823456120 2.00000000000000D+04 5.13183D-05 111 8.2 900.0 95.6
1234567 300.0000000 28234561290-1.00000000000000D+03 1.00000D-06 111 9.2 900.0 95.6
1234567 300.0000000 2723456 190-3.00000000000000D+03 1.00000D-06 111 7.2 900.0 95.6
1234567 300.0000000 2823456120 2.00000000000000D+04 5.13183D-05 111 8.2 900.0 95.6
* 我还没有真正测试过这段代码,但我认为这应该可行。
但是要回答您的一般问题,您可以使用cols = df_data.columns
df = df_data.rdd\
.map(
lambda row: tuple(
[row[c] if c != 'A' else (json.loads(row[c]) if row[c] is not None else None)
for c in cols]
)
)\
.toDF(cols)
就地转换列。
withColumn()
df = df_data.withColumn("A", my_transformation_function("A").alias("A"))
可以是my_transformation_function()
或udf
。
答案 1 :(得分:1)
从我能理解的,你想要达到的目标是什么?
import pyspark.sql.functions as F
import json
json_convert = F.udf(lambda x: json.loads(x) if x is not None else None)
cols = df_data.columns
df = df_data.select([json_convert(F.col('A')).alias('A')] + \
[col for col in cols if col != 'A'])