Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/295.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Apache spark 分组记录后的字数计算(第2部分)_Apache Spark_Pyspark - Fatal编程技术网

Apache spark 分组记录后的字数计算(第2部分)

Apache spark 分组记录后的字数计算(第2部分),apache-spark,pyspark,Apache Spark,Pyspark,虽然我支持我想要实现的目标,但问题是这是一种缓慢的方式。数据集不是很大。总共是50GB,但受影响的部分可能只有5到10GB的数据。然而,以下是我所需要的,但这是一种缓慢的方式,我所说的缓慢是指它运行了一个小时,并没有终止 df_u3;=spark.createDataFrame[ “你好,今天好吗?”, “1”,“你好吗”, “2”,“你好,你在吗”, “2”,“怎么样”, “3”,“你好”, “3”,“你好”, “4”,“你好,你今天好吗” ],schema=['label','text']

虽然我支持我想要实现的目标,但问题是这是一种缓慢的方式。数据集不是很大。总共是50GB,但受影响的部分可能只有5到10GB的数据。然而,以下是我所需要的,但这是一种缓慢的方式,我所说的缓慢是指它运行了一个小时,并没有终止

df_u3;=spark.createDataFrame[ “你好,今天好吗?”, “1”,“你好吗”, “2”,“你好,你在吗”, “2”,“怎么样”, “3”,“你好”, “3”,“你好”, “4”,“你好,你今天好吗” ],schema=['label','text'] tokenizer=TokenizerinputCol='text',outputCol='tokens' tokens=tokenizer.transformdf_ token_计数。groupby'label'\ .aggF.collect_listF.structF.col'token',F.col'count'。别名'text'\ .showtruncate=False 这为我提供了每个标签的令牌计数:

+-----+----------------------------------------------------------------+
|label|text                                                            |
+-----+----------------------------------------------------------------+
|3    |[[are,2], [how,2], [hello,2], [you,2]]                          |
|1    |[[today,1], [how,2], [are,3], [you,2], [hello,2]]               |
|4    |[[hello,1], [how,1], [is,1], [today,1], [you,1], [it,1]]        |
|2    |[[hello,1], [are,1], [you,1], [here,1], [is,1], [how,1], [it,1]]|
+-----+----------------------------------------------------------------+
然而,我认为对这个来说,要求爆炸的代价太高了

我不知道,但计算每个dokument中的令牌数,然后将其合并到groupBy中可能会更快:

df_u.select['label']+[udf_get_tokensF.col'text'。别名'text']\ .rdd.maplambda x:x[0],listCounterx[1]。项\ .toDFschema=['label','text']\ 显示 给出了计数:

+-----+--------------------+
|label|                text|
+-----+--------------------+
|    1|[[are,2], [hello,...|
|    1|[[are,1], [hello,...|
|    2|[[are,1], [hello,...|
|    2|[[how,1], [it,1],...|
|    3|[[are,1], [hello,...|
|    3|[[are,1], [hello,...|
|    4|[[you,1], [today,...|
+-----+--------------------+
有没有一种方法可以更有效地合并这些令牌计数?

如果由id定义的组更大,那么改进的明显目标就是洗牌大小。洗牌标签,而不是洗牌文本。第一矢量化输入

从pyspark.ml.feature导入CountVectorizer 从pyspark.ml导入管道 管道\模型=管道阶段=[ TokenizerinputCol='text',outputCol='tokens', CountVectorierInputCol='tokens',outputCol='vectors' ]fitdf先生_ df\u vec=管道模型。转换df\ux。选择标签,向量 然后汇总:

从pyspark.ml.linalg导入SparseVector、DenseVector 从集合导入defaultdict def seq_funcacc,v: 如果isinstancev,SparseVector: 对于i/v指数: acc[inti]+=v[inti] 如果是安装,则DenseVector: 对于lenv中的i: acc[inti]+=v[inti] 返回acc def comb_funcacc1、acc2: 对于acc2.1项目中的k、v: acc1[k]+=v 返回acc1 聚合=rdd.aggregateByKeyDefaultDictent,seq_func,comb_func 并映射回所需的输出:

词汇表=管道模型。阶段[-1]。词汇表 def fx,词汇=词汇: 对于元组列表,使用[词汇表[i],floatv表示i,v表示x.items] 返回{词汇表[i]:floatv表示i,v表示x.items} 聚合的.mapValuesf.toDF[id,文本].showtruncate=False +--+-------------------------------------------+ |id |文本| +--+-------------------------------------------+ |4 |[如何->1.0,今天->1.0,是->1.0,它->1.0,你好->1.0,你->1.0]| |3 |[如何->2.0,你好->2.0,是->2.0,你->2.0]| |1 |[如何->2.0,你好->2.0,是->3.0,你->2.0,今天->1.0]| |2 |[这里->1.0,如何->1.0,是->1.0,是->1.0,它->1.0,你好->1.0,你->1.0]| +--+-------------------------------------------+
只有在文本部分相当大的情况下才值得尝试,否则DataFrame和Python对象之间所有必需的转换可能比收集列表更昂贵。

Hi!谢谢你的回答!不幸的是,我只能在下周的星期二测试它,但我不会忘记接受它:很抱歉反应太晚-直到今天我才有时间继续进行这方面的工作。你的答案绝对比爆炸版快!非常感谢。