Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/scala/16.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

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/apache-spark/5.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
Scala Spark:增加分区的数量而不引起混乱?_Scala_Apache Spark - Fatal编程技术网

Scala Spark:增加分区的数量而不引起混乱?

Scala Spark:增加分区的数量而不引起混乱?,scala,apache-spark,Scala,Apache Spark,当减少分区数量时,可以使用合并,这很好,因为它不会引起混乱,而且似乎可以立即工作(不需要额外的作业阶段) 有时我想做相反的事情,但是重新分区会导致混乱。我想几个月前,我通过使用CoalescedRDD和balanceSlack=1.0实现了这一点,所以会发生的事情是,它会分割一个分区,从而使生成的分区都位于同一节点上(如此小的净IO) 这种功能在Hadoop中是自动的,只需调整拆分大小即可。在Spark中,除非减少分区的数量,否则它似乎不会以这种方式工作。我认为解决方案可能是编写一个自定义分区器

当减少分区数量时,可以使用
合并
,这很好,因为它不会引起混乱,而且似乎可以立即工作(不需要额外的作业阶段)

有时我想做相反的事情,但是
重新分区
会导致混乱。我想几个月前,我通过使用
CoalescedRDD
balanceSlack=1.0
实现了这一点,所以会发生的事情是,它会分割一个分区,从而使生成的分区都位于同一节点上(如此小的净IO)

这种功能在Hadoop中是自动的,只需调整拆分大小即可。在Spark中,除非减少分区的数量,否则它似乎不会以这种方式工作。我认为解决方案可能是编写一个自定义分区器和一个自定义RDD,我们在其中定义
getPreferredLocations
。。。但我认为这是一件如此简单和普通的事情,肯定有一种直接的方式去做吗

尝试过的事情:


.set(“spark.default.parallelism”,partitions)
在我的
SparkConf
上,在阅读拼花地板的上下文中,我尝试了
sqlContext.sql("设置spark.sql.shuffle.partitions=…
,它在1.0.0上会导致一个错误,并不是我想要的,我想要分区号在所有类型的作业中都改变,而不仅仅是洗牌。

我不太明白你的意思。你是说你现在有5个分区,但在下一次操作之后你想要数据分布到10个分区吗?因为10,但仍然使用5没有多大意义…将数据发送到新分区的过程必须在某个时候进行

在执行
coalesce
时,您可以去掉未指定的分区,例如:如果您最初有100个分区,但在reduceByKey之后您得到了10个分区(在那里只有10个键),您可以设置
coalesce

如果您想让流程走另一条路,您可以强制进行某种分区:

[RDD].partitionBy(new HashPartitioner(100))
我不确定这就是你想要的,但希望如此。

请观看此空间


这种非常简单的显而易见的特性最终会被实现——我猜就在他们完成了
数据集中所有不必要的特性之后。

正如您所知,pyspark使用某种“懒惰”的运行方式。它只会在有一些动作要做时(例如“df.count()”或“df.show()”进行计算.因此,您可以在这些操作之间定义洗牌分区

你可以写:

sparkSession.sqlContext().sql("set spark.sql.shuffle.partitions=100")
# you spark code here with some transformation and at least one action
df = df.withColumn("sum", sum(df.A).over(your_window_function))
df.count() # your action

df = df.filter(df.B <10)
df = df.count()   

sparkSession.sqlContext().sql("set spark.sql.shuffle.partitions=10")
# you reduce the number of partition because you know you will have a lot 
# less data
df = df.withColumn("max", max(df.A).over(your_other_window_function))
df.count() # your action
sparkSession.sqlContext().sql(“set spark.sql.shuffle.partitions=100”)
#您可以在这里通过一些转换和至少一个操作来激发代码
df=df.withColumn(“sum”,sum(df.A).over(你的窗口函数))
df.count()#你的行动

df=df.filter(df.B每个分区都有一个位置,即一个节点,假设我有5个分区和5个节点。如果我调用
repartition
,或您的代码,将其分配到10个分区,这将洗牌数据-即5个节点中的每个节点的数据都可能通过网络传递到其他节点。我想要的是,Spark只需将每个分区拆分为2个,而不移动周围的任何数据-这是Hadoop在调整拆分设置时发生的情况。我不确定你是否能做到。我猜你需要某种
.forEachNode
函数。但我从未见过类似的情况。我不确定它是否能轻松实现。分区器必须为同一对象返回相同的分区我。默认情况下,Spark使用
HashPartitioner
,它对分区的数量进行hashCode模运算。如果你只是将数据分割成两个新分区,它们最终肯定不会出现在它们的位置上。这就是为什么需要混洗的原因。也许如果你有自己的分区器,它可以增加分区的数量,而不会在网上混洗。运气好吗找到此问题的解决方案?
spark.sql.shuffle.partitions
只会对洗牌操作(如联接、聚集和排序)产生影响,而不会对筛选产生影响