繁体   English   中英

将tsv文件中的json列解析为Spark RDD

[英]Parsing a json column in tsv file to Spark RDD

我正在尝试将现有的Python(PySpark)脚本移植到Scala,以提高性能。

我在麻烦的基本问题上遇到了麻烦-如何在Scala中解析json列?

这是Python版本

# Each row in file is tab separated, example:
# 2015-10-10 149775392 {"url": "http://example.com", "id": 149775392, "segments": {"completed_segments": [321, 4322, 126]}}

action_files = sc.textFile("s3://my-s3-bucket/2015/10/10/")
actions = (action_files
    .map(lambda row: json.loads(row.split('\t')[-1]))
    .filter(lambda a: a.get('url') != None and a.get('segments') != None and a.get('segments').get('completed_segments') != None)
    .map(lambda a: (action['url'], {"url": action['url'], "action_id": action["id"], "completed_segments": action["segments"]["completed_segments"],}))
    .partitionBy(100)
    .persist())

基本上,我只是试图解析json列,然后将其转换为可以在SparkSQL中进一步处理的简化版本

作为新的Scala用户,我发现有数十个库json解析库可用于此简单任务。 看起来stdlib中没有一个。 从我到目前为止所读的内容来看,强类型语言似乎使这个简单的任务有些繁琐。

我希望能向正确的方向发展!

PS。 顺便说一句,如果我缺少明显的东西使PySpark版本爬行,我很想听听它! 我正在从Hadoop / MR移植Pig脚本,而在MR上性能从17分钟的MR下降到超过5个半小时! 我猜想这是往返于Python的序列化开销。

如果您的目标是将数据传递给SparkSQL,并且您确定没有格式错误的字段(我的代码中没有任何异常处理),那么我完全不会手动进行解析:

val raw = sqlContext.read.json(action_files.flatMap(_.split("\t").takeRight(1)))

val df = raw
  .withColumn("completed_segments", $"segments.completed_segments")
  .where($"url".isNotNull && $"completed_segments".isNotNull)
  .select($"url", $"id".alias("action_id"), $"completed_segments")

关于您的Python代码:

  • 不要使用!=None比较。 正确的使用方法is / is not 从语义上讲这是正确的(“ None是单例),并且速度明显更快。 另请参阅PEP8
  • 除非必须,否则不要重复数据。 两次发送url意味着更高的内存使用率和后续的网络流量
  • 如果您打算使用SparkSQL,则可以在DataFrame上执行与Scala相同的缺失值检查。 我还将坚持DataFrame而不是RDD。

顺带一提,我相当怀疑,但是序列化在这里是一个真正的问题。 有开销,但是真正的影响不应该与您所描述的相近。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM